diff --git a/.github/workflows/docs.yml b/.github/workflows/docs.yml new file mode 100644 index 000000000..35c12179a --- /dev/null +++ b/.github/workflows/docs.yml @@ -0,0 +1,103 @@ +name: Docs site + +# Build and deploy the VitePress documentation site. +# +# Triggers: +# - push to master: build the site and deploy it to GitHub Pages. +# - pull_request to master: build the site only (no deploy) so doc-breaking +# changes surface in PR review. +# +# Action versions are pinned to commit SHAs (tag aliases appear in trailing +# comments) so a tag rewrite cannot silently change what runs. +on: + push: + branches: [ master ] + pull_request: + branches: [ master ] + +# Least-privilege defaults. The deploy job overrides this with the +# `pages: write` + `id-token: write` permissions GitHub Pages requires. +permissions: + contents: read + +# Only one deploy can run at a time. In-progress deploys are not canceled +# so that a started Pages publish gets to finish. +concurrency: + group: pages + cancel-in-progress: false + +env: + NODE_VERSION: '20' + DOTNET_VERSION: '8.0.x' + +jobs: + build: + name: Build VitePress site + runs-on: ubuntu-latest + steps: + - name: Checkout + uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 + with: + fetch-depth: 0 + + - name: Setup .NET + uses: actions/setup-dotnet@d4c94342e560b34958eacfc5d055d21461ed1c5d # v5.0.0 + with: + dotnet-version: ${{ env.DOTNET_VERSION }} + + - name: Install docfx + run: dotnet tool install -g docfx + + - name: Setup Node.js + uses: actions/setup-node@48b55a011bda9f5d6aeb4c2d9c7362e8dae4041e # v6.4.0 + with: + node-version: ${{ env.NODE_VERSION }} + cache: npm + cache-dependency-path: docs/package-lock.json + + - name: Install dependencies + working-directory: docs + run: npm ci + + - name: Generate API reference + run: bash docs/scripts/generate-api-ref.sh + + - name: Regenerate auto-generated reference pages + run: bash docs/scripts/generate-reference.sh + + - name: Verify reference pages match source (drift gate) + run: bash docs/scripts/generate-reference.sh --check + + # Only required on push-to-master (deploy path). Computes the correct + # base-path for the Pages site and writes it where later steps see it. + - name: Configure GitHub Pages + if: github.event_name == 'push' && github.ref == 'refs/heads/master' + uses: actions/configure-pages@45bfe0192ca1faeb007ade9deae92b16b8254a0d # v6.0.0 + + - name: Build site + working-directory: docs + run: npm run build + + # Upload the built artifact only on the deploy path. PR builds stop + # after the build step (success / failure surfaces in the check). + - name: Upload Pages artifact + if: github.event_name == 'push' && github.ref == 'refs/heads/master' + uses: actions/upload-pages-artifact@fc324d3547104276b827a68afc52ff2a11cc49c9 # v5.0.0 + with: + path: docs/.vitepress/dist + + deploy: + name: Deploy to GitHub Pages + needs: build + if: github.event_name == 'push' && github.ref == 'refs/heads/master' + runs-on: ubuntu-latest + permissions: + pages: write + id-token: write + environment: + name: github-pages + url: ${{ steps.deployment.outputs.page_url }} + steps: + - name: Deploy + id: deployment + uses: actions/deploy-pages@cd2ce8fcbc39b97be8ca5fce6e763baed58fa128 # v5.0.0 diff --git a/.gitignore b/.gitignore index 9c72a70d4..d97af7dd5 100644 --- a/.gitignore +++ b/.gitignore @@ -37,6 +37,9 @@ gulpfile.js package.json package-lock.json +# Documentation site needs its own Node manifest tracked. +!docs/package.json +!docs/package-lock.json # Visual Studio 2015 cache/options directory .vs/ @@ -318,3 +321,13 @@ $RECYCLE.BIN/ # Windows shortcuts *.lnk + +# VitePress documentation site +node_modules/ +docs/.vitepress/cache/ +docs/.vitepress/dist/ + +# docfx-generated API reference (regenerated by docs/scripts/generate-api-ref.sh +# on every CI run; keep the section index but ignore the per-type pages). +docs/api/** +!docs/api/index.md diff --git a/MTConnect.NET.sln b/MTConnect.NET.sln index 3bb77114c..c65b5e7d8 100644 --- a/MTConnect.NET.sln +++ b/MTConnect.NET.sln @@ -133,9 +133,9 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MTConnect-Compliance-Tests" EndProject Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MTConnect.NET-AgentModule-MqttRelay-Tests", "tests\MTConnect.NET-AgentModule-MqttRelay-Tests\MTConnect.NET-AgentModule-MqttRelay-Tests.csproj", "{E726EF85-4464-47D9-91EF-AD435D14F9D6}" EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MTConnect.NET-Tests-Agents", "tests\MTConnect.NET-Tests-Agents\MTConnect.NET-Tests-Agents.csproj", "{AE09D1CA-5572-40BF-B984-74230E8634E1}" +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MTConnect.NET-Docs-Tests", "tests\MTConnect.NET-Docs-Tests\MTConnect.NET-Docs-Tests.csproj", "{B340EB29-41C8-4C64-859F-387D51F401A5}" EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MTConnect.NET-HTTP-Tests", "tests\MTConnect.NET-HTTP-Tests\MTConnect.NET-HTTP-Tests.csproj", "{3E89B860-A428-470C-8E48-0DDABC4027F0}" +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MTConnect.NET-DocsGen", "build\MTConnect.NET-DocsGen\MTConnect.NET-DocsGen.csproj", "{17E64F59-0E62-4FCE-BEC4-EABBCF95B9A2}" EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution @@ -473,22 +473,22 @@ Global {E726EF85-4464-47D9-91EF-AD435D14F9D6}.Package|Any CPU.Build.0 = Debug|Any CPU {E726EF85-4464-47D9-91EF-AD435D14F9D6}.Release|Any CPU.ActiveCfg = Release|Any CPU {E726EF85-4464-47D9-91EF-AD435D14F9D6}.Release|Any CPU.Build.0 = Release|Any CPU - {AE09D1CA-5572-40BF-B984-74230E8634E1}.Debug|Any CPU.ActiveCfg = Debug|Any CPU - {AE09D1CA-5572-40BF-B984-74230E8634E1}.Debug|Any CPU.Build.0 = Debug|Any CPU - {AE09D1CA-5572-40BF-B984-74230E8634E1}.Docker|Any CPU.ActiveCfg = Debug|Any CPU - {AE09D1CA-5572-40BF-B984-74230E8634E1}.Docker|Any CPU.Build.0 = Debug|Any CPU - {AE09D1CA-5572-40BF-B984-74230E8634E1}.Package|Any CPU.ActiveCfg = Debug|Any CPU - {AE09D1CA-5572-40BF-B984-74230E8634E1}.Package|Any CPU.Build.0 = Debug|Any CPU - {AE09D1CA-5572-40BF-B984-74230E8634E1}.Release|Any CPU.ActiveCfg = Release|Any CPU - {AE09D1CA-5572-40BF-B984-74230E8634E1}.Release|Any CPU.Build.0 = Release|Any CPU - {3E89B860-A428-470C-8E48-0DDABC4027F0}.Debug|Any CPU.ActiveCfg = Debug|Any CPU - {3E89B860-A428-470C-8E48-0DDABC4027F0}.Debug|Any CPU.Build.0 = Debug|Any CPU - {3E89B860-A428-470C-8E48-0DDABC4027F0}.Docker|Any CPU.ActiveCfg = Debug|Any CPU - {3E89B860-A428-470C-8E48-0DDABC4027F0}.Docker|Any CPU.Build.0 = Debug|Any CPU - {3E89B860-A428-470C-8E48-0DDABC4027F0}.Package|Any CPU.ActiveCfg = Debug|Any CPU - {3E89B860-A428-470C-8E48-0DDABC4027F0}.Package|Any CPU.Build.0 = Debug|Any CPU - {3E89B860-A428-470C-8E48-0DDABC4027F0}.Release|Any CPU.ActiveCfg = Release|Any CPU - {3E89B860-A428-470C-8E48-0DDABC4027F0}.Release|Any CPU.Build.0 = Release|Any CPU + {B340EB29-41C8-4C64-859F-387D51F401A5}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {B340EB29-41C8-4C64-859F-387D51F401A5}.Debug|Any CPU.Build.0 = Debug|Any CPU + {B340EB29-41C8-4C64-859F-387D51F401A5}.Docker|Any CPU.ActiveCfg = Debug|Any CPU + {B340EB29-41C8-4C64-859F-387D51F401A5}.Docker|Any CPU.Build.0 = Debug|Any CPU + {B340EB29-41C8-4C64-859F-387D51F401A5}.Package|Any CPU.ActiveCfg = Debug|Any CPU + {B340EB29-41C8-4C64-859F-387D51F401A5}.Package|Any CPU.Build.0 = Debug|Any CPU + {B340EB29-41C8-4C64-859F-387D51F401A5}.Release|Any CPU.ActiveCfg = Release|Any CPU + {B340EB29-41C8-4C64-859F-387D51F401A5}.Release|Any CPU.Build.0 = Release|Any CPU + {17E64F59-0E62-4FCE-BEC4-EABBCF95B9A2}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {17E64F59-0E62-4FCE-BEC4-EABBCF95B9A2}.Debug|Any CPU.Build.0 = Debug|Any CPU + {17E64F59-0E62-4FCE-BEC4-EABBCF95B9A2}.Docker|Any CPU.ActiveCfg = Debug|Any CPU + {17E64F59-0E62-4FCE-BEC4-EABBCF95B9A2}.Docker|Any CPU.Build.0 = Debug|Any CPU + {17E64F59-0E62-4FCE-BEC4-EABBCF95B9A2}.Package|Any CPU.ActiveCfg = Debug|Any CPU + {17E64F59-0E62-4FCE-BEC4-EABBCF95B9A2}.Package|Any CPU.Build.0 = Debug|Any CPU + {17E64F59-0E62-4FCE-BEC4-EABBCF95B9A2}.Release|Any CPU.ActiveCfg = Release|Any CPU + {17E64F59-0E62-4FCE-BEC4-EABBCF95B9A2}.Release|Any CPU.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE @@ -541,8 +541,8 @@ Global {94E2A2D0-71FD-4563-B1A3-FC58136017E0} = {14375E03-6BF8-45E6-B868-D2399368992B} {37320C1F-5E50-4CDF-B00D-0E0ADB4F1AE6} = {94E2A2D0-71FD-4563-B1A3-FC58136017E0} {E726EF85-4464-47D9-91EF-AD435D14F9D6} = {14375E03-6BF8-45E6-B868-D2399368992B} - {AE09D1CA-5572-40BF-B984-74230E8634E1} = {14375E03-6BF8-45E6-B868-D2399368992B} - {3E89B860-A428-470C-8E48-0DDABC4027F0} = {14375E03-6BF8-45E6-B868-D2399368992B} + {B340EB29-41C8-4C64-859F-387D51F401A5} = {14375E03-6BF8-45E6-B868-D2399368992B} + {17E64F59-0E62-4FCE-BEC4-EABBCF95B9A2} = {BBF53739-168D-4635-8595-083AC0C65E4C} EndGlobalSection GlobalSection(ExtensibilityGlobals) = postSolution SolutionGuid = {CC13D3AD-18BF-4695-AB2A-087EF0885B20} diff --git a/README.md b/README.md index 2ffcd50c6..f89680129 100644 --- a/README.md +++ b/README.md @@ -34,6 +34,23 @@ +## Documentation + +The full documentation site is built with VitePress under [`docs/`](docs/) and published to GitHub Pages. The source lives in this repository so every change rides the same review process as the libraries. + +- **Getting started**, **Configure & Use**, **Concepts**, **Wire formats**, **Modules**, **CLI**, **Cookbook**, and **Troubleshooting** narrative pages sit under [`docs/`](docs/). +- The **API reference** is generated by [docfx](https://dotnet.github.io/docfx/) from the Release `net8.0` build of every shipped library. Regenerate locally with `bash docs/scripts/generate-api-ref.sh`; the same script runs in CI ahead of every VitePress build. +- **Compliance** posture and per-version compatibility matrices sit under [`docs/compliance/`](docs/compliance/). + +Build the site locally: + +```bash +cd docs +npm install +npm run build # outputs to docs/.vitepress/dist +npm run dev # local dev server with hot reload +``` + ## Overview MTConnect.NET is a fully featured and fully Open Source **[.NET](https://dotnet.microsoft.com/)** library for **[MTConnect](https://www.mtconnect.org/)** to develop Agents, Adapters, and Clients. Supports MTConnect versions up to 2.7. A pre-compiled Agent application is available to download as well as an Adapter application that can be easily customized. diff --git a/adapter/Directory.Build.props b/adapter/Directory.Build.props new file mode 100644 index 000000000..71c6f4b81 --- /dev/null +++ b/adapter/Directory.Build.props @@ -0,0 +1,25 @@ + + + + + + + + true + $(WarningsAsErrors);CS1591 + + + diff --git a/adapter/MTConnect.NET-Adapter/Program.cs b/adapter/MTConnect.NET-Adapter/Program.cs index b29ef7e86..34bf38a3a 100644 --- a/adapter/MTConnect.NET-Adapter/Program.cs +++ b/adapter/MTConnect.NET-Adapter/Program.cs @@ -6,6 +6,15 @@ namespace MTConnect.Applications { + /// + /// Process entry point for the standalone mtconnect.net-adapter + /// host. Wires the bundled implementation to + /// an and runs the adapter + /// in blocking mode. The CLI surface (commands such as run, + /// debug, install, …) is implemented by + /// MTConnectAdapterApplication; see docs/reference/cli.md + /// for the full reference. + /// public class Program { // This is the Application Name shown in the Console header information @@ -17,6 +26,14 @@ public class Program private const string ApplicationCopyright = "Copyright 2024 TrakHound Inc., All Rights Reserved"; + /// + /// Process entry point. Prints the console header, instantiates + /// the bundled , and delegates to + /// + /// in blocking mode. + /// + /// Command-line arguments forwarded to + /// . public static void Main(string[] args) { // Print an application header to the console diff --git a/adapter/MTConnect.NET-Adapter/README.md b/adapter/MTConnect.NET-Adapter/README.md new file mode 100644 index 000000000..99009178e --- /dev/null +++ b/adapter/MTConnect.NET-Adapter/README.md @@ -0,0 +1,106 @@ +![MTConnect.NET Logo](https://raw.githubusercontent.com/TrakHound/MTConnect.NET/master/img/mtconnect-net-03-md.png) + +# MTConnect.NET Adapter + +[![MTConnect.NET](https://github.com/TrakHound/MTConnect.NET/actions/workflows/dotnet.yml/badge.svg)](https://github.com/TrakHound/MTConnect.NET/actions/workflows/dotnet.yml) + +## Overview +This project is a ready-to-run MTConnect Adapter application. It reads data from a connected device or simulator (implemented in `DataSource.cs`) and forwards that data to an MTConnect Agent using the SHDR protocol or via MQTT, depending on which output modules are configured. + +The application shell is thin: `Program.cs` wires a `DataSource` instance to an `MTConnectAdapterApplication` and delegates all lifecycle management—including command-line parsing, Windows Service support, and configuration file monitoring—to the [MTConnect.NET-Applications-Adapter](../MTConnect.NET-Applications-Adapter/) library. + +To build your own adapter for a specific machine or controller, replace the `DataSource` class with one that reads from your hardware, then configure the output modules in `adapter.config.yaml`. + +## Usage +The adapter can be run from a command-line prompt or installed as a Windows Service: + +``` +adapter [help|install|install-start|start|stop|remove|debug|run|run-service] [configuration_file] + +-------------------- + +Options : + + help | Prints usage information + install | Install as a Service + install-start | Install as a Service and Start the Service + start | Start the Service + stop | Stop the Service + remove | Remove the Service + debug | Runs the Adapter in the terminal (with verbose logging) + run | Runs the Adapter in the terminal + run-service | Runs the Adapter as a Service + +Arguments : +-------------------- + + configuration_file | Specifies the Adapter Configuration file to load + Default : adapter.config.yaml +``` + +#### Example 1: +Run the adapter in the terminal +``` +adapter run +``` + +#### Example 2: +Run the adapter in the terminal with verbose (debug) logging +``` +adapter debug +``` + +#### Example 3: +Install the adapter as a Windows Service (requires Administrator privileges) +``` +adapter install +``` + +#### Example 4: +Install and immediately start the adapter as a Windows Service using a specific configuration file +``` +adapter install-start adapter-production.yaml +``` + +## Configuration +The default configuration file (`adapter.config.yaml`) is shown below: + +```yaml +id: PatrickAdapter +deviceKey: OKUMA-Lathe + +modules: + +- shdr: + port: 7878 + +- mqtt: + server: localhost + port: 1883 +``` + +* `id` - A unique identifier for this adapter instance. + +* `deviceKey` - The Name or UUID of the Device this adapter reports for. + +* `modules` - Output module configurations. Each entry specifies the protocol used to forward observations to an MTConnect Agent. + +For the full set of configuration properties supported by each module, see: +- [MTConnect.NET-AdapterModule-SHDR](../Modules/MTConnect.NET-AdapterModule-SHDR/) — SHDR output module +- [MTConnect.NET-AdapterModule-MQTT](../Modules/MTConnect.NET-AdapterModule-MQTT/) — MQTT output module + +## Build +``` +dotnet publish -c:Release -f:net8.0 -r:win-x64 -p:PublishSingleFile=true --self-contained false +``` + +## Source Code +This project uses the [MTConnect.NET-Applications-Adapter](../MTConnect.NET-Applications-Adapter/) library to provide the application host. Creating a custom adapter requires only implementing a `DataSource` subclass and configuring the output modules. + +## Contribution / Feedback +- Please use the [Issues](https://github.com/TrakHound/MTConnect.NET/issues) tab to create issues for specific problems that you may encounter +- Please feel free to use the [Pull Requests](https://github.com/TrakHound/MTConnect.NET/pulls) tab for any suggested improvements to the source code +- For any other questions or feedback, please contact TrakHound directly at **info@trakhound.com**. + +## License +This application and its source code is licensed under the [MIT License](https://choosealicense.com/licenses/mit/) and is free to use and distribute. diff --git a/adapter/MTConnect.NET-Applications-Adapter/Configurations/AdapterConfigurationFileWatcher.cs b/adapter/MTConnect.NET-Applications-Adapter/Configurations/AdapterConfigurationFileWatcher.cs index db275e90a..d72f2dde6 100644 --- a/adapter/MTConnect.NET-Applications-Adapter/Configurations/AdapterConfigurationFileWatcher.cs +++ b/adapter/MTConnect.NET-Applications-Adapter/Configurations/AdapterConfigurationFileWatcher.cs @@ -11,9 +11,25 @@ namespace MTConnect.Configurations /// The type of MTConnectAgentConfiguration file to read public class AdapterConfigurationFileWatcher : ConfigurationFileWatcher, IAdapterConfigurationFileWatcher where TConfiguration : AdapterApplicationConfiguration { + /// + /// Initialises a new watcher against , + /// polling for changes at + /// milliseconds. + /// + /// Filesystem path to watch. + /// Poll interval in milliseconds. public AdapterConfigurationFileWatcher(string path, int interval = DefaultInterval) :base(path, interval) { } + /// + /// Reads the file at as YAML or JSON + /// (selected by file extension) and binds it to + /// . Returns default + /// when the read fails or the extension is unrecognised. + /// + /// Filesystem path of the configuration + /// file. + /// The parsed configuration, or default. protected override AdapterApplicationConfiguration OnRead(string path) { AdapterApplicationConfiguration configuration = default; diff --git a/adapter/MTConnect.NET-Applications-Adapter/IMTConnectAdapterApplication.cs b/adapter/MTConnect.NET-Applications-Adapter/IMTConnectAdapterApplication.cs index 8efd08400..d871ff041 100644 --- a/adapter/MTConnect.NET-Applications-Adapter/IMTConnectAdapterApplication.cs +++ b/adapter/MTConnect.NET-Applications-Adapter/IMTConnectAdapterApplication.cs @@ -12,15 +12,35 @@ namespace MTConnect.Applications /// public interface IMTConnectAdapterApplication { + /// + /// Windows-service identifier the host registers under (e.g. + /// MTConnect-Adapter). Ignored on non-Windows platforms. + /// string ServiceName { get; } + /// + /// Human-readable Windows-service display name. + /// string ServiceDisplayName { get; } + /// + /// Long-form description recorded against the Windows service. + /// string ServiceDescription { get; } + /// + /// Active data-source instance (the data-pull worker that + /// reads from the underlying device or simulator and writes + /// into the adapter). + /// IMTConnectDataSource DataSource { get; } + /// + /// Raised when the configuration-file watcher detects a change + /// and the adapter is restarting with the freshly-loaded + /// . + /// event EventHandler OnRestart; diff --git a/adapter/MTConnect.NET-Applications-Adapter/MTConnectAdapterApplication.cs b/adapter/MTConnect.NET-Applications-Adapter/MTConnectAdapterApplication.cs index 296dad48f..0f90391ab 100644 --- a/adapter/MTConnect.NET-Applications-Adapter/MTConnectAdapterApplication.cs +++ b/adapter/MTConnect.NET-Applications-Adapter/MTConnectAdapterApplication.cs @@ -26,6 +26,8 @@ public class MTConnectAdapterApplication : IMTConnectAdapterApplication private const string DefaultServiceDisplayName = "MTConnect.NET Adapter"; private const string DefaultServiceDescription = "MTConnect Adapter to transfer data to an MTConnect Agent"; + /// NLog logger for application-level diagnostics + /// (startup, shutdown, configuration load). protected readonly Logger _applicationLogger = LogManager.GetLogger("application-logger"); private readonly Dictionary _adapters = new Dictionary(); private readonly Dictionary _loggers = new Dictionary(); @@ -35,25 +37,51 @@ public class MTConnectAdapterApplication : IMTConnectAdapterApplication private IMTConnectDataSource _dataSource; private bool _started = false; + /// When true, the adapter emits a console + /// header at startup and includes per-component summaries in + /// the startup log. protected bool _verboseLogging = true; + /// NLog log-level applied to every internal logger. + /// Defaults to ; the debug + /// CLI command overrides it. protected LogLevel _logLevel = LogLevel.Debug; + /// File-system watcher that reloads the adapter + /// configuration when the underlying YAML / JSON file + /// changes. protected IConfigurationFileWatcher _adapterConfigurationWatcher; + /// + /// Human-readable label shown in the console header (e.g. + /// MTConnect.NET Adapter). + /// public string ServiceLabel { get; set; } + /// public string ServiceName { get; set; } + /// public string ServiceDisplayName { get; set; } + /// public string ServiceDescription { get; set; } + /// public IMTConnectDataSource DataSource => _dataSource; + /// public event EventHandler OnRestart; + /// + /// Initialises a new instance against the supplied data source. + /// Subscribes to the data source's observation / asset / device + /// events so each datum is forwarded into the adapter's + /// outbound queue. + /// + /// Data-pull worker that reads from + /// the underlying device. public MTConnectAdapterApplication(IMTConnectDataSource dataSource) { _dataSource = dataSource; @@ -239,9 +267,24 @@ public void Run(string[] args, bool isBlocking = false) } } + /// + /// Extension hook: invoked once the host has finished parsing + /// the command-line arguments. Override in a derived class to + /// inspect or react to the raw arguments. + /// + /// Raw command-line arguments. protected virtual void OnCommandLineArgumentsRead(string[] args) { } + /// + /// Loads the configuration from + /// and delegates to the + /// in-memory overload. + /// + /// Path to the adapter's + /// configuration file. + /// When true, the adapter + /// emits a console header at startup. public void StartAdapter(string configurationPath, bool verboseLogging = false) { var configuration = AdapterApplicationConfiguration.Read(configurationPath); @@ -250,6 +293,16 @@ public void StartAdapter(string configurationPath, bool verboseLogging = false) StartAdapter(configuration, verboseLogging); } + /// + /// Loads every configured adapter module, wires each module's + /// outbound queue to a dedicated , + /// starts the data source, and optionally wires the + /// configuration-file watcher. Idempotent. + /// + /// Already-loaded adapter + /// configuration. + /// When true, the adapter + /// emits a console header at startup. public void StartAdapter(IAdapterApplicationConfiguration configuration, bool verboseLogging = false) { if (!_started && configuration != null) @@ -294,6 +347,11 @@ public void StartAdapter(IAdapterApplicationConfiguration configuration, bool ve } } + /// + /// Stops the configuration watcher, every module's adapter, + /// and the configured modules. Idempotent if the adapter never + /// started. + /// public void StopAdapter() { if (_started) @@ -316,13 +374,23 @@ public void StopAdapter() } - protected virtual void OnStartAdapter() + /// + /// Extension hook: fires after every module + adapter is + /// wired but before the data source produces its first + /// reading. The default implementation starts the data source. + /// + protected virtual void OnStartAdapter() { // Start DataSource if (_dataSource != null) _dataSource.Start(); } - protected virtual void OnStopAdapter() + /// + /// Extension hook: fires once has + /// stopped every module + adapter. The default implementation + /// stops the data source. + /// + protected virtual void OnStopAdapter() { // Stop DataSource if (_dataSource != null) _dataSource.Stop(); @@ -353,6 +421,13 @@ private void AdapterConfigurationFileUpdated(object sender, AdapterApplicationCo } } + /// + /// Extension hook: fires after the configuration watcher + /// reloads the configuration from disk. Override to react to + /// runtime configuration changes. + /// + /// Freshly-reloaded + /// configuration. protected virtual void OnAdapterConfigurationUpdated(AdapterApplicationConfiguration configuration) { } private void AdapterConfigurationFileError(object sender, string message) @@ -449,10 +524,23 @@ private void PrintHelp() OnPrintHelpArguments(); } + /// + /// Extension hook: returns extra text appended to the + /// Usage: line printed by the help command. + /// + /// Extra usage text, or an empty string for none. protected virtual string OnPrintHelpUsage() { return ""; } + /// + /// Extension hook: prints extra rows in the Options: + /// section of the help command. + /// protected virtual void OnPrintHelpOptions() { } + /// + /// Extension hook: prints extra rows in the Arguments: + /// section of the help command. + /// protected virtual void OnPrintHelpArguments() { } #endregion diff --git a/adapter/MTConnect.NET-Applications-Adapter/README.md b/adapter/MTConnect.NET-Applications-Adapter/README.md new file mode 100644 index 000000000..9a1d29501 --- /dev/null +++ b/adapter/MTConnect.NET-Applications-Adapter/README.md @@ -0,0 +1,94 @@ +![MTConnect.NET Logo](https://raw.githubusercontent.com/TrakHound/MTConnect.NET/master/img/mtconnect-net-03-md.png) + +# MTConnect.NET-Applications-Adapter +MTConnect.NET-Applications-Adapter contains the base classes and infrastructure needed to build a fully featured MTConnect Adapter application, including command-line argument handling, Windows Service support, configuration file monitoring, and output module management. + +## Nuget + + + + + + + + + + + + + + + +
Package NameDownloadsLink
MTConnect.NET-Applications-Adapterhttps://www.nuget.org/packages/MTConnect.NET-Applications-Adapter
+ +## Overview +This library makes it straightforward to create a production-quality MTConnect Adapter application. The central class is `MTConnectAdapterApplication`, which handles: + +- **Command-line interface** — `run`, `debug`, `install`, `install-start`, `start`, `stop`, `remove`, and `run-service` commands identical to the MTConnect Agent CLI. +- **Windows Service** — installs and runs as a background service on Windows; degrades gracefully on Linux. +- **Configuration management** — reads `adapter.config.yaml` on startup; optional file-system monitoring restarts the adapter automatically when the configuration file changes. +- **Module loading** — discovers and starts all configured output modules (SHDR, MQTT, etc.) and wires each module's outbound queue to a dedicated `MTConnectAdapter` instance. +- **Data source lifecycle** — starts and stops the user-supplied `IMTConnectDataSource` implementation in sync with the adapter modules. +- **Logging** — structured NLog logging with separate log targets for application and per-module output. + +## Usage + +### Minimal application +```csharp +using MTConnect.Applications; + +// 1. Implement your data source +var dataSource = new MyDataSource(); + +// 2. Create the application host +var app = new MTConnectAdapterApplication(dataSource); + +// 3. Run (pass args so CLI commands work) +app.Run(args, isBlocking: true); +``` + +### Implementing a data source +```csharp +using MTConnect.Input; + +public class MyDataSource : MTConnectDataSource +{ + protected override void OnRead() + { + // Called on the configured interval; add observations here + AddObservation("L2estop", "ARMED"); + AddObservation("L2p1execution", "AUTOMATIC"); + } +} +``` + +## Configuration +The adapter reads `adapter.config.yaml` from its working directory. The full set of supported properties is documented in [MTConnect.NET-Common/Configurations](../../libraries/MTConnect.NET-Common/). Key top-level properties: + +* `id` - A unique identifier for this adapter instance. +* `deviceKey` - The Name or UUID of the Device this adapter reports for. +* `writeInterval` - The interval (in milliseconds) at which buffered observations are flushed to the output modules. +* `enableBuffer` - Whether to buffer observations between write intervals. +* `monitorConfigurationFiles` - Whether to watch the configuration file for changes and automatically restart on update. +* `configurationFileRestartInterval` - Minimum time (in seconds) between restarts triggered by configuration file changes. +* `serviceName` - Windows Service name (used when installing or removing the service). +* `serviceAutoStart` - When `true`, the Windows Service starts automatically at boot. +* `modules` - List of output module configurations (SHDR, MQTT, etc.). + +## Output Modules +Each entry in the `modules` list activates an output module that forwards observations from the data source to an MTConnect Agent: + +- [MTConnect.NET-AdapterModule-SHDR](../Modules/MTConnect.NET-AdapterModule-SHDR/) — SHDR TCP server +- [MTConnect.NET-AdapterModule-MQTT](../Modules/MTConnect.NET-AdapterModule-MQTT/) — MQTT publisher + +## Related Libraries +- [MTConnect.NET-Common](../../libraries/MTConnect.NET-Common/) — Core MTConnect entity model +- [MTConnect.NET-Applications-Agents](../../agent/MTConnect.NET-Applications-Agents/) — Symmetrical host library for MTConnect Agent applications + +## Contribution / Feedback +- Please use the [Issues](https://github.com/TrakHound/MTConnect.NET/issues) tab to create issues for specific problems that you may encounter +- Please feel free to use the [Pull Requests](https://github.com/TrakHound/MTConnect.NET/pulls) tab for any suggested improvements to the source code +- For any other questions or feedback, please contact TrakHound directly at **info@trakhound.com**. + +## License +This library and its source code is licensed under the [MIT License](https://choosealicense.com/licenses/mit/) and is free to use and distribute. diff --git a/adapter/MTConnect.NET-Applications-Adapter/Service.cs b/adapter/MTConnect.NET-Applications-Adapter/Service.cs index 30a162c75..3ef9aa201 100644 --- a/adapter/MTConnect.NET-Applications-Adapter/Service.cs +++ b/adapter/MTConnect.NET-Applications-Adapter/Service.cs @@ -15,34 +15,72 @@ public class Service : MTConnectAdapterService private readonly IMTConnectAdapterApplication _application; + /// + /// Initialises a new Windows-service wrapper that delegates + /// every Start / Stop action to the supplied + /// adapter application. + /// + /// Adapter application the service + /// hosts. + /// Human-readable label. + /// Windows-service identifier. + /// Service display name. + /// Service description. + /// Whether the service should be set + /// to start automatically on boot. public Service(IMTConnectAdapterApplication application, string label = null, string name = null, string displayName = null, string description = null, bool autoStart = true) - : base(label, name, displayName, description, autoStart) + : base(label, name, displayName, description, autoStart) { _application = application; } + /// + /// Service-control hook: delegates to + /// . + /// + /// Path to the adapter's + /// configuration file. protected override void StartAdapter(string configurationPath) { _application.StartAdapter(configurationPath); } + /// + /// Service-control hook: delegates to + /// . + /// protected override void StopAdapter() { _application.StopAdapter(); } + /// + /// Routes informational service messages to the + /// service-logger NLog target. + /// + /// Message to log. protected override void OnLogInformation(string message) { _serviceLogger.Info(message); } + /// + /// Routes warning service messages to the + /// service-logger NLog target. + /// + /// Message to log. protected override void OnLogWarning(string message) { _serviceLogger.Warn(message); } + /// + /// Routes error service messages to the service-logger + /// NLog target. + /// + /// Message to log. protected override void OnLogError(string message) { _serviceLogger.Error(message); diff --git a/adapter/Modules/MTConnect.NET-AdapterModule-MQTT/Module.cs b/adapter/Modules/MTConnect.NET-AdapterModule-MQTT/Module.cs index 1c81abd92..607feea20 100644 --- a/adapter/Modules/MTConnect.NET-AdapterModule-MQTT/Module.cs +++ b/adapter/Modules/MTConnect.NET-AdapterModule-MQTT/Module.cs @@ -18,8 +18,19 @@ namespace MTConnect { + /// + /// Adapter module that publishes observations to a downstream MQTT + /// broker. Each adapter-side observation is serialised via the + /// configured and + /// published to . Supports + /// TLS (mutual or CA-only), authentication, and configurable QoS. + /// public class Module : MTConnectAdapterModule { + /// + /// Token used in adapter.config.yaml to bind this + /// module (type: mqtt). + /// public const string ConfigurationTypeId = "mqtt"; private const string ModuleId = "MQTT"; @@ -29,6 +40,17 @@ public class Module : MTConnectAdapterModule private CancellationTokenSource _stop; + /// + /// Initialises the module against the supplied + /// and configuration payload. The MQTT + /// connection itself is opened by the background worker that + /// spawns. + /// + /// Adapter-side identifier the host passes + /// through. + /// Raw configuration payload + /// bound to ; defaults to a + /// fresh instance when null. public Module(string id, object moduleConfiguration) : base(id) { Id = ModuleId; @@ -41,6 +63,10 @@ public Module(string id, object moduleConfiguration) : base(id) } + /// + /// Module lifecycle hook: spawns the MQTT publish worker on a + /// background task. The worker reconnects on transport failure. + /// protected override void OnStart() { _stop = new CancellationTokenSource(); @@ -48,6 +74,10 @@ protected override void OnStart() _ = Task.Run(Worker, _stop.Token); } + /// + /// Module lifecycle hook: cancels the publish worker and + /// disposes the MQTT client. + /// protected override void OnStop() { if (_stop != null) _stop.Cancel(); @@ -153,6 +183,15 @@ private async Task Worker() } + /// + /// Serialises the supplied observations via the configured + /// document format and publishes them to + /// {Topic}/observations with the configured QoS and the + /// retain flag set. + /// + /// Observations to publish. + /// Always true; transport-level errors are + /// logged but do not break the adapter pipeline. public override bool AddObservations(IEnumerable observations) { if (_mqttClient != null && !observations.IsNullOrEmpty()) @@ -176,6 +215,14 @@ public override bool AddObservations(IEnumerable observations return true; } + /// + /// Serialises the supplied assets via the configured document + /// format and publishes them to {Topic}/assets with the + /// configured QoS and the retain flag set. + /// + /// Assets to publish. + /// Always true; transport-level errors are + /// logged but do not break the adapter pipeline. public override bool AddAssets(IEnumerable assets) { if (_mqttClient != null && !assets.IsNullOrEmpty()) @@ -199,6 +246,14 @@ public override bool AddAssets(IEnumerable assets) return true; } + /// + /// Serialises the supplied device descriptors via the configured + /// document format and publishes them to {Topic}/devices + /// with the configured QoS and the retain flag set. + /// + /// Devices to publish. + /// Always true; transport-level errors are + /// logged but do not break the adapter pipeline. public override bool AddDevices(IEnumerable devices) { if (_mqttClient != null && !devices.IsNullOrEmpty()) diff --git a/adapter/Modules/MTConnect.NET-AdapterModule-MQTT/ModuleConfiguration.cs b/adapter/Modules/MTConnect.NET-AdapterModule-MQTT/ModuleConfiguration.cs index 358ea77e7..cdbe35d20 100644 --- a/adapter/Modules/MTConnect.NET-AdapterModule-MQTT/ModuleConfiguration.cs +++ b/adapter/Modules/MTConnect.NET-AdapterModule-MQTT/ModuleConfiguration.cs @@ -3,44 +3,114 @@ namespace MTConnect.Configurations { + /// + /// Configuration shape for the MQTT output adapter module. Bound + /// from the adapter module's section of adapter.config.yaml. + /// public class ModuleConfiguration { + /// + /// The MQTT broker hostname to publish to. + /// public string Server { get; set; } + /// + /// The MQTT broker port number to publish to. + /// public int Port { get; set; } + /// + /// Username for broker authentication. Leave blank for + /// anonymous brokers. + /// public string Username { get; set; } + /// + /// Password for broker authentication. Leave blank for + /// anonymous brokers. + /// public string Password { get; set; } + /// + /// MQTT client identifier; the broker disambiguates concurrent + /// connections by this value. + /// public string ClientId { get; set; } + /// + /// MQTT Quality-of-Service level (0 = at most once, + /// 1 = at least once, 2 = exactly once). + /// public int Qos { get; set; } + /// + /// Filesystem path to the Certificate Authority bundle used + /// when is on. + /// public string CertificateAuthority { get; set; } + /// + /// Filesystem path to the PEM-encoded client certificate. + /// public string PemCertificate { get; set; } + /// + /// Filesystem path to the PEM-encoded private key paired with + /// . + /// public string PemPrivateKey { get; set; } + /// + /// When true, certificate-chain validation errors are + /// ignored. Intended for local development; never enable in + /// production. + /// public bool AllowUntrustedCertificates { get; set; } + /// + /// Whether the connection should be wrapped in TLS. + /// public bool UseTls { get; set; } + /// + /// Connect timeout in milliseconds. + /// public int ConnectionTimeout { get; set; } + /// + /// Reconnect delay in milliseconds after a disconnection. + /// public int ReconnectInterval { get; set; } + /// + /// MQTT topic the adapter publishes to. + /// public string Topic { get; set; } + /// + /// Local device key whose observations should be published on + /// . Matches against device UUID or name. + /// public string DeviceKey { get; set; } + /// + /// Document-format identifier used to serialise each published + /// payload (e.g. json, xml). + /// public string DocumentFormat { get; set; } + /// + /// Initialises a new instance with the bundled defaults + /// (Server = "localhost", Port = 7878, + /// ConnectionTimeout = 5000 ms, + /// ReconnectInterval = 10000 ms, + /// DocumentFormat = "json"). YAML / JSON values override + /// the defaults. + /// public ModuleConfiguration() { Server = "localhost"; @@ -50,4 +120,4 @@ public ModuleConfiguration() DocumentFormat = "json"; } } -} \ No newline at end of file +} diff --git a/adapter/Modules/MTConnect.NET-AdapterModule-SHDR/Module.cs b/adapter/Modules/MTConnect.NET-AdapterModule-SHDR/Module.cs index 22e17717f..614ce0f83 100644 --- a/adapter/Modules/MTConnect.NET-AdapterModule-SHDR/Module.cs +++ b/adapter/Modules/MTConnect.NET-AdapterModule-SHDR/Module.cs @@ -15,8 +15,19 @@ namespace MTConnect { + /// + /// Adapter module that listens for SHDR-protocol TCP clients (i.e. + /// downstream MTConnect agents) and streams observations / assets / + /// device models as SHDR text lines. The module owns an + /// and routes outbound + /// data to every connected agent client. + /// public class Module : MTConnectAdapterModule { + /// + /// Token used in adapter.config.yaml to bind this + /// module (type: shdr). + /// public const string ConfigurationTypeId = "shdr"; private const string ModuleId = "SDHR"; @@ -28,6 +39,16 @@ public class Module : MTConnectAdapterModule private CancellationTokenSource _stop; + /// + /// Initialises the module, binds the supplied configuration + /// payload to , and wires the + /// connect / + /// disconnect / ping / pong events. + /// + /// Adapter-side identifier the host passes + /// through. + /// Raw configuration payload + /// bound to . public Module(string id, object moduleConfiguration) : base(id) { Id = ModuleId; @@ -45,6 +66,10 @@ public Module(string id, object moduleConfiguration) : base(id) } + /// + /// Module lifecycle hook: starts the SHDR-protocol connection + /// listener so downstream agents can connect. + /// protected override void OnStart() { _stop = new CancellationTokenSource(); @@ -53,6 +78,11 @@ protected override void OnStart() _connectionListener.Start(_stop.Token); } + /// + /// Module lifecycle hook: cancels the connection-listener + /// token and stops the listener. Existing clients drain via + /// their own disconnect handlers. + /// protected override void OnStop() { if (_stop != null) _stop.Cancel(); @@ -62,6 +92,15 @@ protected override void OnStop() #region "Entities" + /// + /// Translates each observation into one or more SHDR text + /// lines (data items, messages, conditions, time-series, + /// data-sets, tables) and writes them to every connected + /// agent client. + /// + /// Observations to transmit. + /// Always true; transport-level errors per + /// client are caught inside WriteLine. public override bool AddObservations(IEnumerable observations) { // DataItems @@ -151,6 +190,13 @@ public override bool AddObservations(IEnumerable observations return true; } + /// + /// Serialises each asset into an SHDR asset block and writes + /// it to every connected agent client. + /// + /// Assets to transmit. + /// Always true; transport-level errors per + /// client are caught inside WriteLine. public override bool AddAssets(IEnumerable assets) { foreach (var asset in assets) @@ -163,6 +209,13 @@ public override bool AddAssets(IEnumerable assets) return true; } + /// + /// Serialises each device into an SHDR device block and writes + /// it to every connected agent client. + /// + /// Devices to transmit. + /// Always true; transport-level errors per + /// client are caught inside WriteLine. public override bool AddDevices(IEnumerable devices) { foreach (var device in devices) @@ -257,6 +310,14 @@ private void RemoveAgentClient(string clientId) #region "Write" + /// + /// Writes the supplied SHDR text line to every connected agent + /// client. Per-client transport failures are caught and the + /// affected client is silently dropped from the broadcast set. + /// + /// SHDR-encoded text line. + /// true when at least one client was written + /// to; false otherwise. protected bool WriteLine(string line) { if (!string.IsNullOrEmpty(line)) diff --git a/adapter/Modules/MTConnect.NET-AdapterModule-SHDR/ModuleConfiguration.cs b/adapter/Modules/MTConnect.NET-AdapterModule-SHDR/ModuleConfiguration.cs index 7878ccc88..c0c1fee74 100644 --- a/adapter/Modules/MTConnect.NET-AdapterModule-SHDR/ModuleConfiguration.cs +++ b/adapter/Modules/MTConnect.NET-AdapterModule-SHDR/ModuleConfiguration.cs @@ -3,6 +3,10 @@ namespace MTConnect.Configurations { + /// + /// Configuration shape for the SHDR output adapter module. Bound + /// from the adapter module's section of adapter.config.yaml. + /// public class ModuleConfiguration { /// @@ -38,6 +42,15 @@ public class ModuleConfiguration public string TimeZoneOutput { get; set; } + /// + /// Initialises a new instance with the bundled defaults + /// (Hostname = "localhost", Port = 7878, + /// Heartbeat = 10000 ms, + /// ConnectionTimeout = 5000 ms, + /// ReconnectInterval = 10000 ms, + /// TimeZoneOutput = "Z"). YAML / JSON values override + /// the defaults. + /// public ModuleConfiguration() { Hostname = "localhost"; diff --git a/agent/Directory.Build.props b/agent/Directory.Build.props new file mode 100644 index 000000000..4731dffd6 --- /dev/null +++ b/agent/Directory.Build.props @@ -0,0 +1,25 @@ + + + + + + + + true + $(WarningsAsErrors);CS1591 + + + diff --git a/agent/MTConnect.NET-Agent/Program.cs b/agent/MTConnect.NET-Agent/Program.cs index f91de5298..8f9837534 100644 --- a/agent/MTConnect.NET-Agent/Program.cs +++ b/agent/MTConnect.NET-Agent/Program.cs @@ -6,6 +6,14 @@ namespace MTConnect.Applications { + /// + /// Process entry point for the standalone mtconnect.net-agent + /// host. Prints a console header, instantiates an + /// , and runs it in blocking + /// mode. The CLI surface (commands such as run, debug, + /// install, …) is implemented by MTConnectAgentApplication; + /// see docs/reference/cli.md for the full reference. + /// public class Program { // This is the Application Name shown in the Console header information @@ -16,6 +24,14 @@ public class Program // This is just what is shown in the console header. If you want to show support for the MTConnect.NET project, you can reference it using the links in the default header private const string ApplicationCopyright = "Copyright 2025 TrakHound Inc., All Rights Reserved"; + /// + /// Process entry point. Prints the console header, then delegates + /// to + /// in blocking mode so the process stays alive for the lifetime + /// of the agent. + /// + /// Command-line arguments forwarded verbatim + /// to . public static void Main(string[] args) { // Print an application header to the console diff --git a/agent/MTConnect.NET-Applications-Agents/Configurations/AgentConfigurationFileWatcher.cs b/agent/MTConnect.NET-Applications-Agents/Configurations/AgentConfigurationFileWatcher.cs index f249b03cd..f2dad5cd7 100644 --- a/agent/MTConnect.NET-Applications-Agents/Configurations/AgentConfigurationFileWatcher.cs +++ b/agent/MTConnect.NET-Applications-Agents/Configurations/AgentConfigurationFileWatcher.cs @@ -11,9 +11,25 @@ namespace MTConnect.Configurations /// The type of MTConnectAgentConfiguration file to read public class AgentConfigurationFileWatcher : ConfigurationFileWatcher, IAgentConfigurationFileWatcher where TConfiguration : AgentConfiguration { + /// + /// Initialises a new watcher against , + /// polling for changes at + /// milliseconds. + /// + /// Filesystem path to watch. + /// Poll interval in milliseconds. public AgentConfigurationFileWatcher(string path, int interval = DefaultInterval) :base(path, interval) { } + /// + /// Reads the file at as YAML or JSON + /// (selected by file extension) and binds it to + /// . Returns default + /// when the read fails or the extension is unrecognised. + /// + /// Filesystem path of the configuration + /// file. + /// The parsed configuration, or default. protected override AgentConfiguration OnRead(string path) { AgentConfiguration configuration = default; diff --git a/agent/MTConnect.NET-Applications-Agents/IMTConnectAgentApplication.cs b/agent/MTConnect.NET-Applications-Agents/IMTConnectAgentApplication.cs index 3be7cdff4..d432e1b12 100644 --- a/agent/MTConnect.NET-Applications-Agents/IMTConnectAgentApplication.cs +++ b/agent/MTConnect.NET-Applications-Agents/IMTConnectAgentApplication.cs @@ -12,15 +12,36 @@ namespace MTConnect.Applications /// public interface IMTConnectAgentApplication { + /// + /// Windows-service identifier the host registers under (e.g. + /// MTConnect-Agent). Ignored on non-Windows platforms. + /// string ServiceName { get; } + /// + /// Human-readable Windows-service display name, shown in the + /// Services management console. + /// string ServiceDisplayName { get; } + /// + /// Long-form description recorded against the Windows service + /// in the registry. + /// string ServiceDescription { get; } + /// + /// The underlying agent broker the application hosts. Available + /// from the moment StartAgent returns. + /// IMTConnectAgentBroker Agent { get; } + /// + /// Raised when the configuration-file watcher detects a change + /// and the agent is restarting with the freshly-loaded + /// . + /// event EventHandler OnRestart; diff --git a/agent/MTConnect.NET-Applications-Agents/MTConnectAgentApplication.cs b/agent/MTConnect.NET-Applications-Agents/MTConnectAgentApplication.cs index 488c0ab02..3a416fb6c 100644 --- a/agent/MTConnect.NET-Applications-Agents/MTConnectAgentApplication.cs +++ b/agent/MTConnect.NET-Applications-Agents/MTConnectAgentApplication.cs @@ -29,17 +29,32 @@ public class MTConnectAgentApplication : IMTConnectAgentApplication private const string DefaultServiceDisplayName = "MTConnect.NET Agent"; private const string DefaultServiceDescription = "MTConnect Agent to provide access to device information using the MTConnect Standard"; + /// NLog logger for application-level diagnostics + /// (startup, shutdown, configuration load). protected readonly Logger _applicationLogger = LogManager.GetLogger("application-logger"); + /// NLog logger for the agent broker's internal events + /// (device add, observation enqueue). protected readonly Logger _agentLogger = LogManager.GetLogger("agent-logger"); + /// NLog logger for the periodic agent-metrics emitter + /// (observation rate, buffer depth). protected readonly Logger _agentMetricLogger = LogManager.GetLogger("agent-metrics"); + /// NLog logger for input-validation issues + /// (rejected observations, type mismatches). protected readonly Logger _agentValidationLogger = LogManager.GetLogger("agent-validation"); + /// NLog logger shared by every configured agent + /// module. protected readonly Logger _moduleLogger = LogManager.GetLogger("module"); + /// NLog logger shared by every configured agent + /// processor. protected readonly Logger _processorLogger = LogManager.GetLogger("processor"); private readonly List _deviceConfigurationWatchers = new List(); private readonly Dictionary _loggers = new Dictionary(); private readonly object _lock = new object(); + /// NLog log-level applied to every internal logger. + /// Defaults to ; the debug + /// and trace CLI commands override it. protected LogLevel _logLevel = LogLevel.Debug; private MTConnectAgentBroker _mtconnectAgent; private IMTConnectObservationBuffer _observationBuffer; @@ -47,24 +62,44 @@ public class MTConnectAgentApplication : IMTConnectAgentApplication private MTConnectAgentModules _modules; private MTConnectAgentProcessors _processors; private IAgentApplicationConfiguration _initialAgentConfiguration; + /// File-system watcher that reloads the agent + /// configuration when the underlying YAML / JSON file + /// changes. protected IAgentConfigurationFileWatcher _agentConfigurationWatcher; private System.Timers.Timer _metricsTimer; private bool _started = false; + /// When true, the agent emits a console header + /// at startup and includes per-component summaries in the + /// startup log. protected bool _verboseLogging = true; + /// public string ServiceName { get; set; } + /// public string ServiceDisplayName { get; set; } + /// public string ServiceDescription { get; set; } + /// public IMTConnectAgentBroker Agent => _mtconnectAgent; + /// public event EventHandler OnRestart; + /// + /// Initialises a new instance, optionally seeded with an + /// already-loaded . When a + /// configuration is supplied the service-name / display-name / + /// description triple is taken from it; otherwise the bundled + /// MTConnect.NET-Agent defaults apply. + /// + /// Pre-loaded configuration, + /// or null to load from disk during . public MTConnectAgentApplication(IAgentApplicationConfiguration agentConfiguration = null) { if (agentConfiguration != null) @@ -321,8 +356,26 @@ public void Run(string[] args, bool isBlocking = false) } } + /// + /// Extension hook: invoked once the host has finished parsing + /// the command-line arguments. Override in a derived class to + /// inspect or react to the raw arguments. + /// + /// Raw command-line arguments. protected virtual void OnCommandLineArgumentsRead(string[] args) { } + /// + /// Extension hook: loads the agent configuration from + /// . The default + /// implementation delegates to + /// ; override + /// to swap the loader (e.g. to read from an environment- + /// variable backing store). + /// + /// Path to the agent's YAML / + /// JSON configuration file. + /// The loaded configuration, or null when the + /// file could not be read. protected virtual IAgentApplicationConfiguration OnConfigurationFileRead(string configurationPath) { // Read the Configuration File @@ -330,6 +383,16 @@ protected virtual IAgentApplicationConfiguration OnConfigurationFileRead(string } + /// + /// Loads the configuration from + /// (via the hook) and + /// delegates to the in-memory overload. + /// + /// Path to the agent's YAML / + /// JSON configuration file. + /// When true, the agent + /// emits a console header at startup and includes per-component + /// summaries in the startup log. public void StartAgent(string configurationPath, bool verboseLogging = false) { var configuration = OnConfigurationFileRead(configurationPath); @@ -338,6 +401,17 @@ public void StartAgent(string configurationPath, bool verboseLogging = false) StartAgent(configuration, verboseLogging); } + /// + /// Builds the agent broker, loads every device + module + + /// processor described in , and + /// starts the agent. Idempotent — a second call while the agent + /// is running is a no-op. + /// + /// Already-loaded agent + /// configuration. + /// When true, the agent + /// emits a console header at startup and includes per-component + /// summaries in the startup log. public void StartAgent(IAgentApplicationConfiguration configuration, bool verboseLogging = false) { if (!_started && configuration != null) @@ -517,6 +591,12 @@ public void StartAgent(IAgentApplicationConfiguration configuration, bool verbos } } + /// + /// Stops every running component (device watchers, modules, + /// processors, configuration watcher, metrics timer) and + /// disposes the agent broker. Idempotent if the agent never + /// started. + /// public void StopAgent() { if (_started) @@ -545,15 +625,46 @@ public void StopAgent() } + /// + /// Extension hook: fires after the agent broker is created but + /// before devices are added to it. Override to register custom + /// data-items or initialise extension state that the device + /// load relies on. + /// + /// Devices that are about to be added. + /// Whether the agent should + /// seed observations for every data item. protected virtual void OnStartAgentBeforeLoad(IEnumerable devices, bool initializeDataItems = false) { } + /// + /// Extension hook: fires after every device + module + + /// processor has been added to the agent broker. Override to + /// register custom subscribers that depend on the fully-built + /// agent. + /// + /// Devices that have been added. + /// Whether the agent seeded + /// observations for every data item. protected virtual void OnStartAgentAfterLoad(IEnumerable devices, bool initializeDataItems = false) { } + /// + /// Extension hook: fires once has + /// disposed every internal component. Override to release any + /// extension state held by a derived class. + /// protected virtual void OnStopAgent() { } #region "Agent Configuration" + /// + /// Extension hook: creates the file-system watcher that + /// reloads the agent configuration on disk changes. The + /// default implementation wires a + /// against the + /// file path declared in . + /// + /// Currently-active configuration. protected virtual void OnAgentConfigurationWatcherInitialize(IAgentApplicationConfiguration configuration) { _agentConfigurationWatcher = new AgentConfigurationFileWatcher(configuration.Path, configuration.ConfigurationFileRestartInterval * 1000); @@ -576,6 +687,14 @@ private void AgentConfigurationFileUpdated(object sender, AgentConfiguration con } } + /// + /// Extension hook: fires after the configuration watcher + /// reloads the configuration from disk. Override to react to + /// runtime configuration changes (e.g. update derived state in + /// a host application). + /// + /// Freshly-reloaded + /// configuration. protected virtual void OnAgentConfigurationUpdated(AgentConfiguration configuration) { } private void AgentConfigurationFileError(object sender, string message) @@ -688,10 +807,26 @@ private void PrintHelp() OnPrintHelpArguments(); } + /// + /// Extension hook: returns extra text appended to the + /// Usage: line printed by the help command. + /// Override in a host that adds custom commands or arguments. + /// + /// Extra usage text, or an empty string for none. protected virtual string OnPrintHelpUsage() { return ""; } + /// + /// Extension hook: prints extra rows in the Options: + /// section of the help command. The default + /// implementation is empty. + /// protected virtual void OnPrintHelpOptions() { } + /// + /// Extension hook: prints extra rows in the Arguments: + /// section of the help command. The default + /// implementation is empty. + /// protected virtual void OnPrintHelpArguments() { } #endregion diff --git a/agent/MTConnect.NET-Applications-Agents/README.md b/agent/MTConnect.NET-Applications-Agents/README.md new file mode 100644 index 000000000..e723b6001 --- /dev/null +++ b/agent/MTConnect.NET-Applications-Agents/README.md @@ -0,0 +1,137 @@ +![MTConnect.NET Logo](https://raw.githubusercontent.com/TrakHound/MTConnect.NET/master/img/mtconnect-net-03-md.png) + +# MTConnect.NET-Applications-Agents +MTConnect.NET-Applications-Agents contains the base classes and infrastructure needed to build a fully featured MTConnect Agent application, including command-line argument handling, Windows Service support, device and buffer management, configuration file monitoring, and agent module loading. + +## Nuget + + + + + + + + + + + + + + + +
Package NameDownloadsLink
MTConnect.NET-Applications-Agentshttps://www.nuget.org/packages/MTConnect.NET-Applications-Agents
+ +## Overview +This library makes it straightforward to create a production-quality MTConnect Agent application. The central class is `MTConnectAgentApplication`, which handles: + +- **Command-line interface** — `run`, `debug`, `install`, `install-start`, `start`, `stop`, `remove`, and `run-service` commands (the same surface as the standalone MTConnect Agent binary). +- **Windows Service** — installs and runs as a background service on Windows; degrades gracefully on Linux. +- **Agent broker** — creates and manages the internal `MTConnectAgentBroker` that holds the observation and asset buffers. +- **Device management** — loads device model files from the configured path (a single file or a directory of per-device files) and registers a file-system watcher for live reloads. +- **Configuration management** — reads `agent.config.yaml` on startup; optional file-system monitoring restarts the agent automatically when the configuration file changes. +- **Module loading** — discovers and starts all configured agent modules (HTTP server, MQTT relay/broker, SHDR adapter, MQTT adapter, HTTP adapter, etc.). +- **Processor loading** — discovers and starts all configured agent processors (e.g., Python script transformation). +- **Durable buffers** — optional file-backed observation and asset buffers that survive application restarts. +- **Logging** — structured NLog logging with separate log targets for application, agent, validation, module, and processor output. + +## Usage + +### Minimal application +```csharp +using MTConnect.Applications; + +// Create and run an agent application using the default MTConnectAgentApplication +var app = new MTConnectAgentApplication(); + +// Run (pass args so CLI commands work; true = block until Ctrl+C) +app.Run(args, isBlocking: true); +``` + +### Custom application with extended startup logic +```csharp +using MTConnect.Applications; +using MTConnect.Configurations; + +public class MyAgentApplication : MTConnectAgentApplication +{ + protected override void OnAgentStarted(IAgentApplicationConfiguration configuration) + { + // Custom initialization after the agent broker and modules are running + _applicationLogger.Info("Custom agent started successfully."); + } +} +``` + +## Configuration +The agent reads `agent.config.yaml` from its working directory. The default configuration is shown below: + +```yaml +# - Modules - +modules: + +- http-server: # - Add HTTP Server module + port: 5000 + indentOutput: true + documentFormat: xml + accept: + text/xml: xml + application/json: json + responseCompression: + - gzip + - br + +# The maximum number of Observations the agent can hold in its buffer +observationBufferSize: 150000 + +# The maximum number of assets the agent can hold in its buffer +assetBufferSize: 1000 + +# Sets whether the Agent buffers are durable and retain state after restart +durable: false + +# Sets the default MTConnect version to output response documents for. +defaultVersion: 2.2 +``` + +Key configuration properties: + +* `devices` - Path to the Device Information Model file(s) to load. May be a single file or a directory. Defaults to a `devices` subdirectory. +* `observationBufferSize` - Maximum number of observations the agent holds in its ring buffer. +* `assetBufferSize` - Maximum number of assets held in the asset buffer. +* `durable` - When `true`, buffers are written to disk and survive application restarts. +* `defaultVersion` - The MTConnect version used for response documents when the client does not specify one. +* `monitorConfigurationFiles` - When `true`, configuration file changes trigger an automatic agent restart. +* `modules` - List of agent module configurations. +* `processors` - List of agent processor configurations. +* `serviceName` - Windows Service name used when installing or removing the service. +* `serviceAutoStart` - When `true`, the Windows Service starts automatically at boot. + +## Agent Modules +Each entry in the `modules` list activates an agent module. The bundled modules are: + +- [MTConnect.NET-AgentModule-HttpServer](../Modules/MTConnect.NET-AgentModule-HttpServer/) — MTConnect REST HTTP server +- [MTConnect.NET-AgentModule-MqttRelay](../Modules/MTConnect.NET-AgentModule-MqttRelay/) — MQTT relay to an external broker +- [MTConnect.NET-AgentModule-MqttBroker](../Modules/MTConnect.NET-AgentModule-MqttBroker/) — embedded MQTT broker +- [MTConnect.NET-AgentModule-ShdrAdapter](../Modules/MTConnect.NET-AgentModule-ShdrAdapter/) — SHDR adapter input +- [MTConnect.NET-AgentModule-MqttAdapter](../Modules/MTConnect.NET-AgentModule-MqttAdapter/) — MQTT adapter input +- [MTConnect.NET-AgentModule-HttpAdapter](../Modules/MTConnect.NET-AgentModule-HttpAdapter/) — HTTP adapter input + +## Logging +Logging uses [NLog](https://github.com/NLog/NLog). The default configuration file creates separate log files for: +- **(application-logger)** — application startup, shutdown, and configuration load +- **(agent-logger)** — agent broker events (device add, observation enqueue) +- **(agent-validation-logger)** — input validation errors and type mismatches +- **(module-logger)** — per-module events +- **(processor-logger)** — per-processor events + +## Related Libraries +- [MTConnect.NET-Common](../../libraries/MTConnect.NET-Common/) — Core MTConnect entity model +- [MTConnect.NET-Applications-Adapter](../../adapter/MTConnect.NET-Applications-Adapter/) — Symmetrical host library for MTConnect Adapter applications + +## Contribution / Feedback +- Please use the [Issues](https://github.com/TrakHound/MTConnect.NET/issues) tab to create issues for specific problems that you may encounter +- Please feel free to use the [Pull Requests](https://github.com/TrakHound/MTConnect.NET/pulls) tab for any suggested improvements to the source code +- For any other questions or feedback, please contact TrakHound directly at **info@trakhound.com**. + +## License +This library and its source code is licensed under the [MIT License](https://choosealicense.com/licenses/mit/) and is free to use and distribute. diff --git a/agent/MTConnect.NET-Applications-Agents/Service.cs b/agent/MTConnect.NET-Applications-Agents/Service.cs index 45ce99d39..99caaa312 100644 --- a/agent/MTConnect.NET-Applications-Agents/Service.cs +++ b/agent/MTConnect.NET-Applications-Agents/Service.cs @@ -15,34 +15,72 @@ public class Service : MTConnectAgentService private readonly IMTConnectAgentApplication _application; + /// + /// Initialises a new Windows-service wrapper that delegates + /// every Start / Stop action to the supplied + /// agent application. + /// + /// Agent application the service + /// hosts. + /// Windows-service identifier. + /// Human-readable display name. + /// Service description. + /// Whether the service should be set + /// to start automatically on boot. public Service(IMTConnectAgentApplication application, string name = null, string displayName = null, string description = null, bool autoStart = true) - : base(name, displayName, description, autoStart) + : base(name, displayName, description, autoStart) { _application = application; } + /// + /// Service-control hook: delegates to + /// with the + /// supplied configuration path. + /// + /// Path to the agent's + /// configuration file. protected override void StartAgent(string configurationPath) { _application.StartAgent(configurationPath); } + /// + /// Service-control hook: delegates to + /// . + /// protected override void StopAgent() { _application.StopAgent(); } + /// + /// Routes informational service messages to the + /// service-logger NLog target. + /// + /// Message to log. protected override void OnLogInformation(string message) { _serviceLogger.Info(message); } + /// + /// Routes warning service messages to the + /// service-logger NLog target. + /// + /// Message to log. protected override void OnLogWarning(string message) { _serviceLogger.Warn(message); } + /// + /// Routes error service messages to the service-logger + /// NLog target. + /// + /// Message to log. protected override void OnLogError(string message) { _serviceLogger.Error(message); diff --git a/agent/Modules/MTConnect.NET-AgentModule-HttpAdapter/DeviceMappingConfiguration.cs b/agent/Modules/MTConnect.NET-AgentModule-HttpAdapter/DeviceMappingConfiguration.cs index a8292fe36..1cd7cd890 100644 --- a/agent/Modules/MTConnect.NET-AgentModule-HttpAdapter/DeviceMappingConfiguration.cs +++ b/agent/Modules/MTConnect.NET-AgentModule-HttpAdapter/DeviceMappingConfiguration.cs @@ -3,12 +3,32 @@ namespace MTConnect { + /// + /// Maps an upstream device (identified by name, UUID, or id) onto + /// the local agent's device catalog. Bound from the + /// deviceMappings section of the HTTP-adapter module's + /// configuration. + /// public class DeviceMappingConfiguration { + /// + /// Upstream device name to match against. When set, observations + /// whose source device carries this name are routed to the + /// matching local device. + /// public string Name { get; set; } + /// + /// Upstream device UUID to match against. Preferred over + /// when both are set because UUIDs are stable + /// across rename operations. + /// public string Uuid { get; set; } + /// + /// Upstream device id to match against. Falls back to + /// / matching when not set. + /// public string Id { get; set; } } } diff --git a/agent/Modules/MTConnect.NET-AgentModule-HttpAdapter/HttpAdapterModuleConfiguration.cs b/agent/Modules/MTConnect.NET-AgentModule-HttpAdapter/HttpAdapterModuleConfiguration.cs index b5152a086..511711c12 100644 --- a/agent/Modules/MTConnect.NET-AgentModule-HttpAdapter/HttpAdapterModuleConfiguration.cs +++ b/agent/Modules/MTConnect.NET-AgentModule-HttpAdapter/HttpAdapterModuleConfiguration.cs @@ -5,8 +5,21 @@ namespace MTConnect.Configurations { + /// + /// Configuration shape for the HTTP-adapter agent module. Inherits + /// every HTTP client setting (URL, timeout, TLS, …) from + /// and adds the + /// mapping table that routes upstream-agent + /// devices onto the local agent's device catalogue. + /// public class HttpAdapterModuleConfiguration : HttpClientConfiguration { + /// + /// Per-device mapping table: keyed by the local device key, each + /// entry pins an upstream device by name / UUID / id so the + /// adapter knows which source observations belong to which local + /// device. + /// public Dictionary Devices { get; set; } } } \ No newline at end of file diff --git a/agent/Modules/MTConnect.NET-AgentModule-HttpAdapter/Module.cs b/agent/Modules/MTConnect.NET-AgentModule-HttpAdapter/Module.cs index 0d14c7fd5..73d01ffd3 100644 --- a/agent/Modules/MTConnect.NET-AgentModule-HttpAdapter/Module.cs +++ b/agent/Modules/MTConnect.NET-AgentModule-HttpAdapter/Module.cs @@ -15,8 +15,19 @@ namespace MTConnect.Modules { + /// + /// Agent module that pulls observations + assets from one or more + /// upstream MTConnect agents over HTTP and routes them into the + /// local agent. Each configured device mapping spawns a dedicated + /// whose probe / current / sample + /// / assets responses are forwarded to the local agent broker. + /// public class Module : MTConnectAgentModule { + /// + /// Token used in agent.config.yaml to bind this module + /// (type: http-adapter). + /// public const string ConfigurationTypeId = "http-adapter"; private const string ModuleId = "HTTP Adapter"; @@ -27,6 +38,17 @@ public class Module : MTConnectAgentModule private System.Timers.Timer _clientInformationTimer; + /// + /// Initialises the module and binds the supplied configuration + /// payload to . The + /// upstream HTTP client connections are *not* opened here — that + /// happens in after the agent's + /// device catalogue is ready. + /// + /// Upstream agent broker the + /// module writes into. + /// Raw configuration payload bound + /// to . public Module(IMTConnectAgentBroker mtconnectAgent, object configuration) : base(mtconnectAgent) { Id = ModuleId; @@ -36,6 +58,13 @@ public Module(IMTConnectAgentBroker mtconnectAgent, object configuration) : base } + /// + /// Module lifecycle hook: opens the configured upstream HTTP + /// client connections and wires their probe / current / sample + /// / assets event streams to the local agent broker. + /// + /// Inherited flag; unused by + /// this module. protected override void OnStartAfterLoad(bool initializeDataItems) { if (_configuration != null && !string.IsNullOrEmpty(_configuration.Address)) @@ -122,6 +151,10 @@ protected override void OnStartAfterLoad(bool initializeDataItems) } } + /// + /// Module lifecycle hook: stops every upstream HTTP client. + /// Idempotent if the module never opened any clients. + /// protected override void OnStop() { if (!_clients.IsNullOrEmpty()) foreach (var client in _clients) client.Stop(); diff --git a/agent/Modules/MTConnect.NET-AgentModule-HttpServer/HttpServerModuleConfiguration.cs b/agent/Modules/MTConnect.NET-AgentModule-HttpServer/HttpServerModuleConfiguration.cs index ad31b0036..bab8517b5 100644 --- a/agent/Modules/MTConnect.NET-AgentModule-HttpServer/HttpServerModuleConfiguration.cs +++ b/agent/Modules/MTConnect.NET-AgentModule-HttpServer/HttpServerModuleConfiguration.cs @@ -5,23 +5,62 @@ namespace MTConnect.Configurations { + /// + /// Configuration shape for the HTTP-server agent module. Inherits + /// the base (host, port, + /// allowed paths, …) and adds per-document namespace and stylesheet + /// settings so the emitted XML / JSON responses can carry custom + /// XSD namespaces or XSL stylesheets. + /// public class HttpServerModuleConfiguration : HttpServerConfiguration { + /// + /// Extra XML namespaces injected into MTConnectDevices + /// responses. + /// public IEnumerable DevicesNamespaces { get; set; } + /// + /// Extra XML namespaces injected into MTConnectStreams + /// (current / sample) responses. + /// public IEnumerable StreamsNamespaces { get; set; } + /// + /// Extra XML namespaces injected into MTConnectAssets + /// responses. + /// public IEnumerable AssetsNamespaces { get; set; } + /// + /// Extra XML namespaces injected into MTConnectError + /// responses. + /// public IEnumerable ErrorNamespaces { get; set; } + /// + /// XSL stylesheet pinned to every MTConnectDevices + /// response. + /// public StyleConfiguration DevicesStyle { get; set; } + /// + /// XSL stylesheet pinned to every MTConnectStreams + /// response. + /// public StyleConfiguration StreamsStyle { get; set; } + /// + /// XSL stylesheet pinned to every MTConnectAssets + /// response. + /// public StyleConfiguration AssetsStyle { get; set; } + /// + /// XSL stylesheet pinned to every MTConnectError + /// response. + /// public StyleConfiguration ErrorStyle { get; set; } } } \ No newline at end of file diff --git a/agent/Modules/MTConnect.NET-AgentModule-HttpServer/MTConnectHttpAgentServer.cs b/agent/Modules/MTConnect.NET-AgentModule-HttpServer/MTConnectHttpAgentServer.cs index 314163e66..fbcf3d701 100644 --- a/agent/Modules/MTConnect.NET-AgentModule-HttpServer/MTConnectHttpAgentServer.cs +++ b/agent/Modules/MTConnect.NET-AgentModule-HttpServer/MTConnectHttpAgentServer.cs @@ -30,6 +30,14 @@ public class MTConnectHttpAgentServer : MTConnectHttpServer private readonly HttpServerModuleConfiguration _moduleConfiguration; + /// + /// Initialises a new instance against the supplied module + /// configuration and agent broker. + /// + /// Module configuration with the + /// XSL stylesheet and XSD-namespace settings. + /// Agent broker the server reads + /// observations + assets from. public MTConnectHttpAgentServer(HttpServerModuleConfiguration configuration, IMTConnectAgentBroker mtconnectAgent) : base(configuration, mtconnectAgent) { _moduleConfiguration = configuration; @@ -41,6 +49,15 @@ public MTConnectHttpAgentServer(HttpServerModuleConfiguration configuration, IMT // base.OnConfigureServer(serverConfig); //} + /// + /// Serves the configured Devices / Streams XSL stylesheets when + /// the request's local path matches the configured location. + /// Returns null for any other static-file request so the + /// default file pipeline runs. + /// + /// Incoming static-file request. + /// The stylesheet contents as a stream, or null + /// when no stylesheet matches. protected override Stream OnProcessStatic(MTConnectStaticFileRequest request) { if (request.LocalPath != null) @@ -70,6 +87,15 @@ protected override Stream OnProcessStatic(MTConnectStaticFileRequest request) return null; } + /// + /// Builds the per-request format-options bag passed to the + /// document formatter. For XML responses the bag carries the + /// XSD schema text, the configured XML namespaces, and the + /// stylesheet location / path key-value pairs. + /// + /// Pre-formatting metadata (request type, + /// document format, MTConnect version, validation level). + /// List of format-option key-value pairs. protected override List> OnCreateFormatOptions(MTConnectFormatOptionsArgs args) { var x = new List>(); diff --git a/agent/Modules/MTConnect.NET-AgentModule-HttpServer/MTConnectShdrHttpAgentServer.cs b/agent/Modules/MTConnect.NET-AgentModule-HttpServer/MTConnectShdrHttpAgentServer.cs index 2c857712f..9143fe45c 100644 --- a/agent/Modules/MTConnect.NET-AgentModule-HttpServer/MTConnectShdrHttpAgentServer.cs +++ b/agent/Modules/MTConnect.NET-AgentModule-HttpServer/MTConnectShdrHttpAgentServer.cs @@ -20,9 +20,26 @@ namespace MTConnect.Modules.Http /// public class MTConnectShdrHttpAgentServer : MTConnectHttpAgentServer { + /// + /// Initialises a new instance against the supplied module + /// configuration and agent broker. + /// + /// Module configuration. + /// Agent broker the server feeds. public MTConnectShdrHttpAgentServer(HttpServerModuleConfiguration configuration, IMTConnectAgentBroker mtconnectAgent) : base(configuration, mtconnectAgent) { } + /// + /// Translates an HTTP-PUT / -POST observation input into an + /// SHDR-shaped / + /// / + /// and forwards it to the agent broker. Returns true + /// when the input was accepted, false when the device or + /// data item could not be resolved. + /// + /// Inbound observation: device key, + /// data-item key, value, and timestamp. + /// true if the observation was enqueued. protected override bool OnObservationInput(MTConnectObservationInputArgs args) { // Get the Devices Document from the Agent @@ -93,6 +110,16 @@ protected override bool OnObservationInput(MTConnectObservationInputArgs args) return false; } + /// + /// Deserialises an HTTP-POST asset payload via + /// and forwards it to + /// the agent broker. Returns true when the asset was + /// parsed and enqueued, false when the payload was + /// malformed or the device could not be resolved. + /// + /// Inbound asset: device key, asset type, + /// asset id, document format, and the raw request body. + /// true if the asset was enqueued. protected override bool OnAssetInput(MTConnectAssetInputArgs args) { if (!string.IsNullOrEmpty(args.DeviceKey) && !string.IsNullOrEmpty(args.AssetType)) diff --git a/agent/Modules/MTConnect.NET-AgentModule-HttpServer/Module.cs b/agent/Modules/MTConnect.NET-AgentModule-HttpServer/Module.cs index a22eddd65..7d0795708 100644 --- a/agent/Modules/MTConnect.NET-AgentModule-HttpServer/Module.cs +++ b/agent/Modules/MTConnect.NET-AgentModule-HttpServer/Module.cs @@ -13,8 +13,19 @@ namespace MTConnect.Modules.Http { + /// + /// Agent module that hosts the Ceen-based HTTP server. Exposes the + /// standard MTConnect request types (/probe, /current, + /// /sample, /assets, /asset/{id}, and the per- + /// device variants) plus the configured XSL stylesheets and XSD + /// namespaces. + /// public class Module : MTConnectAgentModule { + /// + /// Token used in agent.config.yaml to bind this module + /// (type: http-server). + /// public const string ConfigurationTypeId = "http-server"; private const string ModuleId = "HTTP Server"; private const string HttpServerLogId = "HTTP-Server"; @@ -24,6 +35,16 @@ public class Module : MTConnectAgentModule private readonly IMTConnectAgentBroker _mtconnectAgent; private MTConnectHttpServer _httpServer; + /// + /// Initialises the module and binds the supplied controller- + /// configuration payload to . + /// The HTTP server itself is created in + /// . + /// + /// Agent broker the HTTP server + /// reads from. + /// Raw configuration + /// payload bound to . public Module(IMTConnectAgentBroker mtconnectAgent, object controllerConfiguration) : base(mtconnectAgent) { Id = ModuleId; @@ -33,6 +54,14 @@ public Module(IMTConnectAgentBroker mtconnectAgent, object controllerConfigurati } + /// + /// Module lifecycle hook: creates the bundled + /// , wires its + /// connection / response / error events to the module logger, + /// and starts listening. + /// + /// Inherited flag; unused by + /// this module. protected override void OnStartAfterLoad(bool initializeDataItems) { // Intialize the Http Server @@ -53,6 +82,11 @@ protected override void OnStartAfterLoad(bool initializeDataItems) _httpServer.Start(); } + /// + /// Module lifecycle hook: stops the HTTP server and disposes + /// its underlying Ceen host. Idempotent if the server never + /// started. + /// protected override void OnStop() { if (_httpServer != null) diff --git a/agent/Modules/MTConnect.NET-AgentModule-MqttAdapter/Module.cs b/agent/Modules/MTConnect.NET-AgentModule-MqttAdapter/Module.cs index 6806e1ed7..9cb253b0c 100644 --- a/agent/Modules/MTConnect.NET-AgentModule-MqttAdapter/Module.cs +++ b/agent/Modules/MTConnect.NET-AgentModule-MqttAdapter/Module.cs @@ -21,8 +21,19 @@ namespace MTConnect.Modules { + /// + /// Agent module that subscribes to an upstream MQTT broker and + /// converts published observations, assets, and + /// device messages into observations the local agent broker + /// can serve. Pairs with an upstream agent's MQTT-output / MQTT- + /// broker module. + /// public class Module : MTConnectAgentModule { + /// + /// Token used in agent.config.yaml to bind this module + /// (type: mqtt-adapter). + /// public const string ConfigurationTypeId = "mqtt-adapter"; private const string ModuleId = "MQTT Adapter"; private const string ObservationTopic = "observations"; @@ -36,6 +47,14 @@ public class Module : MTConnectAgentModule private CancellationTokenSource _stop; + /// + /// Initialises the module, creates the MQTTnet client, and binds + /// the supplied configuration payload to + /// . + /// + /// Local agent broker the + /// translated observations are written into. + /// Raw configuration payload. public Module(IMTConnectAgentBroker mtconnectAgent, object configuration) : base(mtconnectAgent) { Id = ModuleId; @@ -49,6 +68,12 @@ public Module(IMTConnectAgentBroker mtconnectAgent, object configuration) : base } + /// + /// Module lifecycle hook: spawns the MQTT subscription worker on + /// a background task. Subscriptions are managed by Worker + /// which reconnects on failure. + /// + /// Inherited flag; unused. protected override void OnStartAfterLoad(bool initializeDataItems) { if (_configuration != null) @@ -60,6 +85,10 @@ protected override void OnStartAfterLoad(bool initializeDataItems) } + /// + /// Module lifecycle hook: cancels the subscription worker and + /// disposes the MQTT client. + /// protected override void OnStop() { if (_stop != null) _stop.Cancel(); diff --git a/agent/Modules/MTConnect.NET-AgentModule-MqttAdapter/MqttAdapterModuleConfiguration.cs b/agent/Modules/MTConnect.NET-AgentModule-MqttAdapter/MqttAdapterModuleConfiguration.cs index a116bf6f1..081288405 100644 --- a/agent/Modules/MTConnect.NET-AgentModule-MqttAdapter/MqttAdapterModuleConfiguration.cs +++ b/agent/Modules/MTConnect.NET-AgentModule-MqttAdapter/MqttAdapterModuleConfiguration.cs @@ -3,6 +3,11 @@ namespace MTConnect.Configurations { + /// + /// Configuration shape for the MQTT-adapter agent module. Bound + /// from the mqtt-adapter module section of + /// agent.config.yaml. + /// public class MqttAdapterModuleConfiguration { /// @@ -94,6 +99,15 @@ public class MqttAdapterModuleConfiguration public string DocumentFormat { get; set; } + /// + /// Initialises a new instance with the bundled defaults + /// (Server = "localhost", Port = 1883, + /// Qos = 1, CleanSession = true, + /// Timeout = 5000 ms, + /// ReconnectInterval = 10000 ms, + /// DocumentFormat = "json"). YAML / JSON values bound + /// on top of this instance override the defaults. + /// public MqttAdapterModuleConfiguration() { Server = "localhost"; diff --git a/agent/Modules/MTConnect.NET-AgentModule-MqttBroker/Module.cs b/agent/Modules/MTConnect.NET-AgentModule-MqttBroker/Module.cs index 35bb796f3..e6be8622c 100644 --- a/agent/Modules/MTConnect.NET-AgentModule-MqttBroker/Module.cs +++ b/agent/Modules/MTConnect.NET-AgentModule-MqttBroker/Module.cs @@ -24,8 +24,21 @@ namespace MTConnect.Modules { + /// + /// Agent module that hosts an in-process MQTT broker. Devices, + /// observations, and assets the upstream agent emits are forwarded + /// to subscribed MQTT clients on either a document-shaped topic + /// hierarchy (one full MTConnect response per topic) or an entity- + /// shaped topic hierarchy (one observation / device / asset per + /// topic). The topic structure is selected via + /// . + /// public class Module : MTConnectAgentModule { + /// + /// Token used in agent.config.yaml to bind this module + /// (type: mqtt-broker). + /// public const string ConfigurationTypeId = "mqtt-broker"; private const string ModuleId = "MQTT Broker"; @@ -36,6 +49,16 @@ public class Module : MTConnectAgentModule private CancellationTokenSource _stop; + /// + /// Initialises the module, binds the supplied configuration + /// payload to , and + /// wires the document- or entity-shaped MQTT topic server to + /// the upstream agent's event stream. + /// + /// Upstream agent broker the module + /// reads from. + /// Raw configuration payload bound + /// to at startup. public Module(IMTConnectAgentBroker mtconnectAgent, object configuration) : base(mtconnectAgent) { Id = ModuleId; @@ -65,6 +88,13 @@ public Module(IMTConnectAgentBroker mtconnectAgent, object configuration) : base } + /// + /// Module lifecycle hook: spawns the MQTT broker on a background + /// task and blocks for InitialDelay milliseconds so the + /// broker is ready before the agent starts publishing. + /// + /// Inherited flag; unused by + /// the broker module. protected override void OnStartBeforeLoad(bool initializeDataItems) { _stop = new CancellationTokenSource(); @@ -73,6 +103,10 @@ protected override void OnStartBeforeLoad(bool initializeDataItems) Task.Delay(_configuration.InitialDelay).Wait(); } + /// + /// Module lifecycle hook: gracefully stops the in-process MQTT + /// broker (idempotent if the broker never started). + /// protected override void OnStop() { if (_mqttServer != null) _mqttServer.StopAsync(); diff --git a/agent/Modules/MTConnect.NET-AgentModule-MqttBroker/MqttBrokerModuleConfiguration.cs b/agent/Modules/MTConnect.NET-AgentModule-MqttBroker/MqttBrokerModuleConfiguration.cs index 25b407bab..bf9cd46ee 100644 --- a/agent/Modules/MTConnect.NET-AgentModule-MqttBroker/MqttBrokerModuleConfiguration.cs +++ b/agent/Modules/MTConnect.NET-AgentModule-MqttBroker/MqttBrokerModuleConfiguration.cs @@ -5,6 +5,11 @@ namespace MTConnect.Configurations { + /// + /// Configuration shape for the in-process MQTT broker agent + /// module. Bound from the mqtt-broker module section of + /// agent.config.yaml. + /// public class MqttBrokerModuleConfiguration : IMTConnectMqttDocumentServerConfiguration { /// @@ -77,6 +82,14 @@ public class MqttBrokerModuleConfiguration : IMTConnectMqttDocumentServerConfigu public int SampleInterval { get; set; } + /// + /// Initialises a new instance with the bundled defaults + /// (Port = 1883, InitialDelay = 500 ms, + /// Timeout = 5000 ms, TopicPrefix = "MTConnect", + /// TopicStructure = Document, + /// DocumentFormat = "json-cppagent", …). YAML / JSON + /// values bound on top of this instance override the defaults. + /// public MqttBrokerModuleConfiguration() { Server = null; diff --git a/agent/Modules/MTConnect.NET-AgentModule-MqttBroker/MqttTopicStructure.cs b/agent/Modules/MTConnect.NET-AgentModule-MqttBroker/MqttTopicStructure.cs index b182f887c..d535be8a6 100644 --- a/agent/Modules/MTConnect.NET-AgentModule-MqttBroker/MqttTopicStructure.cs +++ b/agent/Modules/MTConnect.NET-AgentModule-MqttBroker/MqttTopicStructure.cs @@ -3,9 +3,23 @@ namespace MTConnect { + /// + /// MQTT topic layout selector for the broker module. + /// public enum MqttTopicStructure { + /// + /// Document-shaped: one MTConnect response document + /// (probe / current / sample / assets) + /// per topic; mirrors the HTTP request types. + /// Document, + + /// + /// Entity-shaped: one observation / device / asset per topic, + /// with the device UUID and data-item identifier embedded in + /// the topic path. Lower per-message bandwidth but more topics. + /// Entity } } diff --git a/agent/Modules/MTConnect.NET-AgentModule-MqttRelay/Module.cs b/agent/Modules/MTConnect.NET-AgentModule-MqttRelay/Module.cs index 9cbedb141..14a30635a 100644 --- a/agent/Modules/MTConnect.NET-AgentModule-MqttRelay/Module.cs +++ b/agent/Modules/MTConnect.NET-AgentModule-MqttRelay/Module.cs @@ -24,8 +24,21 @@ namespace MTConnect { + /// + /// Agent module that relays observations + assets to a downstream + /// MQTT broker. Unlike the in-process broker module, the relay + /// connects out to an existing broker (configured via + /// ) and publishes to + /// either document-shaped topics or entity-shaped topics. + /// Supports durable last-sent-sequence persistence so a relay can + /// resume from where it left off after a restart. + /// public class Module : MTConnectAgentModule { + /// + /// Token used in agent.config.yaml to bind this module + /// (type: mqtt-relay). + /// public const string ConfigurationTypeId = "mqtt-relay"; private const string ModuleId = "MQTT Relay"; @@ -54,6 +67,16 @@ public class Module : MTConnectAgentModule private const string DirectoryBuffer = "buffer"; private const string LastSentSequenceFileName = "mqttrelay_last_sent.seq"; + /// + /// Initialises the module, binds the supplied configuration + /// payload to , and + /// wires the document- or entity-shaped MQTT topic server to + /// the upstream agent's event stream. + /// + /// Upstream agent broker the relay + /// reads observations + assets from. + /// Raw configuration payload bound + /// to . public Module(IMTConnectAgentBroker mtconnectAgent, object configuration) : base(mtconnectAgent) { Id = ModuleId; @@ -86,6 +109,14 @@ public Module(IMTConnectAgentBroker mtconnectAgent, object configuration) : base } + /// + /// Module lifecycle hook: starts the MQTT relay worker on a + /// background task. When + /// is on, seeds the in-memory persister from disk so the first + /// post-restart batch resumes from the last successfully-relayed + /// sequence. + /// + /// Inherited flag; unused. protected override void OnStartAfterLoad(bool initializeDataItems) { _stop = new CancellationTokenSource(); @@ -110,6 +141,14 @@ protected override void OnStartAfterLoad(bool initializeDataItems) _ = Task.Run(Worker, _stop.Token); } + /// + /// Module lifecycle hook: stops the document- / entity-shaped + /// MQTT servers, cancels the relay worker, drains in-flight + /// observation handlers (up to + /// ), and flushes any pending + /// last-sent-sequence to disk so a restart resumes from the + /// correct point. + /// protected override void OnStop() { // Entity-mode constructs only _entityServer, so a bare diff --git a/agent/Modules/MTConnect.NET-AgentModule-MqttRelay/MqttRelayModuleConfiguration.cs b/agent/Modules/MTConnect.NET-AgentModule-MqttRelay/MqttRelayModuleConfiguration.cs index a1829d5d7..b2d57ab11 100644 --- a/agent/Modules/MTConnect.NET-AgentModule-MqttRelay/MqttRelayModuleConfiguration.cs +++ b/agent/Modules/MTConnect.NET-AgentModule-MqttRelay/MqttRelayModuleConfiguration.cs @@ -5,6 +5,10 @@ namespace MTConnect.Configurations { + /// + /// Configuration shape for the MQTT-relay agent module. Bound from + /// the mqtt-relay module section of agent.config.yaml. + /// public class MqttRelayModuleConfiguration : IMTConnectMqttDocumentServerConfiguration { /// @@ -101,6 +105,18 @@ public class MqttRelayModuleConfiguration : IMTConnectMqttDocumentServerConfigur public bool DurableRelay { get; set; } = false; + /// + /// Initialises a new instance with the bundled defaults + /// (Server = "localhost", Port = 1883, + /// Timeout = 5000 ms, + /// ReconnectInterval = 10000 ms, + /// TopicPrefix = "MTConnect", + /// TopicStructure = Document, + /// DocumentFormat = "json-cppAgent", + /// CurrentInterval = 5000 ms, + /// SampleInterval = 500 ms). YAML / JSON values override + /// the defaults. + /// public MqttRelayModuleConfiguration() { Server = "localhost"; diff --git a/agent/Modules/MTConnect.NET-AgentModule-MqttRelay/MqttTopicStructure.cs b/agent/Modules/MTConnect.NET-AgentModule-MqttRelay/MqttTopicStructure.cs index b182f887c..eea35b882 100644 --- a/agent/Modules/MTConnect.NET-AgentModule-MqttRelay/MqttTopicStructure.cs +++ b/agent/Modules/MTConnect.NET-AgentModule-MqttRelay/MqttTopicStructure.cs @@ -3,9 +3,23 @@ namespace MTConnect { + /// + /// MQTT topic layout selector for the relay module. + /// public enum MqttTopicStructure { + /// + /// Document-shaped: one MTConnect response document + /// (probe / current / sample / assets) + /// per topic; mirrors the HTTP request types. + /// Document, + + /// + /// Entity-shaped: one observation / device / asset per topic, + /// with the device UUID and data-item identifier embedded in + /// the topic path. Lower per-message bandwidth but more topics. + /// Entity } } diff --git a/agent/Modules/MTConnect.NET-AgentModule-ShdrAdapter/Module.cs b/agent/Modules/MTConnect.NET-AgentModule-ShdrAdapter/Module.cs index 12ba3e563..6d62ab127 100644 --- a/agent/Modules/MTConnect.NET-AgentModule-ShdrAdapter/Module.cs +++ b/agent/Modules/MTConnect.NET-AgentModule-ShdrAdapter/Module.cs @@ -15,8 +15,20 @@ namespace MTConnect.Modules { + /// + /// Agent module that opens one or more SHDR-protocol TCP client + /// connections to upstream adapters. Each configured device (or + /// every device when DeviceKey is a wildcard) gets a + /// dedicated whose protocol / + /// connect / disconnect events are mirrored to the local agent + /// broker. + /// public class Module : MTConnectAgentModule { + /// + /// Token used in agent.config.yaml to bind this module + /// (type: shdr-adapter). + /// public const string ConfigurationTypeId = "shdr-adapter"; private const string ModuleId = "SHDR Adapter"; @@ -25,6 +37,15 @@ public class Module : MTConnectAgentModule private readonly List _adapters = new List(); + /// + /// Initialises the module and binds the supplied configuration + /// payload to . + /// The SHDR client connections are opened in + /// . + /// + /// Agent broker the SHDR clients + /// feed observations into. + /// Raw configuration payload. public Module(IMTConnectAgentBroker mtconnectAgent, object configuration) : base(mtconnectAgent) { Id = ModuleId; @@ -34,6 +55,16 @@ public Module(IMTConnectAgentBroker mtconnectAgent, object configuration) : base } + /// + /// Module lifecycle hook: opens an + /// per configured device (or + /// per discovered device when DeviceKey is a wildcard, + /// or a single generic client when + /// + /// is on and no devices are configured). + /// + /// Forwarded to each adapter + /// client; controls whether data items are seeded at start. protected override void OnStartAfterLoad(bool initializeDataItems) { if (_configuration != null) @@ -62,6 +93,11 @@ protected override void OnStartAfterLoad(bool initializeDataItems) } } + /// + /// Module lifecycle hook: detaches every event handler from + /// each adapter client, stops the clients, and clears the + /// adapter list. Idempotent if no clients were created. + /// protected override void OnStop() { // Stop Adapter Clients diff --git a/agent/Modules/MTConnect.NET-AgentModule-ShdrAdapter/ShdrAdapterModuleConfiguration.cs b/agent/Modules/MTConnect.NET-AgentModule-ShdrAdapter/ShdrAdapterModuleConfiguration.cs index 5b1fd6278..a10d249d6 100644 --- a/agent/Modules/MTConnect.NET-AgentModule-ShdrAdapter/ShdrAdapterModuleConfiguration.cs +++ b/agent/Modules/MTConnect.NET-AgentModule-ShdrAdapter/ShdrAdapterModuleConfiguration.cs @@ -3,6 +3,14 @@ namespace MTConnect.Configurations { + /// + /// Configuration shape for the SHDR-adapter agent module. Extends + /// the base (host, + /// port, connect-timeout, heartbeat, …) with the + /// opt-in that lets an SHDR adapter + /// transmit its own device model rather than relying on a pre- + /// configured one. + /// public class ShdrAdapterModuleConfiguration : ShdrAdapterClientConfiguration { /// @@ -11,6 +19,11 @@ public class ShdrAdapterModuleConfiguration : ShdrAdapterClientConfiguration public bool AllowShdrDevice { get; set; } + /// + /// Initialises a new instance with + /// set to false (the safe default — a generic adapter + /// client is not auto-created unless this is opted in). + /// public ShdrAdapterModuleConfiguration() { AllowShdrDevice = false; diff --git a/agent/Processors/MTConnect.NET-AgentProcessor-Python/Processor.cs b/agent/Processors/MTConnect.NET-AgentProcessor-Python/Processor.cs index 8eac4578a..564ad08a9 100644 --- a/agent/Processors/MTConnect.NET-AgentProcessor-Python/Processor.cs +++ b/agent/Processors/MTConnect.NET-AgentProcessor-Python/Processor.cs @@ -10,8 +10,22 @@ namespace MTConnect.Processors { + /// + /// Agent processor that pipes each inbound observation through every + /// Python script in a configured directory. Each *.py file must + /// declare a top-level process(observation) function that + /// returns a (possibly modified) ProcessObservation. Scripts + /// are evaluated by the IronPython engine; the directory is watched + /// with a so add / change / remove + /// events trigger a debounced reload. + /// public class Processor : MTConnectAgentProcessor { + /// + /// Token used in agent.config.yaml to bind this processor + /// (type: python). The agent host matches this value + /// against the configuration discriminator at startup. + /// public const string ConfigurationTypeId = "python"; private const string ProcessorId = "Python Scripts"; private const int DefaultUpdateInterval = 2000; @@ -30,7 +44,16 @@ public class Processor : MTConnectAgentProcessor private bool _update = false; - public Processor(object configuration) + /// + /// Initialises the processor, binds the supplied configuration + /// payload to , creates the + /// IronPython engine, and starts the script-directory watcher. + /// + /// Raw configuration object the + /// agent host passes through; bound to + /// via the standard agent + /// configuration helper. + public Processor(object configuration) { Id = ProcessorId; @@ -42,6 +65,13 @@ public Processor(object configuration) } + /// + /// Rescans the configured script directory and (re)loads every + /// *.py file. Existing functions are cleared first so a + /// removed script no longer participates in + /// . Safe to call from the file-system + /// watcher's debounced timer. + /// public override void Load() { lock (_lock) _functions.Clear(); @@ -85,6 +115,19 @@ private void LoadEngine(string file) } + /// + /// Pipes the supplied observation through every loaded Python + /// process function in registration order. Each function + /// receives the *current* observation (with prior functions' + /// changes applied) and returns either a transformed observation + /// or null to drop it. Exceptions inside a function are + /// logged and the original observation continues down the chain. + /// + /// Observation produced by the agent + /// pipeline immediately upstream of this processor. + /// The observation flattened into an + /// ready to enqueue, or + /// null when every function dropped the observation. protected override IObservationInput OnProcess(ProcessObservation observation) { ProcessObservation outputObservation = observation; diff --git a/agent/Processors/MTConnect.NET-AgentProcessor-Python/ProcessorConfiguration.cs b/agent/Processors/MTConnect.NET-AgentProcessor-Python/ProcessorConfiguration.cs index ea77bdc89..669ab6f22 100644 --- a/agent/Processors/MTConnect.NET-AgentProcessor-Python/ProcessorConfiguration.cs +++ b/agent/Processors/MTConnect.NET-AgentProcessor-Python/ProcessorConfiguration.cs @@ -5,8 +5,18 @@ namespace MTConnect.Processors { + /// + /// Configuration shape for the Python agent processor. Bound from + /// the processors.python section of agent.config.yaml + /// and consumed by . + /// public class ProcessorConfiguration { + /// + /// Filesystem directory containing the Python scripts the + /// processor should execute. Each *.py file in the + /// directory is loaded at startup. + /// [JsonPropertyName("directory")] public string Directory { get; set; } } diff --git a/agent/README.md b/agent/README.md index b27612628..439092bd6 100644 --- a/agent/README.md +++ b/agent/README.md @@ -1,5 +1,7 @@ # Standalone MTConnect Agent +For the full agent CLI reference, configuration guide, and module catalogue, see the docs site under [`docs/cli/agent`](../docs/cli/agent.md), [`docs/configure/agent-config`](../docs/configure/agent-config.md), and [`docs/modules/`](../docs/modules/). + diff --git a/build/Directory.Build.props b/build/Directory.Build.props new file mode 100644 index 000000000..38725049f --- /dev/null +++ b/build/Directory.Build.props @@ -0,0 +1,25 @@ + + + + + + + + true + $(WarningsAsErrors);CS1591 + + + diff --git a/build/MTConnect.NET-DocsGen/CliInventory.cs b/build/MTConnect.NET-DocsGen/CliInventory.cs new file mode 100644 index 000000000..5422fb4fe --- /dev/null +++ b/build/MTConnect.NET-DocsGen/CliInventory.cs @@ -0,0 +1,453 @@ +// Copyright (c) 2026 TrakHound Inc., All Rights Reserved. +// TrakHound Inc. licenses this file to you under the MIT license. + +using Microsoft.CodeAnalysis; +using Microsoft.CodeAnalysis.CSharp; +using Microsoft.CodeAnalysis.CSharp.Syntax; +using System.Text.RegularExpressions; + +namespace MTConnect.NET_DocsGen; + +/// +/// Describes a single command-line tool the repository exposes. The +/// taxonomy is intentionally narrow: +/// +/// - "shipped" CLIs ship as released binaries — the standalone +/// MTConnect-Agent + MTConnect-Adapter hosts. +/// - "contributor" CLIs live under tools/ and the +/// build/ tree — every contributor uses them but they are +/// never released. +/// +public sealed record CliInfo( + string Name, // e.g. "mtconnect.net-agent" + string Category, // "shipped" | "contributor" + string Summary, // single-paragraph description + string SourceRelativePath, // canonical source file + IReadOnlyList Commands, + IReadOnlyList Flags, + IReadOnlyList Arguments); + +/// +/// A single sub-command keyword the CLI dispatches on, e.g. +/// run / debug / install. +/// +public sealed record CliCommand(string Name, string Description); + +/// +/// A single CLI flag, with its short alias if any, accepted argument +/// shape, and human-facing description. The description is normally +/// pulled out of the script's docstring or the C# program's printed +/// help text. +/// +public sealed record CliFlag( + string Name, // e.g. "--docker" + string? Short, // e.g. "-d", null if none + string? ArgShape, // e.g. "PATTERN", null if a switch + string Description); + +/// +/// A single positional argument. +/// +public sealed record CliArg(string Name, string Description); + +/// +/// Builds the full CLI inventory. Each tool has a dedicated collector +/// because the help-text shape differs between the C# entry points +/// and the bash / PowerShell wrappers; the collectors agree only on +/// the output record. +/// +public static class CliInventory +{ + /// + /// Walks the shipped agent + adapter entry points, every + /// tools/*.sh wrapper, and the build-tree .NET tools under + /// , returning a deduplicated CLI + /// inventory. Output is ordered with shipped CLIs first, then + /// contributor CLIs alphabetically. + /// + /// Repository root. + /// Ordered list of CLI tools. + public static IReadOnlyList Collect(string repoRoot) + { + var results = new List(); + + // ---- Shipped: agent + adapter ------------------------------------- + var agentApp = Path.Combine(repoRoot, "agent", "MTConnect.NET-Applications-Agents", "MTConnectAgentApplication.cs"); + if (File.Exists(agentApp)) + { + results.Add(CollectAgentLike( + name: "mtconnect.net-agent", + file: agentApp, + repoRoot: repoRoot, + summary: "Standalone HTTP agent host. Loads `agent.config.yaml` (or `agent.config.json`), builds an `MTConnectAgentBroker`, instantiates every configured agent module, and runs them inside a single process. The CLI surface is defined by `MTConnectAgentApplication.Run(args)`.", + argument: new CliArg("configuration_file", "Path to the agent configuration file. Absolute or relative to the executable's directory. If omitted, the agent looks for `agent.config.json`, then `agent.config.yaml`, and copies `agent.config.default.yaml` into place if neither exists."))); + } + + var adapterApp = Path.Combine(repoRoot, "adapter", "MTConnect.NET-Applications-Adapter", "MTConnectAdapterApplication.cs"); + if (File.Exists(adapterApp)) + { + results.Add(CollectAgentLike( + name: "mtconnect.net-adapter", + file: adapterApp, + repoRoot: repoRoot, + summary: "Standalone adapter host. Pumps observations from a data source (SHDR socket, MQTT topic, or a custom `DataSource` implementation) into a downstream agent. Reads `adapter.config.yaml` at startup. The CLI surface is defined by `MTConnectAdapterApplication.Run(args)`.", + argument: new CliArg("configuration_file", "Path to the adapter configuration file. Defaults to `adapter.config.yaml` next to the executable when omitted."))); + } + + // ---- Contributor: tools/*.sh + tools/*.ps1 (paired) --------------- + var toolsDir = Path.Combine(repoRoot, "tools"); + if (Directory.Exists(toolsDir)) + { + foreach (var sh in Directory.EnumerateFiles(toolsDir, "*.sh", SearchOption.TopDirectoryOnly) + .OrderBy(p => p, StringComparer.Ordinal)) + { + var info = CollectShellCli(sh, repoRoot); + if (info is not null) results.Add(info); + } + } + + // ---- Contributor: SysML-Import + DocsGen -------------------------- + var sysmlMain = Path.Combine(repoRoot, "build", "MTConnect.NET-SysML-Import", "Program.cs"); + if (File.Exists(sysmlMain)) + { + results.Add(CollectDotNetTool( + name: "MTConnect.NET-SysML-Import", + file: sysmlMain, + repoRoot: repoRoot, + summary: "Parses an `MTConnectSysMLModel.xml` (the XMI export of the standard's SysML model) and regenerates the `*.g.cs` source files under `libraries/MTConnect.NET-Common/`, `libraries/MTConnect.NET-XML/`, and `libraries/MTConnect.NET-JSON-cppagent/`. Run by maintainers when a new spec version lands.")); + } + + var docsGenMain = Path.Combine(repoRoot, "build", "MTConnect.NET-DocsGen", "Program.cs"); + if (File.Exists(docsGenMain)) + { + results.Add(CollectDotNetTool( + name: "MTConnect.NET-DocsGen", + file: docsGenMain, + repoRoot: repoRoot, + summary: "Walks the repository source tree with Roslyn and emits the auto-generated VitePress reference pages under `docs/reference/`. The same inventory routines are exposed as public static methods so the validation test can re-run them independently.")); + } + + return results + .OrderBy(c => c.Category == "shipped" ? 0 : 1) + .ThenBy(c => c.Name, StringComparer.Ordinal) + .ToList(); + } + + // ----- agent + adapter -------------------------------------------------- + + // Matches the `Console.WriteLine(string.Format("{0,...} | {1,...}", "name", "desc"))` + // pattern in the C# PrintHelp methods. + private static readonly Regex AgentHelpRowRe = new( + @"Console\.WriteLine\([^""]*""\{0,\d+\}\s*\|\s*\{1,\d+\}""\s*,\s*""(?[^""]+)""\s*,\s*""(?[^""]+)""", + RegexOptions.Compiled); + + private static CliInfo CollectAgentLike(string name, string file, string repoRoot, string summary, CliArg argument) + { + var text = File.ReadAllText(file); + var commands = new List(); + var seen = new HashSet(StringComparer.Ordinal); + foreach (Match m in AgentHelpRowRe.Matches(text)) + { + var cmd = m.Groups["name"].Value; + var desc = m.Groups["desc"].Value; + // Defensive guards: + // - PrintHelp blocks include a single header row + // ("Command | Description"). Skip it. + // - The same PrintHelp emits the positional-argument row + // ("configuration_file") in the same table format. That + // belongs in Arguments, not Commands, and the caller already + // supplies a richer description for it. + // - Some entry points are invoked twice (Windows vs. Linux + // branches). Dedupe by command name. + if (cmd.Equals("Command", StringComparison.OrdinalIgnoreCase)) continue; + if (cmd.Equals(argument.Name, StringComparison.OrdinalIgnoreCase)) continue; + if (!seen.Add(cmd)) continue; + commands.Add(new CliCommand(cmd, desc)); + } + + return new CliInfo( + Name: name, + Category: "shipped", + Summary: summary, + SourceRelativePath: Path.GetRelativePath(repoRoot, file).Replace('\\', '/'), + Commands: commands, + Flags: Array.Empty(), + Arguments: new[] { argument }); + } + + // ----- tools/*.sh ------------------------------------------------------- + + // Matches a typical bash help block "Flags:" entry of the form: + // -d, --docker Description that may wrap across + // multiple lines until the next flag or + // a blank line. + // The two-flag form (`-d, --docker`) and the single-flag form + // (`--docker`) are both accepted; an optional argument shape + // (`PATTERN`, ``, `[file]`) is captured. The leading-whitespace + // bound is capped at 6 characters so deeply-indented continuation + // lines like ` --docker (also honored …)` are + // not parsed as new flag entries — they fall through to the + // description-continuation branch below. + private static readonly Regex ShellHelpFlagRe = new( + @"^(?\s{1,6})(?:(?-[a-zA-Z]),\s+)?(?--[a-zA-Z][a-zA-Z0-9-]+)(?:\s+(?[A-Z][A-Z0-9_<>\[\]]*))?\s+(?\S.*)$", + RegexOptions.Compiled); + + private static CliInfo? CollectShellCli(string file, string repoRoot) + { + var lines = File.ReadAllLines(file); + var rel = Path.GetRelativePath(repoRoot, file).Replace('\\', '/'); + var name = Path.GetFileName(file); + + // Pull the leading docstring (the first block of `#` lines after + // the shebang) as the summary. + var summary = ExtractShellSummary(lines); + + // Walk the file for the help-block "Flags:" section. Only the + // FIRST "Flags:" block is consumed — typical scripts repeat the + // same content in both their docstring (leading `#` block) and + // their print_help heredoc, and we only want one row per flag. + var flags = new List(); + bool inFlags = false; + bool flagsBlockDone = false; + CliFlag? pending = null; + var descBuf = new System.Text.StringBuilder(); + + void Flush() + { + if (pending is null) return; + var desc = descBuf.ToString().Trim(); + flags.Add(pending with { Description = desc }); + pending = null; + descBuf.Clear(); + } + + for (int i = 0; i < lines.Length; i++) + { + var line = lines[i]; + var trimmed = line.TrimEnd(); + + // Enter the "Flags:" block — but only once. After the first + // block closes, the second occurrence (in print_help) is + // ignored so the row set isn't duplicated. + if (Regex.IsMatch(trimmed, @"^\s*#?\s*Flags:\s*$")) + { + if (flagsBlockDone) continue; + inFlags = true; + continue; + } + if (!inFlags) continue; + + // Exit when we hit a blank line, a `set -` line, or the + // closing heredoc delimiter. + if (trimmed.Length == 0 + || Regex.IsMatch(trimmed, @"^\s*[A-Z]+$") // EOF / HEREDOC delim + || Regex.IsMatch(trimmed, @"^\s*set\s+-") + || Regex.IsMatch(trimmed, @"^\s*#?\s*[A-Z][A-Za-z\s]+:\s*$")) // next "Usage:" / etc. + { + Flush(); + inFlags = false; + flagsBlockDone = true; + continue; + } + + // Strip a leading `#` (for files where the help block lives + // in the doc-comment block, not the heredoc). + var content = line.StartsWith('#') ? line.Substring(1) : line; + + var m = ShellHelpFlagRe.Match(content); + if (m.Success) + { + Flush(); + pending = new CliFlag( + Name: m.Groups["long"].Value, + Short: m.Groups["shrt"].Success ? m.Groups["shrt"].Value : null, + ArgShape: m.Groups["arg"].Success ? m.Groups["arg"].Value : null, + Description: string.Empty); + descBuf.Clear(); + descBuf.Append(m.Groups["desc"].Value); + } + else if (pending is not null) + { + // Continuation line: append after a space. + descBuf.Append(' ').Append(content.Trim()); + } + } + Flush(); + + // Skip scripts with no flags at all — they are tiny shell wrappers + // that the cli/ reference doesn't need to enumerate. + if (flags.Count == 0) return null; + + return new CliInfo( + Name: name, + Category: "contributor", + Summary: summary, + SourceRelativePath: rel, + Commands: Array.Empty(), + Flags: flags, + Arguments: Array.Empty()); + } + + private static string ExtractShellSummary(string[] lines) + { + // Skip the shebang, then take consecutive `#` lines as prose + // until either a blank line or a non-`#` line. The result is a + // single space-joined paragraph trimmed to 320 chars max. + var sb = new System.Text.StringBuilder(); + int start = 0; + if (lines.Length > 0 && lines[0].StartsWith("#!", StringComparison.Ordinal)) start = 1; + for (int i = start; i < lines.Length; i++) + { + var l = lines[i]; + if (l.Length == 0) break; + if (!l.StartsWith('#')) break; + // Stop at the first "Usage:" or "Flags:" header — that marks + // the end of the prose block. + var stripped = l.TrimStart('#').TrimStart(); + if (Regex.IsMatch(stripped, @"^[A-Z][A-Za-z\s]+:\s*$")) break; + if (sb.Length > 0) sb.Append(' '); + sb.Append(stripped); + } + var text = sb.ToString().Trim(); + return text.Length > 320 ? text.Substring(0, 317) + "..." : text; + } + + // ----- DocsGen + SysML-Import ------------------------------------------- + + // Matches `case "--flag":` and the immediately-following + // `RequireValue` / break statements in the typical + // `for (int i = 0; ...)` argument parser pattern. + private static readonly Regex DotnetFlagRe = new( + @"case\s+""(?--[a-zA-Z][a-zA-Z0-9-]*)""\s*:", + RegexOptions.Compiled); + + private static CliInfo CollectDotNetTool(string name, string file, string repoRoot, string summary) + { + var text = File.ReadAllText(file); + var lines = text.Split('\n'); + + // First pass: try to read structured flag descriptions out of the + // leading `//` Flags: block (same shape as the bash help blocks). + var headerDescs = ExtractDotnetHeaderFlagDescriptions(lines); + + var flags = new List(); + foreach (Match m in DotnetFlagRe.Matches(text)) + { + var flagName = m.Groups["flag"].Value; + if (flags.Any(f => f.Name == flagName)) continue; + + // Description-source order: leading `//` header block (preferred, + // longer prose with newlines), then Console.WriteLine printed help. + string? desc = null; + if (headerDescs.TryGetValue(flagName, out var headerDesc)) desc = headerDesc; + desc ??= ExtractDotnetFlagDescription(text, flagName); + + // Detect whether the case body calls `RequireValue` — if it + // does, the flag takes a value. + bool takesValue = Regex.IsMatch(text, + $@"case\s+""{Regex.Escape(flagName)}""\s*:[\s\S]{{0,200}}?RequireValue"); + flags.Add(new CliFlag( + Name: flagName, + Short: null, + ArgShape: takesValue ? "" : null, + Description: desc ?? string.Empty)); + } + + return new CliInfo( + Name: name, + Category: "contributor", + Summary: summary, + SourceRelativePath: Path.GetRelativePath(repoRoot, file).Replace('\\', '/'), + Commands: Array.Empty(), + Flags: flags + .OrderBy(f => f.Name, StringComparer.Ordinal) + .ToList(), + Arguments: Array.Empty()); + } + + private static Dictionary ExtractDotnetHeaderFlagDescriptions(string[] lines) + { + // Scan the leading `//` block for a "Flags:" header, then collect + // the indented flag rows that follow until a blank `//` line or a + // non-`//` line. + var result = new Dictionary(StringComparer.Ordinal); + bool inFlags = false; + string? pendingFlag = null; + var descBuf = new System.Text.StringBuilder(); + + void Flush() + { + if (pendingFlag is null) return; + result[pendingFlag] = descBuf.ToString().Trim(); + pendingFlag = null; + descBuf.Clear(); + } + + // Matches `// --flag Description...` and + // `// --flag Description...` shapes. + var headerFlagRe = new Regex( + @"^//(?\s{1,6})(?--[a-zA-Z][a-zA-Z0-9-]+)(?:\s+<[^>]+>)?\s+(?\S.*)$", + RegexOptions.Compiled); + + bool seenAnyComment = false; + foreach (var rawLine in lines) + { + var line = rawLine.TrimEnd('\r'); + // A non-comment line either skips us forward to the first + // `//` block (the file may start with `using …;` and friends) + // or, once we've started consuming a comment block, ends it. + if (!line.StartsWith("//", StringComparison.Ordinal)) + { + if (!seenAnyComment) continue; + Flush(); + break; + } + seenAnyComment = true; + var trimmed = line.Substring(2).TrimStart(); + if (Regex.IsMatch(trimmed, @"^Flags:\s*$")) + { + inFlags = true; + continue; + } + if (!inFlags) continue; + // A blank `//` line ends the block. + if (trimmed.Length == 0) + { + Flush(); + inFlags = false; + continue; + } + var m = headerFlagRe.Match(line); + if (m.Success) + { + Flush(); + pendingFlag = m.Groups["long"].Value; + descBuf.Clear(); + descBuf.Append(m.Groups["desc"].Value); + } + else if (pendingFlag is not null) + { + descBuf.Append(' ').Append(trimmed); + } + } + Flush(); + return result; + } + + private static string? ExtractDotnetFlagDescription(string text, string flagName) + { + // The help-print block emits lines like: + // Console.WriteLine(" --repo Repository root (required)"); + // Walk the WriteLine literals looking for the flag name. + var helpRe = new Regex( + $@"Console\.WriteLine\(""(?\s*{Regex.Escape(flagName)}\s+[^""]+)""", + RegexOptions.Compiled); + var m = helpRe.Match(text); + if (!m.Success) return null; + var raw = m.Groups["line"].Value.Trim(); + // Drop the leading flag name + any value-shape so only the + // description remains. + var stripped = Regex.Replace(raw, $@"^{Regex.Escape(flagName)}\s+(?:<[^>]+>)?\s*", ""); + return stripped.Trim(); + } +} diff --git a/build/MTConnect.NET-DocsGen/ConfigInventory.cs b/build/MTConnect.NET-DocsGen/ConfigInventory.cs new file mode 100644 index 000000000..498c6daa7 --- /dev/null +++ b/build/MTConnect.NET-DocsGen/ConfigInventory.cs @@ -0,0 +1,221 @@ +// Copyright (c) 2026 TrakHound Inc., All Rights Reserved. +// TrakHound Inc. licenses this file to you under the MIT license. + +using Microsoft.CodeAnalysis; +using Microsoft.CodeAnalysis.CSharp; +using Microsoft.CodeAnalysis.CSharp.Syntax; +using System.Text; + +namespace MTConnect.NET_DocsGen; + +/// +/// One discovered configuration option class with its inventory of +/// settable / writable properties. The schema is derived from the +/// source-level property declarations, the YAML / JSON attribute +/// aliases, and the `///` summary above each property. +/// +public sealed record ConfigClassInfo( + string TypeName, + string Namespace, + string FileRelativePath, + string Summary, + IReadOnlyList Properties); + +/// +/// A single configuration property. +/// +public sealed record ConfigPropertyInfo( + string Name, + string Type, + string SerialisedKey, + string Summary, + string? DefaultLiteral); + +/// +/// Builds the configuration inventory. Limited deliberately to the +/// agent / adapter / module configuration surface — wire-format +/// "configurations" (sensor configuration, namespace configuration, +/// etc.) are already documented in DocFX-rendered API reference +/// pages and would only add noise here. +/// +public static class ConfigInventory +{ + /// + /// Files whose stem appears here are treated as agent / adapter + /// configuration entry points and walked for property options. + /// Anything else under `libraries/*/Configurations/` is skipped + /// (e.g. namespace / style / device-level wire configuration). + /// + private static readonly HashSet IncludedStems = new(StringComparer.Ordinal) + { + "AgentConfiguration", + "AgentApplicationConfiguration", + "AdapterApplicationConfiguration", + "IAgentConfiguration", + "IAgentApplicationConfiguration", + "IAdapterApplicationConfiguration", + "DataSourceConfiguration", + "IDataSourceConfiguration", + "HttpClientConfiguration", + "IHttpClientConfiguration", + "ShdrClientConfiguration", + "IShdrClientConfiguration", + "ShdrAdapterClientConfiguration", + "IShdrAdapterClientConfiguration", + "TlsConfiguration", + "PfxCertificateConfiguration", + "PemCertificateConfiguration", + "FileConfiguration", + "IFileConfiguration", + }; + + /// + /// Walks every libraries/*/Configurations/*.cs file under + /// whose stem is in + /// and returns one + /// per discovered configuration + /// class. Output is sorted by type name. + /// + /// Repository root. + /// Ordered list of configuration classes. + public static IReadOnlyList Collect(string repoRoot) + { + var results = new List(); + + var librariesDir = Path.Combine(repoRoot, "libraries"); + if (!Directory.Exists(librariesDir)) return results; + + foreach (var file in Directory.EnumerateFiles(librariesDir, "*.cs", SearchOption.AllDirectories)) + { + // Skip generated and build outputs. + if (file.Contains("/bin/", StringComparison.Ordinal) + || file.Contains("/obj/", StringComparison.Ordinal) + || file.Contains("\\bin\\", StringComparison.Ordinal) + || file.Contains("\\obj\\", StringComparison.Ordinal)) continue; + if (file.EndsWith(".g.cs", StringComparison.Ordinal)) continue; + + var stem = Path.GetFileNameWithoutExtension(file); + if (!IncludedStems.Contains(stem)) continue; + + var text = File.ReadAllText(file); + var rel = Path.GetRelativePath(repoRoot, file).Replace('\\', '/'); + var tree = CSharpSyntaxTree.ParseText(text, path: file); + + foreach (var typeDecl in tree.GetRoot().DescendantNodes().OfType()) + { + if (typeDecl is not (ClassDeclarationSyntax or InterfaceDeclarationSyntax)) continue; + if (typeDecl.Identifier.ValueText != stem) continue; + + var ns = (typeDecl.Ancestors().OfType().FirstOrDefault()? + .Name.ToString()) ?? string.Empty; + + var typeSummary = ExtractSummary(typeDecl.GetLeadingTrivia()); + + var props = new List(); + foreach (var member in typeDecl.ChildNodes().OfType()) + { + // Public, instance properties only. + bool isPublic = member.Modifiers.Any(m => m.IsKind(SyntaxKind.PublicKeyword)); + bool isInterface = typeDecl is InterfaceDeclarationSyntax; + if (!isPublic && !isInterface) continue; + + // Skip [JsonIgnore]/[YamlIgnore] both-ignored properties. + bool jsonIgnore = HasAttr(member.AttributeLists, "JsonIgnore"); + bool yamlIgnore = HasAttr(member.AttributeLists, "YamlIgnore"); + if (jsonIgnore && yamlIgnore) continue; + + var summary = ExtractSummary(member.GetLeadingTrivia()); + var serialisedKey = ExtractSerialisedKey(member.AttributeLists, member.Identifier.ValueText); + var type = member.Type.ToString(); + + props.Add(new ConfigPropertyInfo( + Name: member.Identifier.ValueText, + Type: type, + SerialisedKey: serialisedKey, + Summary: summary, + DefaultLiteral: null)); + } + + if (props.Count == 0) continue; + + results.Add(new ConfigClassInfo( + TypeName: typeDecl.Identifier.ValueText, + Namespace: ns, + FileRelativePath: rel, + Summary: typeSummary, + Properties: props + .OrderBy(p => p.SerialisedKey, StringComparer.Ordinal) + .ToList())); + } + } + + return results + .OrderBy(c => c.Namespace, StringComparer.Ordinal) + .ThenBy(c => c.TypeName, StringComparer.Ordinal) + .ToList(); + } + + private static bool HasAttr(SyntaxList lists, string name) + { + foreach (var al in lists) + foreach (var a in al.Attributes) + if (a.Name.ToString() == name) return true; + return false; + } + + private static string ExtractSerialisedKey(SyntaxList attrs, string propName) + { + foreach (var al in attrs) + { + foreach (var a in al.Attributes) + { + var n = a.Name.ToString(); + if (n is "JsonPropertyName" or "YamlMember") + { + if (a.ArgumentList is null) continue; + foreach (var arg in a.ArgumentList.Arguments) + { + // YamlMember(Alias = "x") + if (arg.NameEquals is not null && arg.NameEquals.Name.Identifier.ValueText == "Alias") + { + if (arg.Expression is LiteralExpressionSyntax l1 && l1.IsKind(SyntaxKind.StringLiteralExpression)) + return l1.Token.ValueText; + } + // JsonPropertyName("x") — positional + if (arg.NameEquals is null && arg.Expression is LiteralExpressionSyntax l2 && l2.IsKind(SyntaxKind.StringLiteralExpression)) + { + return l2.Token.ValueText; + } + } + } + } + } + // Convention: lowerCamelCase from PascalCase if no attribute given. + if (string.IsNullOrEmpty(propName)) return propName; + return char.ToLowerInvariant(propName[0]) + propName[1..]; + } + + private static string ExtractSummary(SyntaxTriviaList leading) + { + var trivia = leading.FirstOrDefault(t => + t.IsKind(SyntaxKind.SingleLineDocumentationCommentTrivia) + || t.IsKind(SyntaxKind.MultiLineDocumentationCommentTrivia)); + if (trivia == default) return string.Empty; + + if (trivia.GetStructure() is not DocumentationCommentTriviaSyntax dox) return string.Empty; + var summary = dox.Content.OfType() + .FirstOrDefault(e => e.StartTag.Name.LocalName.ValueText == "summary"); + if (summary is null) return string.Empty; + + var sb = new StringBuilder(); + foreach (var node in summary.Content) sb.Append(node.ToString()); + + var lines = sb.ToString().Split('\n') + .Select(l => l.TrimStart().TrimStart('/').TrimStart()) + .Where(l => l.Length > 0); + var joined = string.Join(' ', lines).Trim(); + while (joined.Contains(" ", StringComparison.Ordinal)) + joined = joined.Replace(" ", " "); + return joined; + } +} diff --git a/build/MTConnect.NET-DocsGen/EnvVarInventory.cs b/build/MTConnect.NET-DocsGen/EnvVarInventory.cs new file mode 100644 index 000000000..9feda8adc --- /dev/null +++ b/build/MTConnect.NET-DocsGen/EnvVarInventory.cs @@ -0,0 +1,357 @@ +// Copyright (c) 2026 TrakHound Inc., All Rights Reserved. +// TrakHound Inc. licenses this file to you under the MIT license. + +using Microsoft.CodeAnalysis; +using Microsoft.CodeAnalysis.CSharp; +using Microsoft.CodeAnalysis.CSharp.Syntax; + +namespace MTConnect.NET_DocsGen; + +/// +/// A single environment-variable reference discovered by either the +/// Roslyn (C#) or the shell-script (Bash / PowerShell) collector. +/// +public sealed record EnvVarInfo( + string Name, + string FallbackLiteral, + string FileRelativePath, + int Line, + string Context, + string Kind); // "csharp-read" | "shell-read" | "shell-write" | "powershell-read" | "powershell-write" + +/// +/// Walks every `*.cs`, `tools/*.sh`, and `tools/*.ps1` file under the +/// repository (excluding build outputs and the docs/ node_modules +/// tree) and records every environment-variable reference. The +/// recognised patterns are: +/// +/// - C# (`*.cs`): +/// Environment.GetEnvironmentVariable("NAME") +/// Environment.GetEnvironmentVariable("NAME", EnvironmentVariableTarget.X) +/// - Bash (`*.sh`): +/// ${MTCONNECT_NAME:-default} (read with default) +/// ${MTCONNECT_NAME} (bare read) +/// export MTCONNECT_NAME=value (write) +/// - PowerShell (`*.ps1`): +/// $env:MTCONNECT_NAME (read) +/// $env:MTCONNECT_NAME = 'value' (write) +/// +/// Each call captures the variable name, the optional default literal +/// that appears alongside the read, the file:line location, and a +/// short snippet of context. +/// +public static class EnvVarInventory +{ + private static readonly string[] ExcludedDirectoryNames = + { + "bin", "obj", "node_modules", ".git", ".vitepress", + }; + + // Match `MTCONNECT_FOO`, `DOTNET_BAR`, plus any other ALL-CAPS env-var + // shape used by the repo. Lower-case shell vars are deliberately + // ignored — they are local variables, not OS env vars. + private static readonly System.Text.RegularExpressions.Regex EnvNameRe = + new(@"\b([A-Z][A-Z0-9_]{2,})\b", System.Text.RegularExpressions.RegexOptions.Compiled); + + /// + /// Walks every *.cs file under + /// plus the tools/*.sh and tools/*.ps1 trees and + /// returns every env-var read / write / docker-pass discovered. + /// Output is deterministically sorted by name, kind, file, line. + /// + /// Repository root. + /// Ordered list of env-var references. + public static IReadOnlyList Collect(string repoRoot) + { + var results = new List(); + + // ---- C# read sites ------------------------------------------------- + foreach (var file in EnumerateCsFiles(repoRoot)) + { + string text; + try { text = File.ReadAllText(file); } + catch { continue; } + + // Cheap text gate before parsing. + if (!text.Contains("GetEnvironmentVariable", StringComparison.Ordinal)) continue; + + var tree = CSharpSyntaxTree.ParseText(text, path: file); + var rel = Path.GetRelativePath(repoRoot, file).Replace('\\', '/'); + + // Local resolution of `const string X = "..."` so call sites + // like `GetEnvironmentVariable(FixtureDirEnv)` still resolve + // without a semantic model. + var localConsts = new Dictionary(StringComparer.Ordinal); + foreach (var field in tree.GetRoot().DescendantNodes().OfType()) + { + bool isConst = field.Modifiers.Any(t => t.IsKind(SyntaxKind.ConstKeyword)); + if (!isConst) continue; + foreach (var v in field.Declaration.Variables) + { + if (v.Initializer?.Value is LiteralExpressionSyntax l + && l.IsKind(SyntaxKind.StringLiteralExpression)) + { + localConsts[v.Identifier.ValueText] = l.Token.ValueText; + } + } + } + + foreach (var inv in tree.GetRoot().DescendantNodes().OfType()) + { + if (inv.Expression is not MemberAccessExpressionSyntax m) continue; + if (m.Name.Identifier.ValueText != "GetEnvironmentVariable") continue; + + var args = inv.ArgumentList.Arguments; + if (args.Count == 0) continue; + string? name = null; + if (args[0].Expression is LiteralExpressionSyntax lit && lit.IsKind(SyntaxKind.StringLiteralExpression)) + { + name = lit.Token.ValueText; + } + else if (args[0].Expression is IdentifierNameSyntax id + && localConsts.TryGetValue(id.Identifier.ValueText, out var resolved)) + { + name = resolved; + } + if (name is null) continue; + + var line = inv.GetLocation().GetLineSpan().StartLinePosition.Line + 1; + + // Look at the enclosing statement / expression for a + // ?? "default" or `?? Environment.GetEnvironmentVariable(...)` + // fallback. + var fallback = string.Empty; + var parent = inv.Parent; + while (parent is not null && parent is not StatementSyntax && parent is not MemberDeclarationSyntax) + { + if (parent is BinaryExpressionSyntax bin && bin.IsKind(SyntaxKind.CoalesceExpression)) + { + fallback = bin.Right.ToString(); + break; + } + parent = parent.Parent; + } + + var context = inv.Parent?.ToString() ?? inv.ToString(); + if (context.Length > 160) context = context.Substring(0, 157) + "..."; + context = context.Replace('\n', ' ').Replace('\r', ' ').Replace('|', '/'); + + results.Add(new EnvVarInfo(name, fallback, rel, line, context, "csharp-read")); + } + } + + // ---- Shell / PowerShell sites -------------------------------------- + var toolsDir = Path.Combine(repoRoot, "tools"); + if (Directory.Exists(toolsDir)) + { + foreach (var sh in Directory.EnumerateFiles(toolsDir, "*.sh", SearchOption.AllDirectories)) + { + CollectShell(sh, repoRoot, results); + } + foreach (var ps in Directory.EnumerateFiles(toolsDir, "*.ps1", SearchOption.AllDirectories)) + { + CollectPowerShell(ps, repoRoot, results); + } + } + + return results + .OrderBy(e => e.Name, StringComparer.Ordinal) + .ThenBy(e => e.Kind, StringComparer.Ordinal) + .ThenBy(e => e.FileRelativePath, StringComparer.Ordinal) + .ThenBy(e => e.Line) + .ToList(); + } + + // ----- Shell collectors ------------------------------------------------- + + // Matches `${VAR:-default}` (read with default literal) and `${VAR}` / + // `$VAR` (bare read). The default literal can be either bare text or a + // quoted string. The default capture stops at the closing `}` of the + // outer expansion and explicitly allows a nested `${…}` inside (for + // patterns like `${MTCONNECT_DOTNET_IMAGE:-${IMAGE_DEFAULT}}`). + private static readonly System.Text.RegularExpressions.Regex ShellReadRe = new( + @"\$\{(?[A-Z][A-Z0-9_]{2,})(?:\:-(?(?:\$\{[^}]*\}|[^}])*))?\}", + System.Text.RegularExpressions.RegexOptions.Compiled); + + // Matches `export VAR=value` and `VAR=value` at the start of a line. + private static readonly System.Text.RegularExpressions.Regex ShellWriteRe = new( + @"^\s*(?:export\s+)?(?[A-Z][A-Z0-9_]{2,})=(?[^\s#]*)", + System.Text.RegularExpressions.RegexOptions.Compiled); + + // Matches `docker run -e VAR=value` or `-e "VAR=value"` — the variable + // is passed into a child container's environment. From a documentation + // standpoint these are still env-var references the codebase honors. + private static readonly System.Text.RegularExpressions.Regex DockerEnvRe = new( + @"-e\s+""?(?[A-Z][A-Z0-9_]{2,})=(?[^""\s]*)", + System.Text.RegularExpressions.RegexOptions.Compiled); + + // Matches the start of a heredoc and captures the delimiter, with or + // without single-quote / double-quote wrapping (which only affects + // interpolation, not the body-bracket). + private static readonly System.Text.RegularExpressions.Regex HeredocStartRe = new( + @"<<-?\s*['""]?(?[A-Za-z_][A-Za-z0-9_]*)['""]?", + System.Text.RegularExpressions.RegexOptions.Compiled); + + private static void CollectShell(string file, string repoRoot, List sink) + { + string[] lines; + try { lines = File.ReadAllLines(file); } + catch { return; } + var rel = Path.GetRelativePath(repoRoot, file).Replace('\\', '/'); + + // De-dupe identical hits on the same (kind, line) tuple — a single + // PS expression that mentions `$env:X` twice should yield one row. + var seen = new HashSet<(string Name, string Kind, int Line)>(); + string? heredocDelim = null; + + for (int i = 0; i < lines.Length; i++) + { + var line = lines[i]; + + // Track heredoc bodies. A heredoc opens on `<[A-Z][A-Z0-9_]{2,})", + System.Text.RegularExpressions.RegexOptions.Compiled); + + // Matches `$env:NAME = 'value'` writes. + private static readonly System.Text.RegularExpressions.Regex PsWriteRe = new( + @"\$env:(?[A-Z][A-Z0-9_]{2,})\s*=\s*(?'[^']*'|""[^""]*""|\S+)", + System.Text.RegularExpressions.RegexOptions.Compiled); + + private static void CollectPowerShell(string file, string repoRoot, List sink) + { + string[] lines; + try { lines = File.ReadAllLines(file); } + catch { return; } + var rel = Path.GetRelativePath(repoRoot, file).Replace('\\', '/'); + + // De-dupe identical hits on the same (kind, line) tuple. + var seen = new HashSet<(string Name, string Kind, int Line)>(); + + for (int i = 0; i < lines.Length; i++) + { + var line = lines[i]; + var trimmed = line.TrimStart(); + // PowerShell comments start with `#` too. + if (trimmed.StartsWith('#')) continue; + + // Writes first so a single line like `$env:X = '1'` is only + // counted once (a write line also matches the read pattern). + var w = PsWriteRe.Match(line); + if (w.Success) + { + var name = w.Groups["name"].Value; + if (IsRelevantVar(name) && seen.Add((name, "powershell-write", i + 1))) + { + sink.Add(new EnvVarInfo(name, w.Groups["value"].Value, rel, i + 1, Snip(line), "powershell-write")); + continue; + } + } + + foreach (System.Text.RegularExpressions.Match m in PsReadRe.Matches(line)) + { + var name = m.Groups["name"].Value; + if (!IsRelevantVar(name)) continue; + if (!seen.Add((name, "powershell-read", i + 1))) continue; + sink.Add(new EnvVarInfo(name, string.Empty, rel, i + 1, Snip(line), "powershell-read")); + } + } + } + + // Keep the inventory focused on MTConnect-namespaced environment + // variables plus the small set of well-known cross-cutting ones the + // repo actually honors. Without this filter every uppercase token in + // every line of every script (PATH, HOME, NUGET_PACKAGES, ...) would + // flood the inventory. + private static bool IsRelevantVar(string name) => + name.StartsWith("MTCONNECT_", StringComparison.Ordinal); + + private static string Snip(string s) + { + var t = s.Trim(); + return t.Length > 160 ? t.Substring(0, 157) + "..." : t; + } + + private static IEnumerable EnumerateCsFiles(string root) + { + var stack = new Stack(); + stack.Push(root); + while (stack.Count > 0) + { + var dir = stack.Pop(); + IEnumerable subs; + try { subs = Directory.EnumerateDirectories(dir); } + catch { continue; } + foreach (var sub in subs) + { + var name = Path.GetFileName(sub); + if (ExcludedDirectoryNames.Contains(name, StringComparer.Ordinal)) continue; + stack.Push(sub); + } + IEnumerable files; + try { files = Directory.EnumerateFiles(dir, "*.cs"); } + catch { continue; } + foreach (var f in files) yield return f; + } + } +} diff --git a/build/MTConnect.NET-DocsGen/MTConnect.NET-DocsGen.csproj b/build/MTConnect.NET-DocsGen/MTConnect.NET-DocsGen.csproj new file mode 100644 index 000000000..703ae5c26 --- /dev/null +++ b/build/MTConnect.NET-DocsGen/MTConnect.NET-DocsGen.csproj @@ -0,0 +1,24 @@ + + + + Exe + net8.0 + MTConnect.NET_DocsGen + enable + enable + false + + + + + + + + diff --git a/build/MTConnect.NET-DocsGen/Program.cs b/build/MTConnect.NET-DocsGen/Program.cs new file mode 100644 index 000000000..7221217b4 --- /dev/null +++ b/build/MTConnect.NET-DocsGen/Program.cs @@ -0,0 +1,157 @@ +// Copyright (c) 2026 TrakHound Inc., All Rights Reserved. +// TrakHound Inc. licenses this file to you under the MIT license. + +using MTConnect.NET_DocsGen; + +// DocsGen entry point. Walks the repository source tree (Roslyn-only, +// no compiled assemblies) and emits the auto-generated VitePress +// reference pages: +// +// docs/reference/http-api.md +// docs/reference/environment-variables.md +// docs/reference/configuration.md +// docs/reference/cli.md +// +// Usage: +// dotnet run --project build/MTConnect.NET-DocsGen \ +// -- --repo [--out ] +// +// Flags: +// --repo Repository root. Required. +// --out Docs root. Defaults to "/docs". +// --check Run the inventory but do NOT write files; exits 0 +// iff the inventory matches what is already on disk. +// +// The same inventory routines are exposed as public static methods on +// `RouteInventory`, `EnvVarInventory`, `ConfigInventory`, and +// `CliInventory` so the validation test in `tests/` can re-run them +// independently and assert the on-disk markdown is in lock-step with +// the source tree. + +string? repoRoot = null; +string? docsRoot = null; +bool checkOnly = false; + +for (int i = 0; i < args.Length; i++) +{ + switch (args[i]) + { + case "--repo": + repoRoot = RequireValue(args, ref i, "--repo"); + break; + case "--out": + docsRoot = RequireValue(args, ref i, "--out"); + break; + case "--check": + checkOnly = true; + break; + case "-h": + case "--help": + PrintHelp(); + return 0; + default: + Console.Error.WriteLine($"Unknown argument: {args[i]}"); + PrintHelp(); + return 2; + } +} + +if (string.IsNullOrEmpty(repoRoot)) +{ + Console.Error.WriteLine("--repo is required."); + PrintHelp(); + return 2; +} + +repoRoot = Path.GetFullPath(repoRoot); +docsRoot ??= Path.Combine(repoRoot, "docs"); +docsRoot = Path.GetFullPath(docsRoot); + +if (!Directory.Exists(repoRoot)) +{ + Console.Error.WriteLine($"Repository root does not exist: {repoRoot}"); + return 2; +} + +var referenceDir = Path.Combine(docsRoot, "reference"); +Directory.CreateDirectory(referenceDir); + +Console.WriteLine($"==> repo : {repoRoot}"); +Console.WriteLine($"==> docs : {docsRoot}"); + +var routes = RouteInventory.Collect(repoRoot); +var envVars = EnvVarInventory.Collect(repoRoot); +var configs = ConfigInventory.Collect(repoRoot); +var clis = CliInventory.Collect(repoRoot); + +Console.WriteLine($" routes : {routes.Count}"); +Console.WriteLine($" env-vars : {envVars.Count}"); +Console.WriteLine($" config keys : {configs.Sum(c => c.Properties.Count)} across {configs.Count} types"); +Console.WriteLine($" CLIs : {clis.Count} ({clis.Count(c => c.Category == "shipped")} shipped, {clis.Count(c => c.Category == "contributor")} contributor)"); + +var httpMd = HttpApiRenderer.Render(routes); +var envMd = EnvVarRenderer.Render(envVars); +var configMd = ConfigRenderer.Render(configs); +var cliMd = CliRenderer.Render(clis); + +var paths = new (string path, string content)[] +{ + (Path.Combine(referenceDir, "http-api.md"), httpMd), + (Path.Combine(referenceDir, "environment-variables.md"), envMd), + (Path.Combine(referenceDir, "configuration.md"), configMd), + (Path.Combine(referenceDir, "cli.md"), cliMd), + (Path.Combine(referenceDir, "index.md"), IndexRenderer.Render()), +}; + +if (checkOnly) +{ + bool drift = false; + foreach (var (path, expected) in paths) + { + if (!File.Exists(path)) + { + Console.Error.WriteLine($"MISSING: {path}"); + drift = true; + continue; + } + var actual = File.ReadAllText(path); + if (!string.Equals(actual, expected, StringComparison.Ordinal)) + { + Console.Error.WriteLine($"DRIFT : {path}"); + drift = true; + } + } + if (drift) + { + Console.Error.WriteLine("docs reference is out of date; re-run without --check to regenerate."); + return 1; + } + Console.WriteLine("==> reference pages match source inventory."); + return 0; +} + +foreach (var (path, content) in paths) +{ + File.WriteAllText(path, content); + Console.WriteLine($" wrote {Path.GetRelativePath(repoRoot, path)} ({content.Length:N0} chars)"); +} + +Console.WriteLine("==> done."); +return 0; + +static string RequireValue(string[] args, ref int i, string flag) +{ + if (i + 1 >= args.Length) + { + throw new InvalidOperationException($"{flag} requires a value"); + } + return args[++i]; +} + +static void PrintHelp() +{ + Console.WriteLine("dotnet run --project build/MTConnect.NET-DocsGen --"); + Console.WriteLine(" --repo Repository root (required)"); + Console.WriteLine(" --out Docs root (defaults to /docs)"); + Console.WriteLine(" --check Verify pages are in sync; exit 1 on drift"); +} diff --git a/build/MTConnect.NET-DocsGen/Renderers.cs b/build/MTConnect.NET-DocsGen/Renderers.cs new file mode 100644 index 000000000..a0b898583 --- /dev/null +++ b/build/MTConnect.NET-DocsGen/Renderers.cs @@ -0,0 +1,401 @@ +// Copyright (c) 2026 TrakHound Inc., All Rights Reserved. +// TrakHound Inc. licenses this file to you under the MIT license. + +using System.Text; + +namespace MTConnect.NET_DocsGen; + +/// +/// Markdown for `docs/reference/index.md` — the landing page for the +/// auto-generated reference section. +/// +public static class IndexRenderer +{ + /// + /// HTML comment marker prepended to every auto-generated page so + /// reviewers (and the parity test) can detect manual edits. + /// + public const string AutoGenMarker = ""; + + /// + /// Builds the contents of docs/reference/index.md: the + /// landing page that lists every auto-generated reference page. + /// + /// Full markdown text. + public static string Render() + { + var sb = new StringBuilder(); + sb.AppendLine(AutoGenMarker); + sb.AppendLine(); + sb.AppendLine("# Auto-generated reference"); + sb.AppendLine(); + sb.AppendLine("Every page in this section is produced by `build/MTConnect.NET-DocsGen` at docs-build time by inspecting the source tree with Roslyn. Editing these files by hand will be overwritten on the next regeneration; instead, edit the source and re-run:"); + sb.AppendLine(); + sb.AppendLine("```bash"); + sb.AppendLine("dotnet run --project build/MTConnect.NET-DocsGen -- --repo ."); + sb.AppendLine("```"); + sb.AppendLine(); + sb.AppendLine("## Pages"); + sb.AppendLine(); + sb.AppendLine("- [HTTP API endpoints](./http-api)"); + sb.AppendLine("- [Environment variables](./environment-variables)"); + sb.AppendLine("- [Configuration schema](./configuration)"); + sb.AppendLine("- [CLI reference](./cli)"); + sb.AppendLine(); + sb.AppendLine("## Validation"); + sb.AppendLine(); + sb.AppendLine("`MTConnect.NET-Docs-Tests` includes a `DocsReferenceGenerationTests` fixture that re-runs the same Roslyn / shell inventories and asserts the on-disk markdown is in sync. Adding an HTTP route, a `Environment.GetEnvironmentVariable(\"…\")` read, a `${MTCONNECT_…}` reference in a contributor script, or a configuration property without regenerating the reference therefore fails CI."); + sb.AppendLine(); + return sb.ToString(); + } +} + +/// +/// Markdown for `docs/reference/http-api.md`. +/// +public static class HttpApiRenderer +{ + /// + /// Builds the contents of docs/reference/http-api.md from + /// the supplied endpoint inventory. + /// + /// Endpoints discovered by + /// . + /// Full markdown text. + public static string Render(IReadOnlyList endpoints) + { + var sb = new StringBuilder(); + sb.AppendLine(IndexRenderer.AutoGenMarker); + sb.AppendLine(); + sb.AppendLine("# HTTP API reference"); + sb.AppendLine(); + sb.AppendLine("This page lists every HTTP endpoint exposed by an MTConnect.NET agent, separated by the underlying transport implementation. The list is generated by walking the source tree with Roslyn and does not require any project to compile — including `MTConnect.NET-HTTP-AspNetCore`, which currently fails to build on `net8.0` (see `extra-files.user/spec/` for the porting issue) and is documented here statically."); + sb.AppendLine(); + sb.AppendLine("## Surface taxonomy"); + sb.AppendLine(); + sb.AppendLine("- **Agent API** — the MTConnect-Standard request types (`/probe`, `/current`, `/sample`, `/assets`, `/asset/{id}`, and the per-device variants of the same). Every endpoint listed below currently belongs to this surface."); + sb.AppendLine("- **Admin / diagnostic** — none. No administrative endpoint is currently exposed by either transport. A search for `/admin`, `/diagnostics`, `/metrics`, or `/health` across the source tree returns no hits."); + sb.AppendLine(); + sb.AppendLine("## Ceen transport (`MTConnect.NET-HTTP`)"); + sb.AppendLine(); + sb.AppendLine("Routes are registered inside `MTConnectHttpServer.ConfigureServer` and dispatched by the bundled Ceen router."); + sb.AppendLine(); + RenderTable(sb, endpoints.Where(e => e.Source == "Ceen")); + + sb.AppendLine(); + sb.AppendLine("## AspNetCore transport (`MTConnect.NET-HTTP-AspNetCore`)"); + sb.AppendLine(); + sb.AppendLine("Routes are declared on `[ApiController]` types under `Http/Controllers/`. The project does not currently build on `net8.0`, so this section is generated by static Roslyn inspection and will track any future controller changes regardless of build state."); + sb.AppendLine(); + RenderTable(sb, endpoints.Where(e => e.Source == "AspNetCore")); + + sb.AppendLine(); + sb.AppendLine("## Per-endpoint detail"); + sb.AppendLine(); + foreach (var e in endpoints) + { + sb.AppendLine($"### `{e.Method} {e.PathTemplate}` — {e.Source}"); + sb.AppendLine(); + sb.AppendLine($"- **Handler**: `{e.Handler}`"); + sb.AppendLine($"- **Surface**: {e.Surface}"); + sb.AppendLine($"- **Source**: [`{e.FileRelativePath}:{e.Line}`](https://github.com/TrakHound/MTConnect.NET/blob/master/{e.FileRelativePath}#L{e.Line})"); + if (e.ResponseStatusCodes.Count > 0) + { + sb.AppendLine($"- **Response status codes**: {string.Join(", ", e.ResponseStatusCodes)}"); + } + sb.AppendLine(); + if (!string.IsNullOrEmpty(e.Summary)) + { + sb.AppendLine(e.Summary); + sb.AppendLine(); + } + if (e.Parameters.Count > 0) + { + sb.AppendLine("**Parameters**"); + sb.AppendLine(); + sb.AppendLine("| Name | Kind | Type | Default | Description |"); + sb.AppendLine("| --- | --- | --- | --- | --- |"); + foreach (var p in e.Parameters) + { + sb.AppendLine($"| `{p.Name}` | {p.Kind} | `{EscapeCell(p.Type)}` | {EscapeCell(p.DefaultValue ?? string.Empty)} | {EscapeCell(p.Summary)} |"); + } + sb.AppendLine(); + } + } + + return sb.ToString(); + } + + private static void RenderTable(StringBuilder sb, IEnumerable rows) + { + var list = rows.ToList(); + if (list.Count == 0) + { + sb.AppendLine("_No endpoints discovered._"); + sb.AppendLine(); + return; + } + sb.AppendLine("| Method | Path | Handler | Source |"); + sb.AppendLine("| --- | --- | --- | --- |"); + foreach (var e in list) + { + sb.AppendLine($"| `{e.Method}` | `{e.PathTemplate}` | `{e.Handler}` | `{e.FileRelativePath}:{e.Line}` |"); + } + } + + private static string EscapeCell(string s) => s.Replace("|", "\\|").Replace("\n", " ").Replace("\r", " "); +} + +/// +/// Markdown for `docs/reference/environment-variables.md`. +/// +public static class EnvVarRenderer +{ + /// + /// Builds the contents of + /// docs/reference/environment-variables.md from the + /// supplied env-var inventory. + /// + /// Env-var references discovered by + /// . + /// Full markdown text. + public static string Render(IReadOnlyList vars) + { + var sb = new StringBuilder(); + sb.AppendLine(IndexRenderer.AutoGenMarker); + sb.AppendLine(); + sb.AppendLine("# Environment variables"); + sb.AppendLine(); + sb.AppendLine("Every environment-variable reference discovered in the source tree. Both the C# `Environment.GetEnvironmentVariable(\"…\")` read sites and the contributor scripts under `tools/` (`*.sh` and `*.ps1`) are scanned. Variables are grouped by name, so reads, writes, and defaults that all target the same variable appear together."); + sb.AppendLine(); + if (vars.Count == 0) + { + sb.AppendLine("_No environment-variable references found in the current source tree._"); + sb.AppendLine(); + return sb.ToString(); + } + + // Group by variable name. + var byName = vars + .GroupBy(v => v.Name, StringComparer.Ordinal) + .OrderBy(g => g.Key, StringComparer.Ordinal) + .ToList(); + + sb.AppendLine("## Summary"); + sb.AppendLine(); + sb.AppendLine("| Variable | Kinds | Default(s) |"); + sb.AppendLine("| --- | --- | --- |"); + foreach (var g in byName) + { + var kinds = string.Join(", ", g.Select(v => v.Kind).Distinct().OrderBy(k => k, StringComparer.Ordinal)); + var defaults = string.Join(", ", g.Where(v => !string.IsNullOrEmpty(v.FallbackLiteral)) + .Select(v => $"`{v.FallbackLiteral}`").Distinct()); + sb.AppendLine($"| `{g.Key}` | {kinds} | {defaults} |"); + } + sb.AppendLine(); + + sb.AppendLine("## Per-variable detail"); + sb.AppendLine(); + foreach (var g in byName) + { + sb.AppendLine($"### `{g.Key}`"); + sb.AppendLine(); + sb.AppendLine("| Kind | Source | Default / value | Context |"); + sb.AppendLine("| --- | --- | --- | --- |"); + foreach (var v in g) + { + var fallback = string.IsNullOrEmpty(v.FallbackLiteral) ? "" : $"`{v.FallbackLiteral}`"; + sb.AppendLine($"| `{v.Kind}` | [`{v.FileRelativePath}:{v.Line}`](https://github.com/TrakHound/MTConnect.NET/blob/master/{v.FileRelativePath}#L{v.Line}) | {fallback} | {Escape(v.Context)} |"); + } + sb.AppendLine(); + } + + sb.AppendLine("Adding a new `Environment.GetEnvironmentVariable(\"…\")` call, a new `${MTCONNECT_…}` read in a contributor script, or a new `$env:MTCONNECT_…` reference in a PowerShell script without regenerating this page fails the validation test in CI."); + sb.AppendLine(); + return sb.ToString(); + } + + private static string Escape(string s) => s.Replace("|", "\\|").Replace("\n", " ").Replace("\r", " "); +} + +/// +/// Markdown for `docs/reference/cli.md`. +/// +public static class CliRenderer +{ + /// + /// Builds the contents of docs/reference/cli.md from the + /// supplied CLI inventory. + /// + /// CLI tools discovered by + /// . + /// Full markdown text. + public static string Render(IReadOnlyList tools) + { + var sb = new StringBuilder(); + sb.AppendLine(IndexRenderer.AutoGenMarker); + sb.AppendLine(); + sb.AppendLine("# CLI reference"); + sb.AppendLine(); + sb.AppendLine("Every command-line tool the repository exposes — including the shipped `mtconnect.net-agent` + `mtconnect.net-adapter` binaries and the contributor scripts under `tools/` plus the .NET tools under `build/`. The list is built by walking the source tree at docs-build time, so a new flag added to any tool surfaces here on the next regeneration."); + sb.AppendLine(); + + var shipped = tools.Where(t => t.Category == "shipped").ToList(); + var contrib = tools.Where(t => t.Category == "contributor").ToList(); + + sb.AppendLine("## Shipped CLIs"); + sb.AppendLine(); + if (shipped.Count == 0) + { + sb.AppendLine("_No shipped CLIs discovered._"); + sb.AppendLine(); + } + foreach (var t in shipped) RenderOne(sb, t); + + sb.AppendLine("## Contributor CLIs"); + sb.AppendLine(); + if (contrib.Count == 0) + { + sb.AppendLine("_No contributor CLIs discovered._"); + sb.AppendLine(); + } + foreach (var t in contrib) RenderOne(sb, t); + + return sb.ToString(); + } + + private static void RenderOne(StringBuilder sb, CliInfo t) + { + sb.AppendLine($"### `{t.Name}`"); + sb.AppendLine(); + sb.AppendLine($"- **Source**: [`{t.SourceRelativePath}`](https://github.com/TrakHound/MTConnect.NET/blob/master/{t.SourceRelativePath})"); + sb.AppendLine(); + if (!string.IsNullOrEmpty(t.Summary)) + { + sb.AppendLine(t.Summary); + sb.AppendLine(); + } + + if (t.Commands.Count > 0) + { + sb.AppendLine("**Commands**"); + sb.AppendLine(); + sb.AppendLine("| Command | Description |"); + sb.AppendLine("| --- | --- |"); + foreach (var c in t.Commands) + { + sb.AppendLine($"| `{c.Name}` | {Escape(c.Description)} |"); + } + sb.AppendLine(); + } + + if (t.Flags.Count > 0) + { + sb.AppendLine("**Flags**"); + sb.AppendLine(); + sb.AppendLine("| Flag | Short | Argument | Description |"); + sb.AppendLine("| --- | --- | --- | --- |"); + foreach (var f in t.Flags) + { + var sh = string.IsNullOrEmpty(f.Short) ? "" : $"`{f.Short}`"; + var arg = string.IsNullOrEmpty(f.ArgShape) ? "" : $"`{f.ArgShape}`"; + sb.AppendLine($"| `{f.Name}` | {sh} | {arg} | {Escape(f.Description)} |"); + } + sb.AppendLine(); + } + + if (t.Arguments.Count > 0) + { + sb.AppendLine("**Positional arguments**"); + sb.AppendLine(); + sb.AppendLine("| Name | Description |"); + sb.AppendLine("| --- | --- |"); + foreach (var a in t.Arguments) + { + sb.AppendLine($"| `{a.Name}` | {Escape(a.Description)} |"); + } + sb.AppendLine(); + } + } + + // CLI descriptions are plain prose that may include placeholder + // tokens like `` or ``. Markdown leaves those + // tokens untouched, and VitePress's Vue compiler then treats them + // as opening HTML tags that need closing — which breaks the build. + // Escape the angle brackets here so the rendered markdown is + // unambiguous; the `` argument-shape tokens emitted into + // the Argument column are kept inside backticks elsewhere and stay + // literal in their own code spans. + private static string Escape(string s) => s + .Replace("|", "\\|") + .Replace("\n", " ") + .Replace("\r", " ") + .Replace("<", "<") + .Replace(">", ">"); +} + +/// +/// Markdown for `docs/reference/configuration.md`. +/// +public static class ConfigRenderer +{ + /// + /// Builds the contents of docs/reference/configuration.md + /// from the supplied configuration-class inventory. + /// + /// Configuration classes discovered by + /// . + /// Full markdown text. + public static string Render(IReadOnlyList classes) + { + var sb = new StringBuilder(); + sb.AppendLine(IndexRenderer.AutoGenMarker); + sb.AppendLine(); + sb.AppendLine("# Configuration schema"); + sb.AppendLine(); + sb.AppendLine("The agent and adapter accept YAML or JSON configuration. The schema below is derived from the source declarations of every option class — the `JsonPropertyName` / `YamlMember.Alias` value gives the on-the-wire key, and the `///` summary above each property is reproduced verbatim."); + sb.AppendLine(); + sb.AppendLine("## Worked example"); + sb.AppendLine(); + sb.AppendLine("A minimal `agent.config.yaml` for an HTTP agent on port 5000:"); + sb.AppendLine(); + sb.AppendLine("```yaml"); + sb.AppendLine("observationBufferSize: 150000"); + sb.AppendLine("assetBufferSize: 1000"); + sb.AppendLine("defaultVersion: \"2.5\""); + sb.AppendLine("enableAgentDevice: true"); + sb.AppendLine("enableMetrics: true"); + sb.AppendLine(""); + sb.AppendLine("modules:"); + sb.AppendLine(" - http:"); + sb.AppendLine(" port: 5000"); + sb.AppendLine(" documentFormat: xml"); + sb.AppendLine("```"); + sb.AppendLine(); + sb.AppendLine("## Option classes"); + sb.AppendLine(); + foreach (var c in classes) + { + sb.AppendLine($"### `{c.TypeName}`"); + sb.AppendLine(); + sb.AppendLine($"- **Namespace**: `{c.Namespace}`"); + sb.AppendLine($"- **Source**: [`{c.FileRelativePath}`](https://github.com/TrakHound/MTConnect.NET/blob/master/{c.FileRelativePath})"); + sb.AppendLine(); + if (!string.IsNullOrEmpty(c.Summary)) + { + sb.AppendLine(c.Summary); + sb.AppendLine(); + } + sb.AppendLine("| Key | C# property | Type | Description |"); + sb.AppendLine("| --- | --- | --- | --- |"); + foreach (var p in c.Properties) + { + sb.AppendLine($"| `{p.SerialisedKey}` | `{p.Name}` | `{Escape(p.Type)}` | {Escape(p.Summary)} |"); + } + sb.AppendLine(); + } + return sb.ToString(); + } + + private static string Escape(string s) => s.Replace("|", "\\|").Replace("\n", " ").Replace("\r", " "); +} diff --git a/build/MTConnect.NET-DocsGen/RouteInventory.cs b/build/MTConnect.NET-DocsGen/RouteInventory.cs new file mode 100644 index 000000000..79e6e7fad --- /dev/null +++ b/build/MTConnect.NET-DocsGen/RouteInventory.cs @@ -0,0 +1,585 @@ +// Copyright (c) 2026 TrakHound Inc., All Rights Reserved. +// TrakHound Inc. licenses this file to you under the MIT license. + +using Microsoft.CodeAnalysis; +using Microsoft.CodeAnalysis.CSharp; +using Microsoft.CodeAnalysis.CSharp.Syntax; +using System.Text; + +namespace MTConnect.NET_DocsGen; + +/// +/// Describes a single discovered HTTP endpoint. The inventory is +/// produced by Roslyn syntax-only inspection; no semantic model or +/// compiled assembly is required. +/// +public sealed record EndpointInfo( + string Source, // "Ceen" | "AspNetCore" + string Surface, // "Agent" | "Admin" + string Method, // GET / POST / PUT / DELETE / ANY + string PathTemplate, // e.g. "/probe", "/{deviceKey}/sample" + string Handler, // handler class or controller.action + string Summary, // XML-doc summary (may be empty) + IReadOnlyList Parameters, + IReadOnlyList ResponseStatusCodes, + string FileRelativePath, + int Line); + +/// +/// A single query / route / body parameter on an endpoint. +/// +public sealed record EndpointParam( + string Name, + string Kind, // Route / Query / Body / Header + string Type, + string? DefaultValue, + string Summary); + +/// +/// Builds the endpoint inventory by walking every .cs file in the +/// `libraries/MTConnect.NET-HTTP` and `libraries/MTConnect.NET-HTTP-AspNetCore` +/// trees. Two collectors run side by side and emit a single +/// deterministic ordered list: +/// +/// 1. Ceen routes — `serverConfig.AddRoute("/path", handler)` +/// 2. AspNetCore controllers — `[HttpGet("/path")]` etc. +/// +public static class RouteInventory +{ + /// + /// Walks the Ceen and AspNetCore source trees under + /// and returns the union of HTTP + /// endpoints discovered. Output is deterministically sorted by + /// source, method, path, handler. + /// + /// Repository root. + /// Ordered list of endpoints. + public static IReadOnlyList Collect(string repoRoot) + { + var results = new List(); + + var ceenRoot = Path.Combine(repoRoot, "libraries", "MTConnect.NET-HTTP"); + var aspNetRoot = Path.Combine(repoRoot, "libraries", "MTConnect.NET-HTTP-AspNetCore"); + + if (Directory.Exists(ceenRoot)) + { + CollectCeen(ceenRoot, repoRoot, results); + } + if (Directory.Exists(aspNetRoot)) + { + CollectAspNetCore(aspNetRoot, repoRoot, results); + } + + // Deterministic sort: source, then method, then path. + return results + .OrderBy(e => e.Source, StringComparer.Ordinal) + .ThenBy(e => e.Method, StringComparer.Ordinal) + .ThenBy(e => e.PathTemplate, StringComparer.Ordinal) + .ThenBy(e => e.Handler, StringComparer.Ordinal) + .ToList(); + } + + // ----- Ceen --------------------------------------------------------- + + private static void CollectCeen(string root, string repoRoot, List sink) + { + var serverFile = Path.Combine(root, "Servers", "MTConnectHttpServer.cs"); + if (!File.Exists(serverFile)) return; + + var text = File.ReadAllText(serverFile); + var tree = CSharpSyntaxTree.ParseText(text, path: serverFile); + var rel = Path.GetRelativePath(repoRoot, serverFile).Replace('\\', '/'); + + foreach (var inv in tree.GetRoot() + .DescendantNodes() + .OfType()) + { + if (inv.Expression is not MemberAccessExpressionSyntax member) continue; + if (member.Name.Identifier.ValueText != "AddRoute") continue; + + var args = inv.ArgumentList.Arguments; + // Only the `AddRoute(string, handler)` overload yields a + // user-visible path template. The handler-only overloads + // are dispatchers (e.g. PUT/POST/device-root) that gate by + // method/host inside the closure — we surface those by + // inspecting the closure body separately below. + if (args.Count == 2 && + args[0].Expression is LiteralExpressionSyntax lit && + lit.IsKind(SyntaxKind.StringLiteralExpression)) + { + var path = lit.Token.ValueText; + var handler = ExtractIdentifier(args[1].Expression); + var (summary, method, paramList, statuses) = LookupHandlerMetadata(handler, root); + sink.Add(new EndpointInfo( + Source: "Ceen", + Surface: "Agent", + Method: method, + PathTemplate: NormalisePath(path), + Handler: handler, + Summary: summary, + Parameters: paramList, + ResponseStatusCodes: statuses, + FileRelativePath: rel, + Line: lit.GetLocation().GetLineSpan().StartLinePosition.Line + 1)); + } + else if (args.Count == 1 && + args[0].Expression is ParenthesizedLambdaExpressionSyntax lambda) + { + // Method-gating dispatcher closures: surface as ANY of + // the gated method on "*" so the table still shows them. + var (gateMethod, targetHandler) = SniffLambdaGate(lambda); + if (gateMethod is not null) + { + sink.Add(new EndpointInfo( + Source: "Ceen", + Surface: "Agent", + Method: gateMethod, + PathTemplate: "(any)", + Handler: targetHandler ?? "(dispatcher)", + Summary: "Method-gated dispatcher; routes the request to the handler matching the request method.", + Parameters: Array.Empty(), + ResponseStatusCodes: Array.Empty(), + FileRelativePath: rel, + Line: lambda.GetLocation().GetLineSpan().StartLinePosition.Line + 1)); + } + } + } + } + + private static (string? method, string? handler) SniffLambdaGate(ParenthesizedLambdaExpressionSyntax lambda) + { + // Look for an invocation like `await DeviceRootHandler(probeHandler, context)` + // and a comparison `httpRequest.Method == HttpMethod.Put.Method` in the + // referenced helper. We can't easily resolve cross-method without a + // semantic model, so just check the lambda body text. + var bodyText = lambda.Body.ToString(); + string? method = null; + if (bodyText.Contains("PutHandler", StringComparison.Ordinal)) method = "PUT"; + else if (bodyText.Contains("PostHandler", StringComparison.Ordinal)) method = "POST"; + else if (bodyText.Contains("DeviceRootHandler", StringComparison.Ordinal)) method = "GET"; + + string? handler = null; + foreach (var word in new[] { "putHandler", "postHandler", "probeHandler", "currentHandler", "sampleHandler", "assetsHandler", "assetHandler" }) + { + if (bodyText.Contains(word, StringComparison.Ordinal)) { handler = word; break; } + } + + return (method, handler); + } + + private static string ExtractIdentifier(ExpressionSyntax expr) => expr switch + { + IdentifierNameSyntax id => id.Identifier.ValueText, + MemberAccessExpressionSyntax m => m.Name.Identifier.ValueText, + _ => expr.ToString() + }; + + // Map from Ceen handler-variable identifier (as it appears at the + // AddRoute call site) to the concrete handler class name. The class + // names are structural and stable; the route table lives in source + // and would be tedious to re-derive via lexical-scope analysis + // without a semantic model. The summary text, by contrast, is read + // straight out of each handler class's /// doc-comment. + private static readonly IReadOnlyDictionary CeenHandlerTypeNames = new Dictionary + { + ["probeHandler"] = "MTConnectProbeResponseHandler", + ["currentHandler"] = "MTConnectCurrentResponseHandler", + ["sampleHandler"] = "MTConnectSampleResponseHandler", + ["assetsHandler"] = "MTConnectAssetsResponseHandler", + ["assetHandler"] = "MTConnectAssetResponseHandler", + ["staticHandler"] = "MTConnectStaticResponseHandler", + ["putHandler"] = "MTConnectPutResponseHandler", + ["postHandler"] = "MTConnectPostResponseHandler", + }; + + // HTTP method per handler class. Ceen routes the method-gated + // dispatcher closures into PUT/POST handlers regardless of the + // AddRoute path, so the method is a property of the handler class + // itself (not the AddRoute call). + private static readonly IReadOnlyDictionary CeenHandlerMethods = new Dictionary + { + ["MTConnectProbeResponseHandler"] = "GET", + ["MTConnectCurrentResponseHandler"] = "GET", + ["MTConnectSampleResponseHandler"] = "GET", + ["MTConnectAssetsResponseHandler"] = "GET", + ["MTConnectAssetResponseHandler"] = "GET", + ["MTConnectStaticResponseHandler"] = "GET", + ["MTConnectPutResponseHandler"] = "PUT", + ["MTConnectPostResponseHandler"] = "POST", + }; + + // Parameter shapes per handler class. Ceen parses query parameters + // imperatively inside OnRequestReceived, so the surface is encoded + // structurally here to give the reference page meaningful columns; + // the *summary text* still flows from /// on the handler class. + private static readonly IReadOnlyDictionary> CeenHandlerParameters + = new Dictionary> + { + ["MTConnectProbeResponseHandler"] = new EndpointParam[] + { + new("deviceType", "Query", "string", null, "Optional device-type filter."), + new("version", "Query", "string", null, "Target MTConnect Standard version of the response document."), + new("documentFormat", "Query", "string", "xml", "Response document format (xml | json | json-cppagent)."), + new("validationLevel", "Query", "int", null, "0=ignore, 1=warning, 2=remove, 3=strict."), + new("indentOutput", "Query", "bool", null, "Pretty-print the response document."), + new("outputComments", "Query", "bool", null, "Emit comments / annotations in the response document."), + }, + ["MTConnectCurrentResponseHandler"] = new EndpointParam[] + { + new("path", "Query", "string", null, "XPath that filters the data items included in the response."), + new("at", "Query", "ulong", null, "Sequence number anchoring the snapshot."), + new("interval", "Query", "int", null, "Streaming interval in milliseconds; switches to multipart streaming when > 0."), + new("heartbeat", "Query", "int", "10000", "Heartbeat interval for the streaming response."), + new("deviceType", "Query", "string", null, "Optional device-type filter."), + new("version", "Query", "string", null, "Target MTConnect Standard version of the response document."), + new("documentFormat", "Query", "string", "xml", "Response document format."), + new("indentOutput", "Query", "bool", null, "Pretty-print the response document."), + new("outputComments", "Query", "bool", null, "Emit comments / annotations in the response document."), + }, + ["MTConnectSampleResponseHandler"] = new EndpointParam[] + { + new("path", "Query", "string", null, "XPath that filters the data items included in the response."), + new("from", "Query", "ulong", null, "Sequence number lower bound."), + new("to", "Query", "ulong", null, "Sequence number upper bound."), + new("count", "Query", "int", "100", "Maximum number of observations."), + new("interval", "Query", "int", null, "Streaming interval in milliseconds; switches to multipart streaming when > 0."), + new("heartbeat", "Query", "int", "10000", "Heartbeat interval for the streaming response."), + new("deviceType", "Query", "string", null, "Optional device-type filter."), + new("version", "Query", "string", null, "Target MTConnect Standard version of the response document."), + new("documentFormat", "Query", "string", "xml", "Response document format."), + new("indentOutput", "Query", "bool", null, "Pretty-print the response document."), + new("outputComments", "Query", "bool", null, "Emit comments / annotations in the response document."), + }, + ["MTConnectAssetsResponseHandler"] = new EndpointParam[] + { + new("type", "Query", "string", null, "Asset type filter (e.g. CuttingTool)."), + new("removed", "Query", "bool", null, "Include removed assets when true."), + new("count", "Query", "int", null, "Maximum number of assets."), + new("documentFormat", "Query", "string", "xml", "Response document format."), + new("indentOutput", "Query", "bool", null, "Pretty-print the response document."), + }, + ["MTConnectAssetResponseHandler"] = new EndpointParam[] + { + new("assetId", "Route", "string", null, "Asset identifier captured from the trailing path segment."), + new("documentFormat", "Query", "string", "xml", "Response document format."), + }, + ["MTConnectPutResponseHandler"] = new EndpointParam[] + { + new("(form / query)", "Body", "Dictionary", null, "DataItemId=Value entries to enqueue as observations."), + }, + ["MTConnectPostResponseHandler"] = new EndpointParam[] + { + new("(body)", "Body", "string", null, "Asset document payload."), + }, + }; + + // Cache of parsed /// summary text per handler-class file path, so + // we only Roslyn-parse each file once even though several variables + // (probeHandler, the AddRoute("/", probeHandler) alias, etc.) all + // resolve back to the same class. + private static readonly Dictionary _ceenSummaryCache = new(StringComparer.Ordinal); + + /// + /// Builds the per-endpoint metadata triple for a single Ceen + /// AddRoute call. The HTTP method and the parameter shape are + /// structural properties of the handler class and are encoded + /// statically. The free-text summary, however, is parsed straight + /// out of the handler class's `///` doc-comment via Roslyn — so the + /// docs site stays in lock-step with whatever the handler classes + /// say about themselves. + /// + private static (string Summary, string Method, IReadOnlyList Params, IReadOnlyList Statuses) + LookupHandlerMetadata(string handlerVarName, string ceenRoot) + { + if (!CeenHandlerTypeNames.TryGetValue(handlerVarName, out var typeName)) + { + typeName = handlerVarName; + } + + var method = CeenHandlerMethods.TryGetValue(typeName, out var m) ? m : "ANY"; + + var summary = ReadCeenHandlerSummary(typeName, ceenRoot); + + var parameters = CeenHandlerParameters.TryGetValue(typeName, out var ps) + ? ps + : Array.Empty(); + + IReadOnlyList statuses = method == "ANY" + ? Array.Empty() + : new[] { "200", "400", "404", "406", "500" }; + + return (summary, method, parameters, statuses); + } + + private static string ReadCeenHandlerSummary(string typeName, string ceenRoot) + { + var path = Path.Combine(ceenRoot, "Servers", typeName + ".cs"); + if (_ceenSummaryCache.TryGetValue(path, out var cached)) return cached; + + if (!File.Exists(path)) + { + _ceenSummaryCache[path] = string.Empty; + return string.Empty; + } + + var text = File.ReadAllText(path); + var tree = CSharpSyntaxTree.ParseText(text, path: path); + var cls = tree.GetRoot() + .DescendantNodes() + .OfType() + .FirstOrDefault(c => c.Identifier.ValueText == typeName); + + if (cls is null) + { + _ceenSummaryCache[path] = string.Empty; + return string.Empty; + } + + var trivia = cls.GetLeadingTrivia() + .FirstOrDefault(t => t.IsKind(SyntaxKind.SingleLineDocumentationCommentTrivia) + || t.IsKind(SyntaxKind.MultiLineDocumentationCommentTrivia)); + if (trivia == default || trivia.GetStructure() is not DocumentationCommentTriviaSyntax dox) + { + _ceenSummaryCache[path] = string.Empty; + return string.Empty; + } + + var summary = dox.Content.OfType() + .FirstOrDefault(e => e.StartTag.Name.LocalName.ValueText == "summary"); + if (summary is null) + { + _ceenSummaryCache[path] = string.Empty; + return string.Empty; + } + + var sb = new StringBuilder(); + foreach (var node in summary.Content) sb.Append(node.ToString()); + var result = CleanXmlText(sb.ToString()); + + _ceenSummaryCache[path] = result; + return result; + } + + private static string NormalisePath(string p) => + p.Length == 0 ? "/" : p; + + // ----- AspNetCore --------------------------------------------------- + + private static void CollectAspNetCore(string root, string repoRoot, List sink) + { + var controllersDir = Path.Combine(root, "Http", "Controllers"); + if (!Directory.Exists(controllersDir)) return; + + foreach (var file in Directory.GetFiles(controllersDir, "*.cs")) + { + var text = File.ReadAllText(file); + var rel = Path.GetRelativePath(repoRoot, file).Replace('\\', '/'); + var tree = CSharpSyntaxTree.ParseText(text, path: file); + + foreach (var cls in tree.GetRoot().DescendantNodes().OfType()) + { + if (!IsApiController(cls)) continue; + + var basePath = ExtractRoute(cls.AttributeLists); + + foreach (var method in cls.Members.OfType()) + { + var httpAttrs = method.AttributeLists + .SelectMany(al => al.Attributes) + .Where(a => IsHttpAttr(a, out _)) + .ToList(); + if (httpAttrs.Count == 0) continue; + + var summary = ExtractXmlSummary(method); + var parameters = ExtractParameters(method); + var statuses = ExtractResponseStatuses(method); + + foreach (var attr in httpAttrs) + { + IsHttpAttr(attr, out var verb); + var sub = ExtractFirstStringArg(attr); + var full = Combine(basePath, sub); + + sink.Add(new EndpointInfo( + Source: "AspNetCore", + Surface: "Agent", + Method: verb!, + PathTemplate: full, + Handler: $"{cls.Identifier.ValueText}.{method.Identifier.ValueText}", + Summary: summary, + Parameters: parameters, + ResponseStatusCodes: statuses, + FileRelativePath: rel, + Line: attr.GetLocation().GetLineSpan().StartLinePosition.Line + 1)); + } + } + } + } + } + + private static bool IsApiController(ClassDeclarationSyntax cls) + { + foreach (var al in cls.AttributeLists) + { + foreach (var a in al.Attributes) + { + if (a.Name.ToString() == "ApiController") return true; + } + } + return false; + } + + private static string ExtractRoute(SyntaxList attrs) + { + foreach (var al in attrs) + { + foreach (var a in al.Attributes) + { + if (a.Name.ToString() != "Route") continue; + return ExtractFirstStringArg(a) ?? string.Empty; + } + } + return string.Empty; + } + + private static bool IsHttpAttr(AttributeSyntax a, out string? verb) + { + var name = a.Name.ToString(); + verb = name switch + { + "HttpGet" => "GET", + "HttpPost" => "POST", + "HttpPut" => "PUT", + "HttpDelete" => "DELETE", + "HttpPatch" => "PATCH", + _ => null + }; + return verb is not null; + } + + private static string? ExtractFirstStringArg(AttributeSyntax a) + { + if (a.ArgumentList is null) return null; + var first = a.ArgumentList.Arguments.FirstOrDefault(); + if (first?.Expression is LiteralExpressionSyntax lit && + lit.IsKind(SyntaxKind.StringLiteralExpression)) + { + return lit.Token.ValueText; + } + return null; + } + + private static string Combine(string basePath, string? sub) + { + var b = basePath.TrimEnd('/'); + if (string.IsNullOrEmpty(sub)) return string.IsNullOrEmpty(b) ? "/" : b; + var s = sub.TrimStart('/'); + if (string.IsNullOrEmpty(b)) return "/" + s; + return b + "/" + s; + } + + private static string ExtractXmlSummary(MethodDeclarationSyntax method) + { + var trivia = method.GetLeadingTrivia() + .FirstOrDefault(t => t.IsKind(SyntaxKind.SingleLineDocumentationCommentTrivia) + || t.IsKind(SyntaxKind.MultiLineDocumentationCommentTrivia)); + if (trivia == default) return string.Empty; + + var structure = trivia.GetStructure() as DocumentationCommentTriviaSyntax; + if (structure is null) return string.Empty; + + var summary = structure.Content.OfType() + .FirstOrDefault(e => e.StartTag.Name.LocalName.ValueText == "summary"); + if (summary is null) return string.Empty; + + var sb = new StringBuilder(); + foreach (var node in summary.Content) + { + sb.Append(node.ToString()); + } + return CleanXmlText(sb.ToString()); + } + + private static IReadOnlyList ExtractParameters(MethodDeclarationSyntax method) + { + // Parameter summaries are in the .. nodes + // sitting alongside . + var paramSummaries = new Dictionary(StringComparer.Ordinal); + var trivia = method.GetLeadingTrivia() + .FirstOrDefault(t => t.IsKind(SyntaxKind.SingleLineDocumentationCommentTrivia) + || t.IsKind(SyntaxKind.MultiLineDocumentationCommentTrivia)); + if (trivia != default && trivia.GetStructure() is DocumentationCommentTriviaSyntax dox) + { + foreach (var el in dox.Content.OfType()) + { + if (el.StartTag.Name.LocalName.ValueText != "param") continue; + var nameAttr = el.StartTag.Attributes.OfType().FirstOrDefault(); + if (nameAttr is null) continue; + var name = nameAttr.Identifier.Identifier.ValueText; + var sb = new StringBuilder(); + foreach (var node in el.Content) sb.Append(node.ToString()); + paramSummaries[name] = CleanXmlText(sb.ToString()); + } + } + + var results = new List(); + if (method.ParameterList is null) return results; + + foreach (var p in method.ParameterList.Parameters) + { + string kind = "Query"; + foreach (var al in p.AttributeLists) + { + foreach (var a in al.Attributes) + { + var n = a.Name.ToString(); + if (n == "FromRoute") kind = "Route"; + else if (n == "FromQuery") kind = "Query"; + else if (n == "FromBody") kind = "Body"; + else if (n == "FromHeader") kind = "Header"; + } + } + var def = p.Default?.Value.ToString(); + paramSummaries.TryGetValue(p.Identifier.ValueText, out var summary); + results.Add(new EndpointParam( + Name: p.Identifier.ValueText, + Kind: kind, + Type: p.Type?.ToString() ?? "object", + DefaultValue: def, + Summary: summary ?? string.Empty)); + } + return results; + } + + private static IReadOnlyList ExtractResponseStatuses(MethodDeclarationSyntax method) + { + var results = new List(); + foreach (var al in method.AttributeLists) + { + foreach (var a in al.Attributes) + { + if (a.Name.ToString() != "ProducesResponseType") continue; + var arg = a.ArgumentList?.Arguments.FirstOrDefault()?.Expression?.ToString(); + if (string.IsNullOrEmpty(arg)) continue; + // "StatusCodes.Status200OK" -> "200" + var lastDot = arg.LastIndexOf('.'); + var token = lastDot >= 0 ? arg[(lastDot + 1)..] : arg; + var digits = new string(token.Where(char.IsDigit).ToArray()); + if (digits.Length > 0) results.Add(digits); + } + } + return results.Distinct().OrderBy(s => s, StringComparer.Ordinal).ToList(); + } + + private static string CleanXmlText(string raw) + { + var lines = raw.Split('\n') + .Select(l => l.TrimStart().TrimStart('/').TrimStart()) + .Where(l => l.Length > 0); + var joined = string.Join(' ', lines).Trim(); + // Collapse double spaces. + while (joined.Contains(" ", StringComparison.Ordinal)) + joined = joined.Replace(" ", " "); + return joined; + } +} diff --git a/build/MTConnect.NET-SysML-Import/CSharp/ComponentType.cs b/build/MTConnect.NET-SysML-Import/CSharp/ComponentType.cs index d78dcc663..20c6fb259 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/ComponentType.cs +++ b/build/MTConnect.NET-SysML-Import/CSharp/ComponentType.cs @@ -1,26 +1,70 @@ -using MTConnect.NET_SysML_Import.CSharp; +using MTConnect.NET_SysML_Import.CSharp; using MTConnect.SysML.Models.Devices; using MTConnect.SysML.Xmi; using MTConnect.SysML.Xmi.UML; namespace MTConnect.SysML.CSharp { + /// + /// Template model for an MTConnect ComponentType. Wraps the + /// SysML-import with the + /// C#-emitter-only properties needed by the Scriban template + /// (namespace, XML description, version enums) and exposes the + /// render hooks. + /// public class ComponentType : MTConnectComponentType, ITemplateModel { + /// + /// C# namespace the generated type belongs to. Derived from + /// the SysML identifier via . + /// public string Namespace => NamespaceHelper.GetNamespace(Id); + /// + /// XML-formatted description (XML doc-comment shape) emitted + /// directly into the Scriban template. + /// public string XmlDescription { get; set; } + /// + /// SysML MaximumVersion mapped to the C# enum value + /// emitted by . + /// public string MaximumVersionEnum => MTConnectVersion.GetVersionEnum(MaximumVersion); + /// + /// SysML MinimumVersion mapped to the C# enum value + /// emitted by . + /// public string MinimumVersionEnum => MTConnectVersion.GetVersionEnum(MinimumVersion); + /// + /// Parameterless constructor used by the import pipeline when + /// it copies properties off an existing + /// via reflection. + /// public ComponentType() { } + /// + /// Constructs a model directly from an XMI document tree by + /// delegating to the base type's constructor. + /// + /// Source XMI document. + /// Identifier prefix applied to the + /// rendered type. + /// Backing UML class. public ComponentType(XmiDocument xmiDocument, string idPrefix, UmlClass umlClass) : base (xmiDocument, idPrefix, umlClass) { } + /// + /// Copies every matching property off + /// into a fresh . Returns null + /// when the input is null. Used by the SysML import pipeline to + /// convert generic models into emitter-aware models. + /// + /// Generic SysML-import model. + /// Emitter-aware model, or null. public static ComponentType Create(MTConnectComponentType importModel) { if (importModel != null) @@ -59,14 +103,17 @@ public static ComponentType Create(MTConnectComponentType importModel) } + /// public string RenderModel() { var template = TemplateLoader.LoadOrThrow("CSharp", "Templates", "Devices.ComponentType.scriban"); return template.Render(this); } + /// public string RenderInterface() => null; + /// public string RenderDescriptions() => null; } } diff --git a/build/MTConnect.NET-SysML-Import/CSharp/CompositionType.cs b/build/MTConnect.NET-SysML-Import/CSharp/CompositionType.cs index 2f099583a..22a8b4e7b 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/CompositionType.cs +++ b/build/MTConnect.NET-SysML-Import/CSharp/CompositionType.cs @@ -5,22 +5,48 @@ namespace MTConnect.SysML.CSharp { + /// + /// Template model for an MTConnect CompositionType. Same + /// shape as but backed by a SysML + /// enumeration literal rather than a UML class. + /// public class CompositionType : MTConnectCompositionType, ITemplateModel { + /// C# namespace the generated type belongs to. public string Namespace => NamespaceHelper.GetNamespace(Id); + /// XML-formatted description (XML doc-comment shape). public string XmlDescription { get; set; } + /// SysML MaximumVersion mapped to a C# enum value. public string MaximumVersionEnum => MTConnectVersion.GetVersionEnum(MaximumVersion); + /// SysML MinimumVersion mapped to a C# enum value. public string MinimumVersionEnum => MTConnectVersion.GetVersionEnum(MinimumVersion); + /// Parameterless constructor used by the reflection-based + /// factory. public CompositionType() { } + /// + /// Constructs a model directly from an XMI document tree. + /// + /// Source XMI document. + /// Identifier prefix applied to the + /// rendered type. + /// Backing UML enumeration + /// literal. public CompositionType(XmiDocument xmiDocument, string idPrefix, UmlEnumerationLiteral umlEnumerationLiteral) : base (xmiDocument, idPrefix, umlEnumerationLiteral) { } + /// + /// Copies every matching property off + /// into a fresh . Returns + /// null when the input is null. + /// + /// Generic SysML-import model. + /// Emitter-aware model, or null. public static CompositionType Create(MTConnectCompositionType importModel) { if (importModel != null) @@ -59,14 +85,17 @@ public static CompositionType Create(MTConnectCompositionType importModel) } + /// public string RenderModel() { var template = TemplateLoader.LoadOrThrow("CSharp", "Templates", "Devices.CompositionType.scriban"); return template.Render(this); } + /// public string RenderInterface() => null; + /// public string RenderDescriptions() => null; } } diff --git a/build/MTConnect.NET-SysML-Import/CSharp/CuttingToolMeasurementModel.cs b/build/MTConnect.NET-SysML-Import/CSharp/CuttingToolMeasurementModel.cs index e844cc8c4..97217c033 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/CuttingToolMeasurementModel.cs +++ b/build/MTConnect.NET-SysML-Import/CSharp/CuttingToolMeasurementModel.cs @@ -1,15 +1,30 @@ -using MTConnect.NET_SysML_Import.CSharp; +using MTConnect.NET_SysML_Import.CSharp; using MTConnect.SysML.Models.Assets; namespace MTConnect.SysML.CSharp { + /// + /// Template model for an MTConnect CuttingToolMeasurement + /// asset measurement. Carries the C#-emitter-only properties + /// (namespace, XML description) Scriban needs to render the + /// measurement's *.g.cs output. + /// public class CuttingToolMeasurementModel : MTConnectMeasurementModel, ITemplateModel { + /// C# namespace the generated type belongs to. public string Namespace => NamespaceHelper.GetNamespace(Id); + /// XML-formatted description (XML doc-comment shape). public string XmlDescription { get; set; } + /// + /// Copies every matching property off + /// into a fresh . + /// Returns null when the input is null. + /// + /// Generic SysML-import model. + /// Emitter-aware model, or null. public static CuttingToolMeasurementModel Create(MTConnectMeasurementModel importModel) { if (importModel != null) @@ -44,14 +59,17 @@ public static CuttingToolMeasurementModel Create(MTConnectMeasurementModel impor return null; } + /// public string RenderModel() { var template = TemplateLoader.LoadOrThrow("CSharp", "Templates", "Assets.CuttingToolMeasurement.scriban"); return template.Render(this); } + /// public string RenderInterface() => null; + /// public string RenderDescriptions() => null; } } diff --git a/build/MTConnect.NET-SysML-Import/CSharp/DataItemType.cs b/build/MTConnect.NET-SysML-Import/CSharp/DataItemType.cs index cd87f19ec..83b70541a 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/DataItemType.cs +++ b/build/MTConnect.NET-SysML-Import/CSharp/DataItemType.cs @@ -8,29 +8,79 @@ namespace MTConnect.SysML.CSharp { + /// + /// Template model for an MTConnect DataItemType. Carries + /// the C#-emitter-only properties (namespace, units enum, version + /// enums, default short name) Scriban needs to render the + /// *.g.cs data-item type and its descriptions companion. + /// public class DataItemType : MTConnectDataItemType, ITemplateModel { + /// C# namespace the generated type belongs to. public string Namespace => NamespaceHelper.GetNamespace(Id); + /// XML-formatted description (XML doc-comment shape). public string XmlDescription { get; set; } + /// + /// Short-form name used for camel-case Property output; maps a + /// handful of well-known types to their canonical short names + /// (e.g. EMERGENCY_STOP → estop). + /// public string DefaultName => GetName(Type); + /// Fully-qualified Units enum value emitted into the + /// Scriban template, e.g. Devices.CELSIUS. public string UnitsEnum => Units != null ? $"Devices.{Units}" : null; + /// SysML MaximumVersion mapped to a C# enum + /// value. public string MaximumVersionEnum => MTConnectVersion.GetVersionEnum(MaximumVersion); + /// SysML MinimumVersion mapped to a C# enum + /// value. public string MinimumVersionEnum => MTConnectVersion.GetVersionEnum(MinimumVersion); + /// + /// Result type for Sample / TimeSeries / DataSet / Table / + /// Event data items, with the SysML Enum suffix + /// stripped (e.g. EVENT_VALUE → EVENT_VALUE). + /// public string ResultType { get; set; } + /// Parameterless constructor used by the reflection- + /// based factory. public DataItemType() { } + /// + /// Constructs a model directly from an XMI document tree. + /// + /// Source XMI document. + /// Data-item category (Sample / + /// Event / Condition). + /// Identifier prefix applied to the + /// rendered type. + /// Backing UML class. + /// Backing UML enumeration + /// literal. + /// Optional sub-classes that derive + /// from . public DataItemType(XmiDocument xmiDocument, string category, string idPrefix, UmlClass umlClass, UmlEnumerationLiteral umlEnumerationLiteral, IEnumerable subClasses = null) : base (xmiDocument, category, idPrefix, umlClass, umlEnumerationLiteral, subClasses) { } + /// + /// Copies every matching property off + /// into a fresh and applies a few + /// data-item-specific fix-ups: normalises the Units enum + /// reference, suffixes the Id / Name / ParentName with + /// DataItem, and lifts the Result type via + /// . Returns + /// null when the input is null. + /// + /// Generic SysML-import model. + /// Emitter-aware model, or null. public static DataItemType Create(MTConnectDataItemType importModel) { if (importModel != null) @@ -91,14 +141,17 @@ public static DataItemType Create(MTConnectDataItemType importModel) } + /// public virtual string RenderModel() { var template = TemplateLoader.LoadOrThrow("CSharp", "Templates", "Devices.DataItemType.scriban"); return template.Render(this); } + /// public string RenderInterface() => null; + /// public string RenderDescriptions() => null; diff --git a/build/MTConnect.NET-SysML-Import/CSharp/DataSetResultModel.cs b/build/MTConnect.NET-SysML-Import/CSharp/DataSetResultModel.cs index 1e65a5efe..fbec9dbf1 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/DataSetResultModel.cs +++ b/build/MTConnect.NET-SysML-Import/CSharp/DataSetResultModel.cs @@ -5,13 +5,28 @@ namespace MTConnect.SysML.CSharp { + /// + /// Template model for an MTConnect DataSet result-type + /// entry. Renders the keys-and-values shape used by Sample / Event + /// data items whose result type is a DataSet. + /// public class DataSetResultModel : MTConnectClassModel, ITemplateModel { + /// C# namespace the generated type belongs to. public string Namespace => NamespaceHelper.GetNamespace(Id); + /// XML-formatted description (XML doc-comment shape). public string XmlDescription { get; set; } + /// + /// Copies every matching property off + /// into a fresh and strips the + /// SysML Enum suffix from every property's + /// DataType. Returns null when the input is null. + /// + /// Generic SysML-import model. + /// Emitter-aware model, or null. public static DataSetResultModel Create(MTConnectClassModel importModel) { if (importModel != null) @@ -55,14 +70,17 @@ public static DataSetResultModel Create(MTConnectClassModel importModel) return null; } + /// public string RenderModel() { var template = TemplateLoader.LoadOrThrow("CSharp", "Templates", "Observations.DataSetResults.scriban"); return template.Render(this); } + /// public string RenderInterface() => null; + /// public string RenderDescriptions() => null; } } diff --git a/build/MTConnect.NET-SysML-Import/CSharp/ITemplateModel.cs b/build/MTConnect.NET-SysML-Import/CSharp/ITemplateModel.cs index f98b9919e..d6f743479 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/ITemplateModel.cs +++ b/build/MTConnect.NET-SysML-Import/CSharp/ITemplateModel.cs @@ -1,14 +1,37 @@ namespace MTConnect.SysML.CSharp { + /// + /// Contract every C# template model implements. Each model owns + /// the Scriban rendering of one MTConnect SysML concept and emits + /// three artefacts: the concrete class, the matching interface, + /// and a descriptions companion class. + /// public interface ITemplateModel { + /// + /// Identifier of the concept being rendered (matches the + /// SysML element's xmi:id). + /// string Id { get; } + /// + /// Returns the rendered C# class body. + /// + /// C# source text. string RenderModel(); + /// + /// Returns the rendered C# interface body. + /// + /// C# source text. string RenderInterface(); + /// + /// Returns the rendered C# *Descriptions companion + /// class body. + /// + /// C# source text. string RenderDescriptions(); } } diff --git a/build/MTConnect.NET-SysML-Import/CSharp/InterfaceDataItemType.cs b/build/MTConnect.NET-SysML-Import/CSharp/InterfaceDataItemType.cs index cd363caf6..3f63f3393 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/InterfaceDataItemType.cs +++ b/build/MTConnect.NET-SysML-Import/CSharp/InterfaceDataItemType.cs @@ -8,14 +8,42 @@ namespace MTConnect.SysML.CSharp { + /// + /// Template model for an MTConnect interface-tier data-item type. + /// Derives from and renders against a + /// dedicated Scriban template so interface-level data items can + /// carry slightly different shape than core data items. + /// public class InterfaceDataItemType : DataItemType { + /// Parameterless constructor used by the reflection- + /// based factory. public InterfaceDataItemType() { } + /// + /// Constructs a model directly from an XMI document tree by + /// delegating to the base constructor. + /// + /// Source XMI document. + /// Data-item category. + /// Identifier prefix. + /// Backing UML class. + /// Backing enumeration + /// literal. + /// Optional sub-classes. public InterfaceDataItemType(XmiDocument xmiDocument, string category, string idPrefix, UmlClass umlClass, UmlEnumerationLiteral umlEnumerationLiteral, IEnumerable subClasses = null) : base (xmiDocument, category, idPrefix, umlClass, umlEnumerationLiteral, subClasses) { } + /// + /// Copies every matching property off + /// into a fresh and applies + /// the same Id / Name / ParentName DataItem-suffix fix-up + /// as the parent factory. Returns null when the input is + /// null. + /// + /// Generic SysML-import model. + /// Emitter-aware model, or null. public static InterfaceDataItemType Create(MTConnectInterfaceDataItemType importModel) { if (importModel != null) @@ -61,14 +89,17 @@ public static InterfaceDataItemType Create(MTConnectInterfaceDataItemType import return null; } + /// public override string RenderModel() { var template = TemplateLoader.LoadOrThrow("CSharp", "Templates", "Interfaces.InterfaceDataItemType.scriban"); return template.Render(this); } + /// public string RenderInterface() => null; + /// public string RenderDescriptions() => null; } } diff --git a/build/MTConnect.NET-SysML-Import/CSharp/MeasurementModel.cs b/build/MTConnect.NET-SysML-Import/CSharp/MeasurementModel.cs index 8755c9a2e..5ac65a18f 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/MeasurementModel.cs +++ b/build/MTConnect.NET-SysML-Import/CSharp/MeasurementModel.cs @@ -3,13 +3,27 @@ namespace MTConnect.SysML.CSharp { + /// + /// Template model for an MTConnect pallet-asset measurement. + /// Sibling to ; uses the + /// Pallets.Measurement.scriban template instead. + /// public class MeasurementModel : MTConnectMeasurementModel, ITemplateModel { + /// C# namespace the generated type belongs to. public string Namespace => NamespaceHelper.GetNamespace(Id); + /// XML-formatted description (XML doc-comment shape). public string XmlDescription { get; set; } + /// + /// Copies every matching property off + /// into a fresh . Returns + /// null when the input is null. + /// + /// Generic SysML-import model. + /// Emitter-aware model, or null. public static MeasurementModel Create(MTConnectMeasurementModel importModel) { if (importModel != null) @@ -44,14 +58,17 @@ public static MeasurementModel Create(MTConnectMeasurementModel importModel) return null; } + /// public string RenderModel() { var template = TemplateLoader.LoadOrThrow("CSharp", "Templates", "Pallets.Measurement.scriban"); return template.Render(this); } + /// public string RenderInterface() => null; + /// public string RenderDescriptions() => null; } } diff --git a/build/MTConnect.NET-SysML-Import/CSharp/ObservationModel.cs b/build/MTConnect.NET-SysML-Import/CSharp/ObservationModel.cs index e5d1a9af7..b788e2a0a 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/ObservationModel.cs +++ b/build/MTConnect.NET-SysML-Import/CSharp/ObservationModel.cs @@ -4,13 +4,27 @@ namespace MTConnect.SysML.CSharp { + /// + /// Template model for the MTConnect observation-tier enumeration + /// types (Event values, Condition states, …). Renders both the + /// enum body and an accompanying Descriptions companion. + /// public class ObservationModel : MTConnectObservationModel, ITemplateModel { + /// C# namespace the generated type belongs to. public string Namespace => NamespaceHelper.GetNamespace(Id); + /// XML-formatted description (XML doc-comment shape). public string XmlDescription { get; set; } + /// + /// Copies every matching property off + /// into a fresh . Returns + /// null when the input is null. + /// + /// Generic SysML-import model. + /// Emitter-aware model, or null. public static ObservationModel Create(MTConnectObservationModel importModel) { if (importModel != null) @@ -45,14 +59,17 @@ public static ObservationModel Create(MTConnectObservationModel importModel) return null; } + /// public string RenderModel() { var template = TemplateLoader.LoadOrThrow("CSharp", "Templates", "Observations.Observation.scriban"); return template.Render(this); } + /// public string RenderInterface() => null; + /// public string RenderDescriptions() { var template = TemplateLoader.LoadOrThrow("CSharp", "Templates", "EnumDescriptions.scriban"); diff --git a/build/MTConnect.NET-SysML-Import/CSharp/PropertyModel.cs b/build/MTConnect.NET-SysML-Import/CSharp/PropertyModel.cs index 383775226..92792355d 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/PropertyModel.cs +++ b/build/MTConnect.NET-SysML-Import/CSharp/PropertyModel.cs @@ -5,20 +5,50 @@ namespace MTConnect.SysML.CSharp { + /// + /// Template model for a single C# property on a generated class. + /// Carries emitter flags ( and + /// ) so a property can be elided + /// from the model or the interface independently. + /// public class PropertyModel : MTConnectPropertyModel { + /// XML-formatted description (XML doc-comment shape). public string XmlDescription { get; set; } + /// + /// When true (default), the property is emitted into + /// the generated concrete class. + /// public bool ExportToModel { get; set; } = true; + /// + /// When true (default), the property is emitted into + /// the generated interface as well. + /// public bool ExportToInterface { get; set; } = true; + /// Parameterless constructor used by the reflection- + /// based factory. public PropertyModel() { } + /// + /// Constructs a model directly from a UML property. + /// + /// Source XMI document. + /// Identifier of the parent type. + /// Backing UML property. public PropertyModel(XmiDocument xmiDocument, string id, UmlProperty umlProperty) : base(xmiDocument, id, umlProperty) { } + /// + /// Copies every matching property off + /// into a fresh . Returns null + /// when the input is null. + /// + /// Generic SysML-import model. + /// Emitter-aware model, or null. public static PropertyModel Create(MTConnectPropertyModel importModel) { if (importModel != null) diff --git a/build/MTConnect.NET-SysML-Import/CSharp/TemplateRenderer.cs b/build/MTConnect.NET-SysML-Import/CSharp/TemplateRenderer.cs index 48e462cfc..4c261ff73 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/TemplateRenderer.cs +++ b/build/MTConnect.NET-SysML-Import/CSharp/TemplateRenderer.cs @@ -5,8 +5,25 @@ namespace MTConnect.SysML.CSharp { + /// + /// Orchestrator that loads every Scriban template under + /// CSharp/Templates/ and emits the *.g.cs files for + /// devices, observations, assets, interfaces, and units into the + /// libraries/MTConnect.NET-Common/ subtree of the output + /// directory. + /// public static class CSharpTemplateRenderer { + /// + /// Renders every C# artefact from the supplied SysML import + /// model. The output is partitioned by namespace under + /// . + /// + /// Fully-loaded SysML import + /// model. + /// Repository root that the + /// libraries/MTConnect.NET-Common/ subtree is written + /// into. public static void Render(MTConnectModel mtconnectModel, string outputPath) { if (mtconnectModel != null && !string.IsNullOrEmpty(outputPath)) diff --git a/build/MTConnect.NET-SysML-Import/CSharp/Templates/Assets.CuttingToolMeasurement.scriban b/build/MTConnect.NET-SysML-Import/CSharp/Templates/Assets.CuttingToolMeasurement.scriban index e9c6be049..a23a38c01 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/Templates/Assets.CuttingToolMeasurement.scriban +++ b/build/MTConnect.NET-SysML-Import/CSharp/Templates/Assets.CuttingToolMeasurement.scriban @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class {{name}} : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "{{type_id}}"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "{{code_id}}"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public {{name}}() { Type = TypeId; @@ -19,6 +29,10 @@ namespace MTConnect.Assets.CuttingTools.Measurements {{ if (units_enum) }}Units = {{units_enum}};{{ end }} } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public {{name}}(double value) { Type = TypeId; @@ -27,6 +41,10 @@ namespace MTConnect.Assets.CuttingTools.Measurements {{ if (units_enum) }}Units = {{units_enum}};{{ end }} } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public {{name}}(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/build/MTConnect.NET-SysML-Import/CSharp/Templates/Devices.ComponentType.scriban b/build/MTConnect.NET-SysML-Import/CSharp/Templates/Devices.ComponentType.scriban index 428bf45ab..dfd78e90e 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/Templates/Devices.ComponentType.scriban +++ b/build/MTConnect.NET-SysML-Import/CSharp/Templates/Devices.ComponentType.scriban @@ -10,15 +10,44 @@ namespace MTConnect.Devices.Components /// public {{- if (is_abstract) }} abstract{{ end }} class {{name}} : {{ if (parent_type) }}{{parent_type}}{{else}}Component{{ end }} {{- if (is_organizer) }}, IOrganizerComponent{{ end }} { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "{{type}}"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "{{default_name}}"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "{{description}}"; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - {{ if (maximum_version_enum) }}public override System.Version MaximumVersion => {{maximum_version_enum}};{{ end }} - {{ if (minimum_version_enum) }}public override System.Version MinimumVersion => {{minimum_version_enum}};{{ end }} +{{- if (maximum_version_enum) }} + + /// + /// The maximum MTConnect Version that this Component is valid for; set when the type has been deprecated. + /// + public override System.Version MaximumVersion => {{ maximum_version_enum }}; +{{- end }} +{{- if (minimum_version_enum) }} + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => {{ minimum_version_enum }}; +{{- end }} + /// + /// Initializes a new instance with its Type set to . + /// public {{name}}() { Type = TypeId; diff --git a/build/MTConnect.NET-SysML-Import/CSharp/Templates/Devices.CompositionType.scriban b/build/MTConnect.NET-SysML-Import/CSharp/Templates/Devices.CompositionType.scriban index 8a8171925..f1f0e92e2 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/Templates/Devices.CompositionType.scriban +++ b/build/MTConnect.NET-SysML-Import/CSharp/Templates/Devices.CompositionType.scriban @@ -10,15 +10,44 @@ namespace MTConnect.Devices.Compositions /// public class {{name}} : {{ if (parent_type) }}{{parent_type}}{{else}}Composition{{ end }} { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "{{type}}"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "{{default_name}}"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "{{description}}"; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - {{ if (maximum_version_enum) }}public override System.Version MaximumVersion => {{maximum_version_enum}};{{ end }} - {{ if (minimum_version_enum) }}public override System.Version MinimumVersion => {{minimum_version_enum}};{{ end }} +{{- if (maximum_version_enum) }} + + /// + /// The maximum MTConnect Version that this Composition is valid for; set when the type has been deprecated. + /// + public override System.Version MaximumVersion => {{ maximum_version_enum }}; +{{- end }} +{{- if (minimum_version_enum) }} + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => {{ minimum_version_enum }}; +{{- end }} - public {{name}}() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public {{name}}() { Type = TypeId; } } } \ No newline at end of file diff --git a/build/MTConnect.NET-SysML-Import/CSharp/Templates/Devices.DataItemType.scriban b/build/MTConnect.NET-SysML-Import/CSharp/Templates/Devices.DataItemType.scriban index 3a96b2e5c..b5174056c 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/Templates/Devices.DataItemType.scriban +++ b/build/MTConnect.NET-SysML-Import/CSharp/Templates/Devices.DataItemType.scriban @@ -18,18 +18,63 @@ namespace MTConnect.Devices.DataItems /// public class {{name}} : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.{{category}}; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "{{type}}"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "{{default_name}}"; - {{ if (representation) }}public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.{{representation}};{{ end }} - {{ if (units_enum) }}public const string DefaultUnits = {{units_enum}};{{ end }} +{{- if (representation) }} + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.{{representation}}; +{{- end }} +{{- if (units_enum) }} + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = {{units_enum}}; +{{- end }} + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "{{description}}"; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - {{ if (maximum_version_enum) }}public override System.Version MaximumVersion => {{maximum_version_enum}};{{ end }} - {{ if (minimum_version_enum) }}public override System.Version MinimumVersion => {{minimum_version_enum}};{{ end }} +{{- if (maximum_version_enum) }} + + /// + /// The maximum MTConnect Version that this DataItem is valid for; set when the type has been deprecated. + /// + public override System.Version MaximumVersion => {{ maximum_version_enum }}; +{{- end }} +{{- if (minimum_version_enum) }} + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => {{ minimum_version_enum }}; +{{- end }} {{ if ((sub_types | array.size) > 0) }}{{ i = 0 }} + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { {{- for sub_type in sub_types }}{{ i = i + 1 }} @@ -43,6 +88,9 @@ namespace MTConnect.Devices.DataItems } {{ end }} + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public {{name}}() { Category = CategoryId; @@ -54,6 +102,11 @@ namespace MTConnect.Devices.DataItems {{- if ((sub_types | array.size) > 0) }} + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public {{name}}( string parentId, SubTypes subType @@ -68,10 +121,16 @@ namespace MTConnect.Devices.DataItems {{ if (units_enum) }}Units = DefaultUnits;{{ end }} } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); {{- if ((sub_types | array.size) > 0) }}{{ i = 0 }} + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -87,6 +146,9 @@ namespace MTConnect.Devices.DataItems {{- end }} {{- if ((sub_types | array.size) > 0) }}{{ i = 0 }} + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) @@ -101,13 +163,17 @@ namespace MTConnect.Devices.DataItems {{- end }} {{ else }} + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public {{name}}(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - {{ if (representation) }}Representation = DefaultRepresentation;{{ end }} + {{ if (representation) }}Representation = DefaultRepresentation;{{ end }} {{ if (units_enum) }}Units = DefaultUnits;{{ end }} } {{- end }} diff --git a/build/MTConnect.NET-SysML-Import/CSharp/Templates/Devices.Device.scriban b/build/MTConnect.NET-SysML-Import/CSharp/Templates/Devices.Device.scriban index d600f0bda..5055c1823 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/Templates/Devices.Device.scriban +++ b/build/MTConnect.NET-SysML-Import/CSharp/Templates/Devices.Device.scriban @@ -15,7 +15,14 @@ namespace MTConnect.Devices /// public class Device : IDevice { + /// + /// The MTConnect type value that identifies a Device. + /// public const string TypeId = "Device"; + + /// + /// The description of the Device type as defined by the MTConnect Standard. + /// public const string DescriptionText = "{{descriptions.devices_device}}"; private static readonly Version DefaultMaximumVersion = null; @@ -164,6 +171,9 @@ namespace MTConnect.Devices public virtual Version MinimumVersion => DefaultMinimumVersion; + /// + /// Initializes a new Device with a random Id, default name, and a new Uuid. + /// public Device() { Id = StringFunctions.RandomString(10); @@ -176,11 +186,18 @@ namespace MTConnect.Devices } + /// + /// Computes a content hash over this Device and its data items, compositions, and components. + /// public string GenerateHash() { return GenerateHash(this); } + /// + /// Computes a content hash over the specified Device and its data items, compositions, and components. + /// + /// The Device to hash. public static string GenerateHash(IDevice device) { if (device != null) @@ -587,6 +604,13 @@ namespace MTConnect.Devices } } + /// + /// Creates a DataItem from the specified category, type, optional subType, and optional Id, and adds it to the Device. + /// + /// The DataItem category. + /// The DataItem type. + /// The optional DataItem subType. + /// The optional DataItem Id. public void AddDataItem(DataItemCategory category, string type, string subType = null, string dataItemId = null) { if (!string.IsNullOrEmpty(type)) @@ -641,6 +665,13 @@ namespace MTConnect.Devices #endregion + /// + /// Returns a version-conformant copy of the Device for the specified MTConnect Version, applying + /// the version gating rules for descriptions, references, configuration, and child elements; + /// returns null when the Device cannot be represented in that version. + /// + /// The source Device. + /// The target MTConnect Version. public static Device Process(IDevice device, Version mtconnectVersion) { if (device != null) diff --git a/build/MTConnect.NET-SysML-Import/CSharp/Templates/Enum.scriban b/build/MTConnect.NET-SysML-Import/CSharp/Templates/Enum.scriban index 5919dc329..af2cf333d 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/Templates/Enum.scriban +++ b/build/MTConnect.NET-SysML-Import/CSharp/Templates/Enum.scriban @@ -3,6 +3,9 @@ namespace {{namespace}} { + /// + /// {{ if (description) }}{{ description }}{{ else }}{{ name }} controlled vocabulary as defined by the MTConnect Standard.{{ end }} + /// public enum {{name}} { {{- i = 0 }}{{ for value in values }}{{ i = i + 1 }} diff --git a/build/MTConnect.NET-SysML-Import/CSharp/Templates/EnumDescriptions.scriban b/build/MTConnect.NET-SysML-Import/CSharp/Templates/EnumDescriptions.scriban index 41be9a734..16691ed33 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/Templates/EnumDescriptions.scriban +++ b/build/MTConnect.NET-SysML-Import/CSharp/Templates/EnumDescriptions.scriban @@ -3,6 +3,9 @@ namespace {{namespace}} { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class {{name}}Descriptions { {{- i = 0 }}{{- for value in values }}{{ i = i + 1 }} @@ -17,6 +20,9 @@ namespace {{namespace}} {{- if ((values | array.size) > 0) }}{{ i = 0 }} + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get({{name}} value) { switch (value) diff --git a/build/MTConnect.NET-SysML-Import/CSharp/Templates/EnumString.scriban b/build/MTConnect.NET-SysML-Import/CSharp/Templates/EnumString.scriban index cbee5bb3d..e4705fab7 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/Templates/EnumString.scriban +++ b/build/MTConnect.NET-SysML-Import/CSharp/Templates/EnumString.scriban @@ -3,6 +3,9 @@ namespace {{namespace}} { + /// + /// {{ if (description) }}{{ description }}{{ else }}{{ name }} string constants as defined by the MTConnect Standard.{{ end }} + /// public static {{- if (is_partial) }} partial{{ end }} class {{name}} { {{- i = 0 }}{{ for value in values }}{{ i = i + 1 }} diff --git a/build/MTConnect.NET-SysML-Import/CSharp/Templates/EnumStringDescriptions.scriban b/build/MTConnect.NET-SysML-Import/CSharp/Templates/EnumStringDescriptions.scriban index 18cdb9369..f85216280 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/Templates/EnumStringDescriptions.scriban +++ b/build/MTConnect.NET-SysML-Import/CSharp/Templates/EnumStringDescriptions.scriban @@ -3,6 +3,9 @@ namespace {{namespace}} { + /// + /// Description text for each string constant as defined by the MTConnect Standard. + /// public static class {{name}}Descriptions { {{- i = 0 }}{{- for value in values }}{{ i = i + 1 }} @@ -17,6 +20,9 @@ namespace {{namespace}} {{- if ((values | array.size) > 0) }}{{ i = 0 }} + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(string value) { switch (value) diff --git a/build/MTConnect.NET-SysML-Import/CSharp/Templates/Interfaces.InterfaceDataItemType.scriban b/build/MTConnect.NET-SysML-Import/CSharp/Templates/Interfaces.InterfaceDataItemType.scriban index 475688a72..2e32b4bc6 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/Templates/Interfaces.InterfaceDataItemType.scriban +++ b/build/MTConnect.NET-SysML-Import/CSharp/Templates/Interfaces.InterfaceDataItemType.scriban @@ -10,17 +10,56 @@ namespace MTConnect.Interfaces /// public class {{name}} : InterfaceDataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this Interface DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.{{category}}; + + /// + /// The MTConnect type value that identifies this Interface DataItem. + /// public const string TypeId = "{{type}}"; + + /// + /// The default name assigned to an instance of this Interface DataItem. + /// public const string NameId = "{{default_name}}"; - {{ if (units_enum) }}public const string DefaultUnits = {{units_enum}};{{ end }} +{{- if (units_enum) }} + + /// + /// The default units for this Interface DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = {{units_enum}}; +{{- end }} + + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "{{description}}"; + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - {{ if (maximum_version_enum) }}public override System.Version MaximumVersion => {{maximum_version_enum}};{{ end }} - {{ if (minimum_version_enum) }}public override System.Version MinimumVersion => {{minimum_version_enum}};{{ end }} +{{- if (maximum_version_enum) }} + + /// + /// The maximum MTConnect Version that this Interface DataItem is valid for; set when the type has been deprecated. + /// + public override System.Version MaximumVersion => {{ maximum_version_enum }}; +{{- end }} +{{- if (minimum_version_enum) }} + + /// + /// The minimum MTConnect Version that introduced this Interface DataItem. + /// + public override System.Version MinimumVersion => {{ minimum_version_enum }}; +{{- end }} {{ if ((sub_types | array.size) > 0) }}{{ i = 0 }} + /// + /// The set of subType values defined for this Interface DataItem by the MTConnect Standard. + /// public new enum SubTypes { {{- for sub_type in sub_types }}{{ i = i + 1 }} @@ -34,6 +73,9 @@ namespace MTConnect.Interfaces } {{ end }} + /// + /// Initializes a new instance with its category and type set to the defaults for this Interface DataItem. + /// public {{name}}() { Category = CategoryId; @@ -43,6 +85,11 @@ namespace MTConnect.Interfaces {{- if ((sub_types | array.size) > 0) }} + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this Interface DataItem belongs to. + /// The subType to assign to this Interface DataItem. public {{name}}( string parentId, SubTypes subType @@ -56,10 +103,16 @@ namespace MTConnect.Interfaces {{ if (units_enum) }}Units = DefaultUnits;{{ end }} } + /// + /// The MTConnect Standard description of this Interface DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); {{- if ((sub_types | array.size) > 0) }}{{ i = 0 }} + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public new static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -75,6 +128,9 @@ namespace MTConnect.Interfaces {{- end }} {{- if ((sub_types | array.size) > 0) }}{{ i = 0 }} + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public new static string GetSubTypeId(SubTypes subType) { switch (subType) @@ -89,6 +145,10 @@ namespace MTConnect.Interfaces {{- end }} {{ else }} + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this Interface DataItem belongs to. public {{name}}(string deviceId) { Id = CreateId(deviceId, NameId); diff --git a/build/MTConnect.NET-SysML-Import/CSharp/Templates/Model.scriban b/build/MTConnect.NET-SysML-Import/CSharp/Templates/Model.scriban index 2397fb19b..db0ab32bc 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/Templates/Model.scriban +++ b/build/MTConnect.NET-SysML-Import/CSharp/Templates/Model.scriban @@ -10,16 +10,17 @@ namespace {{namespace}} /// public {{- if (is_abstract) }} abstract{{ end }} {{- if (is_partial) }} partial{{ end }} class {{name}} : {{ if (parent_name) }}{{parent_name}}, {{ end }}I{{name}}{{ for additional_parent_name in additional_parent_names }}, I{{additional_parent_name}}{{ end }} { + /// + /// The description of this type as defined by the MTConnect Standard. + /// {{ if (parent_name) }}public new const string DescriptionText = "{{description}}";{{ else }}public const string DescriptionText = "{{description}}";{{ end }} - {{ i = 0 }}{{- for property in properties }}{{ i = i + 1 }} + /// /// {{property.description}} /// {{ if (property.is_array) }}public System.Collections.Generic.IEnumerable<{{property.data_type}}> {{property.name}} { get; set; }{{ end }} {{- if (!property.is_array) }}public {{property.data_type}}{{ if (property.is_optional) }}?{{ end }} {{property.name}} { get; set; }{{ end }} - {{- if (i < (properties | array.size)) }} - {{ end }} {{- end }} } } \ No newline at end of file diff --git a/build/MTConnect.NET-SysML-Import/CSharp/Templates/ModelDescriptions.scriban b/build/MTConnect.NET-SysML-Import/CSharp/Templates/ModelDescriptions.scriban index fda9440a8..ce71a86f9 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/Templates/ModelDescriptions.scriban +++ b/build/MTConnect.NET-SysML-Import/CSharp/Templates/ModelDescriptions.scriban @@ -3,6 +3,9 @@ namespace {{namespace}} { + /// + /// Description text for each property of {{name}} as defined by the MTConnect Standard. + /// public static class {{name}}Descriptions { {{- i = 0 }}{{- for property in properties }}{{ i = i + 1 }} diff --git a/build/MTConnect.NET-SysML-Import/CSharp/Templates/Pallets.Measurement.scriban b/build/MTConnect.NET-SysML-Import/CSharp/Templates/Pallets.Measurement.scriban index c92505e04..370e84642 100644 --- a/build/MTConnect.NET-SysML-Import/CSharp/Templates/Pallets.Measurement.scriban +++ b/build/MTConnect.NET-SysML-Import/CSharp/Templates/Pallets.Measurement.scriban @@ -8,16 +8,30 @@ namespace {{namespace}} /// public class {{name}} : Measurement, I{{name}} { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "{{type_id}}"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "{{code_id}}"; + /// + /// Initializes a new instance with its type set to the default for this Measurement. + /// public {{name}}() { Type = TypeId; {{ if (units_enum) }}Units = {{units_enum}};{{ end }} } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public {{name}}(double value) { Type = TypeId; @@ -25,6 +39,10 @@ namespace {{namespace}} {{ if (units_enum) }}Units = {{units_enum}};{{ end }} } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public {{name}}(IMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/build/MTConnect.NET-SysML-Import/Json-cppagent/ComponentsModel.cs b/build/MTConnect.NET-SysML-Import/Json-cppagent/ComponentsModel.cs index 088bf2adb..13ee2530e 100644 --- a/build/MTConnect.NET-SysML-Import/Json-cppagent/ComponentsModel.cs +++ b/build/MTConnect.NET-SysML-Import/Json-cppagent/ComponentsModel.cs @@ -2,8 +2,13 @@ namespace MTConnect.SysML.Json_cppagent { + /// + /// Scriban-template bag of + /// entries used by the JSON-cppagent Components template. + /// public class ComponentsModel { + /// The component types to render. public List Types { get; set; } = new(); } } diff --git a/build/MTConnect.NET-SysML-Import/Json-cppagent/CuttingToolMeasurementsModel.cs b/build/MTConnect.NET-SysML-Import/Json-cppagent/CuttingToolMeasurementsModel.cs index 696d72e27..bf80d4966 100644 --- a/build/MTConnect.NET-SysML-Import/Json-cppagent/CuttingToolMeasurementsModel.cs +++ b/build/MTConnect.NET-SysML-Import/Json-cppagent/CuttingToolMeasurementsModel.cs @@ -2,8 +2,14 @@ namespace MTConnect.SysML.Json_cppagent { + /// + /// Scriban-template bag of + /// entries used by the JSON-cppagent CuttingToolMeasurements + /// template. + /// public class CuttingToolMeasurementsModel { + /// The measurement models to render. public List Types { get; set; } = new(); } } diff --git a/build/MTConnect.NET-SysML-Import/Json-cppagent/DataItemsModel.cs b/build/MTConnect.NET-SysML-Import/Json-cppagent/DataItemsModel.cs index 1a6b0f987..9defaac49 100644 --- a/build/MTConnect.NET-SysML-Import/Json-cppagent/DataItemsModel.cs +++ b/build/MTConnect.NET-SysML-Import/Json-cppagent/DataItemsModel.cs @@ -2,8 +2,13 @@ namespace MTConnect.SysML.Json_cppagent { + /// + /// Scriban-template bag of + /// entries used by the JSON-cppagent DataItems template. + /// public class DataItemsModel { + /// The data-item types to render. public List Types { get; set; } = new(); } } diff --git a/build/MTConnect.NET-SysML-Import/Json-cppagent/TemplateRenderer.cs b/build/MTConnect.NET-SysML-Import/Json-cppagent/TemplateRenderer.cs index 790accba6..02651e239 100644 --- a/build/MTConnect.NET-SysML-Import/Json-cppagent/TemplateRenderer.cs +++ b/build/MTConnect.NET-SysML-Import/Json-cppagent/TemplateRenderer.cs @@ -2,8 +2,23 @@ namespace MTConnect.SysML.Json_cppagent { + /// + /// Orchestrator that renders the JSON-cppagent *.g.cs + /// artefacts (components, events, samples, cutting-tool + /// measurements) under libraries/MTConnect.NET-JSON-cppagent/ + /// from a SysML import model. + /// public static class JsonCppAgentTemplateRenderer { + /// + /// Renders every JSON-cppagent artefact from the supplied + /// SysML import model. + /// + /// Fully-loaded SysML import + /// model. + /// Repository root the + /// libraries/MTConnect.NET-JSON-cppagent/ subtree is + /// written into. public static void Render(MTConnectModel mtconnectModel, string outputPath) { if (mtconnectModel != null && !string.IsNullOrEmpty(outputPath)) diff --git a/build/MTConnect.NET-SysML-Import/Json-cppagent/Templates/Components.scriban b/build/MTConnect.NET-SysML-Import/Json-cppagent/Templates/Components.scriban index f10757635..cb07b01b6 100644 --- a/build/MTConnect.NET-SysML-Import/Json-cppagent/Templates/Components.scriban +++ b/build/MTConnect.NET-SysML-Import/Json-cppagent/Templates/Components.scriban @@ -8,16 +8,35 @@ using System.Text.Json.Serialization; namespace MTConnect.Devices.Json { + /// + /// cppagent-style JSON representation of a device's component tree. Each MTConnect + /// component type is exposed as its own strongly-typed collection so the + /// System.Text.Json serializer emits one property per type, matching the + /// flattened object shape the C++ reference agent produces. + /// public class JsonComponents { {{- for type in types }}{{ i = i + 1 }} + /// + /// The set of {{type.type}} components on the device. +{{- if (type.description) }} + /// {{type.description}} +{{- end }} + /// [JsonPropertyName("{{type.type}}")] public IEnumerable {{type.type}} { get; set; } {{ end }} + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonComponents() { } + /// + /// Initializes a new instance from a flat sequence of , + /// bucketing each one into the typed collection that matches its MTConnect type. + /// public JsonComponents(IEnumerable components) { if (!components.IsNullOrEmpty()) @@ -45,6 +64,10 @@ namespace MTConnect.Devices.Json } + /// + /// Flattens every typed component collection back into a single + /// sequence, restoring each item's MTConnect type. + /// public IEnumerable ToComponents() { var components = new List(); @@ -56,4 +79,4 @@ namespace MTConnect.Devices.Json return components; } } -} \ No newline at end of file +} diff --git a/build/MTConnect.NET-SysML-Import/Json-cppagent/Templates/Events.scriban b/build/MTConnect.NET-SysML-Import/Json-cppagent/Templates/Events.scriban index 62e655212..239b85861 100644 --- a/build/MTConnect.NET-SysML-Import/Json-cppagent/Templates/Events.scriban +++ b/build/MTConnect.NET-SysML-Import/Json-cppagent/Templates/Events.scriban @@ -11,8 +11,18 @@ using System.Text.Json.Serialization; namespace MTConnect.Streams.Json { + /// + /// cppagent-style JSON representation of the EVENT-category observations in a + /// stream. Every MTConnect event type is exposed as three typed collections — + /// one each for the VALUE, DATA_SET, and TABLE representations — so the + /// serialized object shape matches the C++ reference agent's output. + /// public class JsonEvents { + /// + /// Materializes every typed collection into a single flat list of + /// , restoring each observation's MTConnect type. + /// [JsonIgnore] public List Observations { @@ -31,19 +41,41 @@ namespace MTConnect.Streams.Json } {{- for type in types }} + /// + /// The {{type.name}} events reported with the scalar VALUE representation. +{{- if (type.description) }} + /// {{type.description}} +{{- end }} + /// [JsonPropertyName("{{type.name}}")] public IEnumerable {{type.name}} { get; set; } + /// + /// The {{type.name}} events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("{{type.name}}DataSet")] public IEnumerable {{type.name}}DataSet { get; set; } + /// + /// The {{type.name}} events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("{{type.name}}Table")] public IEnumerable {{type.name}}Table { get; set; } {{ end }} + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonEvents() { } + /// + /// Initializes a new instance from a flat sequence of , + /// routing each one into the typed collection matching its MTConnect type and + /// representation. + /// public JsonEvents(IEnumerable observations) { if (observations != null) @@ -93,5 +125,5 @@ namespace MTConnect.Streams.Json } } } - } -} \ No newline at end of file + } +} diff --git a/build/MTConnect.NET-SysML-Import/Json-cppagent/Templates/Measurements.scriban b/build/MTConnect.NET-SysML-Import/Json-cppagent/Templates/Measurements.scriban index 70ae52321..4fd28e37b 100644 --- a/build/MTConnect.NET-SysML-Import/Json-cppagent/Templates/Measurements.scriban +++ b/build/MTConnect.NET-SysML-Import/Json-cppagent/Templates/Measurements.scriban @@ -8,16 +8,34 @@ using System.Text.Json.Serialization; namespace MTConnect.Assets.Json.CuttingTools { + /// + /// cppagent-style JSON representation of a cutting tool's measurements. Each + /// MTConnect measurement type is exposed as its own typed collection so the + /// serialized object shape matches the C++ reference agent's output. + /// public class JsonMeasurements { {{- for type in types }} + /// + /// The {{type.type_id}} measurements declared on the cutting tool. +{{- if (type.description) }} + /// {{type.description}} +{{- end }} + /// [JsonPropertyName("{{type.type_id}}")] public List {{type.name}}s { get; set; } {{ end }} + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonMeasurements() { } + /// + /// Initializes a new instance from a flat sequence of , + /// bucketing each one into the typed collection that matches its MTConnect type. + /// public JsonMeasurements(IEnumerable measurements) { if (!measurements.IsNullOrEmpty()) @@ -32,22 +50,26 @@ namespace MTConnect.Assets.Json.CuttingTools {{type.name}}s.Add(new JsonMeasurement(measurement)); break; -{{ end }} - } +{{ end }} + } } - } + } } + /// + /// Flattens every typed measurement collection back into a single + /// sequence, restoring each item's MTConnect type. + /// public IEnumerable ToMeasurements() { var measurements = new List(); - + {{ for type in types }} if (!{{type.name}}s.IsNullOrEmpty()) foreach (var measurement in {{type.name}}s) measurements.Add(measurement.ToMeasurement({{type.name}}.TypeId)); -{{- end }} +{{- end }} return measurements; } } -} \ No newline at end of file +} diff --git a/build/MTConnect.NET-SysML-Import/Json-cppagent/Templates/Samples.scriban b/build/MTConnect.NET-SysML-Import/Json-cppagent/Templates/Samples.scriban index d59e767c1..d4f53cdb2 100644 --- a/build/MTConnect.NET-SysML-Import/Json-cppagent/Templates/Samples.scriban +++ b/build/MTConnect.NET-SysML-Import/Json-cppagent/Templates/Samples.scriban @@ -11,8 +11,18 @@ using System.Text.Json.Serialization; namespace MTConnect.Streams.Json { + /// + /// cppagent-style JSON representation of the SAMPLE-category observations in a + /// stream. Every MTConnect sample type is exposed as four typed collections — + /// one each for the VALUE, DATA_SET, TABLE, and TIME_SERIES representations — so + /// the serialized object shape matches the C++ reference agent's output. + /// public class JsonSamples { + /// + /// Materializes every typed collection into a single flat list of + /// , restoring each observation's MTConnect type. + /// [JsonIgnore] public List Observations { @@ -32,22 +42,48 @@ namespace MTConnect.Streams.Json } {{- for type in types }} + /// + /// The {{type.name}} samples reported with the scalar VALUE representation. +{{- if (type.description) }} + /// {{type.description}} +{{- end }} + /// [JsonPropertyName("{{type.name}}")] public IEnumerable {{type.name}} { get; set; } + /// + /// The {{type.name}} samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("{{type.name}}DataSet")] public IEnumerable {{type.name}}DataSet { get; set; } + /// + /// The {{type.name}} samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("{{type.name}}Table")] public IEnumerable {{type.name}}Table { get; set; } + /// + /// The {{type.name}} samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("{{type.name}}TimeSeries")] public IEnumerable {{type.name}}TimeSeries { get; set; } {{ end }} + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonSamples() { } + /// + /// Initializes a new instance from a flat sequence of , + /// routing each one into the typed collection matching its MTConnect type and + /// representation. + /// public JsonSamples(IEnumerable observations) { if (observations != null) @@ -109,5 +145,5 @@ namespace MTConnect.Streams.Json } } } - } -} \ No newline at end of file + } +} diff --git a/build/MTConnect.NET-SysML-Import/MTConnect.NET-SysML-Import.csproj b/build/MTConnect.NET-SysML-Import/MTConnect.NET-SysML-Import.csproj index d9d823a20..c2b0a2040 100644 --- a/build/MTConnect.NET-SysML-Import/MTConnect.NET-SysML-Import.csproj +++ b/build/MTConnect.NET-SysML-Import/MTConnect.NET-SysML-Import.csproj @@ -9,7 +9,7 @@ - + diff --git a/build/MTConnect.NET-SysML-Import/README.md b/build/MTConnect.NET-SysML-Import/README.md index 2ec7edc61..de44e79dc 100644 --- a/build/MTConnect.NET-SysML-Import/README.md +++ b/build/MTConnect.NET-SysML-Import/README.md @@ -184,7 +184,7 @@ When upgrading Scriban or editing templates, **always** run a v2.5 / v2.6 / v2.7 | Importer prints "Done." but no `.g.cs` files change | Scriban template tree missing or case-mismatched. Build output should contain `CSharp/Templates/`, `Json-cppagent/Templates/`, `Xml/Templates/` — case-correct. The `EnsureTemplateTreesExist` startup check now catches this before XMI parse. | | `CS0246: type 'X' could not be found` after regen | A new XMI version introduced a cross-package parent that the resolver couldn't graft — typically because the parent lives in a sub-model whose `Classes` list isn't yet enumerated by `MTConnectModel.CollectClassLists`. Add it to that helper. | | `InvalidCastException` in `CSharpTemplateRenderer.Render` | A property's `Id` matches a suffix-based class selector. The `Result` selector now type-guards; new selectors should follow the same pattern (`typeof(MTConnectClassModel).IsAssignableFrom(type) && Id.EndsWith(...)`)| -| 11 NuGet vulnerability warnings on Scriban | Known — Scriban 5.x has open advisories. Upgrade to 7.x is tracked as a follow-up dep-update PR, not here. | +| Older NuGet vulnerability warnings on Scriban | Scriban now pinned at 7.2.0 — the 5.x advisories no longer apply. If a warning resurfaces on a fresh dependency, audit the resolved version with `dotnet list package --vulnerable --include-transitive`. | ## Reproducibility diff --git a/build/MTConnect.NET-SysML-Import/Xml/CuttingToolMeasurementsModel.cs b/build/MTConnect.NET-SysML-Import/Xml/CuttingToolMeasurementsModel.cs index 7d85afc53..b8f5d7905 100644 --- a/build/MTConnect.NET-SysML-Import/Xml/CuttingToolMeasurementsModel.cs +++ b/build/MTConnect.NET-SysML-Import/Xml/CuttingToolMeasurementsModel.cs @@ -2,8 +2,13 @@ namespace MTConnect.SysML.Xml { + /// + /// Scriban-template bag of + /// entries used by the XML CuttingToolMeasurements template. + /// public class CuttingToolMeasurementsModel { + /// The measurement models to render. public List Types { get; set; } = new(); } } diff --git a/build/MTConnect.NET-SysML-Import/Xml/TemplateRenderer.cs b/build/MTConnect.NET-SysML-Import/Xml/TemplateRenderer.cs index b7204e5b7..0da5904d3 100644 --- a/build/MTConnect.NET-SysML-Import/Xml/TemplateRenderer.cs +++ b/build/MTConnect.NET-SysML-Import/Xml/TemplateRenderer.cs @@ -2,8 +2,23 @@ namespace MTConnect.SysML.Xml { + /// + /// Orchestrator that renders the XML-emitter *.g.cs + /// artefacts (cutting-tool measurements + life-cycle + cutting + /// item) under libraries/MTConnect.NET-XML/ from a SysML + /// import model. + /// public static class XmlTemplateRenderer { + /// + /// Renders every XML artefact from the supplied SysML import + /// model. + /// + /// Fully-loaded SysML import + /// model. + /// Repository root the + /// libraries/MTConnect.NET-XML/ subtree is written + /// into. public static void Render(MTConnectModel mtconnectModel, string outputPath) { if (mtconnectModel != null && !string.IsNullOrEmpty(outputPath)) diff --git a/build/MTConnect.NET-SysML-Import/Xml/Templates/XmlCuttingItem.scriban b/build/MTConnect.NET-SysML-Import/Xml/Templates/XmlCuttingItem.scriban index e8765824f..63a15bf23 100644 --- a/build/MTConnect.NET-SysML-Import/Xml/Templates/XmlCuttingItem.scriban +++ b/build/MTConnect.NET-SysML-Import/Xml/Templates/XmlCuttingItem.scriban @@ -9,6 +9,11 @@ namespace MTConnect.Assets.Xml.CuttingTools { public partial class XmlCuttingItem { + /// + /// The set of physical and geometric measurements that characterize this cutting item. + /// Each element is deserialized into the concrete subclass + /// registered for its MTConnect measurement type. + /// [XmlArray("Measurements")] {{- for type in types }} [XmlArrayItem({{type.name}}.TypeId, typeof(Xml{{type.name}}))] diff --git a/build/MTConnect.NET-SysML-Import/Xml/Templates/XmlCuttingToolLifeCycle.scriban b/build/MTConnect.NET-SysML-Import/Xml/Templates/XmlCuttingToolLifeCycle.scriban index e93943667..4267cb395 100644 --- a/build/MTConnect.NET-SysML-Import/Xml/Templates/XmlCuttingToolLifeCycle.scriban +++ b/build/MTConnect.NET-SysML-Import/Xml/Templates/XmlCuttingToolLifeCycle.scriban @@ -9,6 +9,11 @@ namespace MTConnect.Assets.Xml.CuttingTools { public partial class XmlCuttingToolLifeCycle { + /// + /// The set of physical and geometric measurements that characterize the cutting tool + /// over its life cycle. Each element is deserialized into the concrete + /// subclass registered for its MTConnect measurement type. + /// [XmlArray("Measurements")] {{- for type in types }} [XmlArrayItem({{type.name}}.TypeId, typeof(Xml{{type.name}}))] diff --git a/build/MTConnect.NET-SysML-Import/Xml/Templates/XmlMeasurements.scriban b/build/MTConnect.NET-SysML-Import/Xml/Templates/XmlMeasurements.scriban index e986afa10..3836178eb 100644 --- a/build/MTConnect.NET-SysML-Import/Xml/Templates/XmlMeasurements.scriban +++ b/build/MTConnect.NET-SysML-Import/Xml/Templates/XmlMeasurements.scriban @@ -6,6 +6,18 @@ using MTConnect.Assets.CuttingTools.Measurements; namespace MTConnect.Assets.Xml.CuttingTools { {{- for type in types }} - public class Xml{{type.name}} : XmlMeasurement { public Xml{{type.name}}() { Type = {{type.name}}.TypeId; } } + /// + /// XML serialization wrapper for the {{type.type_id}} cutting-tool measurement. +{{- if (type.description) }} + /// {{type.description}} +{{- end }} + /// + public class Xml{{type.name}} : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to ({{type.type_id}}). + /// + public Xml{{type.name}}() { Type = {{type.name}}.TypeId; } + } {{ end }} -} \ No newline at end of file +} diff --git a/build/MTConnect.NET.Builder/Files.cs b/build/MTConnect.NET.Builder/Files.cs index f98e9c54d..01f2da46b 100644 --- a/build/MTConnect.NET.Builder/Files.cs +++ b/build/MTConnect.NET.Builder/Files.cs @@ -6,8 +6,26 @@ namespace TrakHound.Builder { + /// + /// Filesystem helpers used by the release-builder script: + /// recursive copy / move with ignore patterns, zip / unzip, and a + /// directory-clear utility. Every method is best-effort — + /// transport failures are swallowed inside the method so the + /// builder script can continue. + /// public static class Files { + /// + /// Recursively copies every file from + /// to + /// , skipping any path + /// that matches one of the + /// regular-expression strings. + /// + /// Source root. + /// Destination root. + /// Regex patterns matched against + /// the full source path; matched paths are skipped. public static void Copy(string sourceDirectory, string destinationDirectory, IEnumerable ignorePatterns = null) { if (!string.IsNullOrEmpty(sourceDirectory) && !string.IsNullOrEmpty(destinationDirectory)) @@ -58,6 +76,15 @@ public static void Copy(string sourceDirectory, string destinationDirectory, IEn } } + /// + /// Recursively moves every file from + /// to + /// , skipping paths + /// matching . + /// + /// Source root. + /// Destination root. + /// Regex patterns to skip. public static void Move(string sourceDirectory, string destinationDirectory, IEnumerable ignorePatterns = null) { if (!string.IsNullOrEmpty(sourceDirectory) && !string.IsNullOrEmpty(destinationDirectory)) @@ -96,6 +123,12 @@ public static void Move(string sourceDirectory, string destinationDirectory, IEn } } + /// + /// Zips the directory at into a + /// new in-memory byte array. + /// + /// Source directory. + /// The zipped archive bytes. public static byte[] Zip(string sourcePath) { if (!string.IsNullOrEmpty(sourcePath)) @@ -127,6 +160,12 @@ public static byte[] Zip(string sourcePath) return null; } + /// + /// Zips the directory at and + /// writes the archive to . + /// + /// Source directory. + /// Destination archive path. public static void Zip(string sourcePath, string destinationPath) { var bytes = Zip(sourcePath); @@ -140,6 +179,12 @@ public static void Zip(string sourcePath, string destinationPath) } } + /// + /// Extracts the supplied zip archive bytes into + /// . + /// + /// In-memory zip archive. + /// Target directory. public static void Unzip(byte[] archivedBytes, string destinationPath) { if (archivedBytes != null && !string.IsNullOrEmpty(destinationPath)) @@ -161,6 +206,12 @@ public static void Unzip(byte[] archivedBytes, string destinationPath) } + /// + /// Recursively deletes every file and subdirectory under + /// , leaving the directory itself + /// in place but empty. Best-effort — IO errors are swallowed. + /// + /// Directory to clear. public static void Clear(string directory) { if (!string.IsNullOrEmpty(directory)) diff --git a/build/MTConnect.NET.Builder/ListExtensions.cs b/build/MTConnect.NET.Builder/ListExtensions.cs index eccca88fb..9f98c520f 100644 --- a/build/MTConnect.NET.Builder/ListExtensions.cs +++ b/build/MTConnect.NET.Builder/ListExtensions.cs @@ -1,5 +1,9 @@ namespace TrakHound.Builder { + /// + /// Collection-related extension helpers used by the release-builder + /// script. + /// public static class ListExtensions { /// @@ -50,6 +54,13 @@ public static bool IsNullOrEmpty(this IEnumerable enumerable) return !enumerable.Any(); } + /// + /// Returns the input sequence with duplicate strings removed, + /// preserving the original insertion order. + /// + /// Input strings, possibly null. + /// The distinct sequence, or the original sequence + /// when it is null or empty. public static IEnumerable ToDistinct(this IEnumerable strings) { if (!strings.IsNullOrEmpty()) diff --git a/build/MTConnect.NET.Builder/StringExtensions.cs b/build/MTConnect.NET.Builder/StringExtensions.cs index 9567bfea1..771660819 100644 --- a/build/MTConnect.NET.Builder/StringExtensions.cs +++ b/build/MTConnect.NET.Builder/StringExtensions.cs @@ -1,13 +1,29 @@ namespace TrakHound.Builder { + /// + /// Lenient string-to-primitive converters used by the + /// release-builder script. + /// public static class StringFunctions { + /// + /// Parses a dotted-quad string into a , + /// returning null on failure. + /// + /// Input string, e.g. "6.9.0". + /// The parsed version, or null. public static Version ToVersion(this string s) { if (!string.IsNullOrEmpty(s) && Version.TryParse(s, out var x)) return x; else return null; } + /// + /// Parses a decimal integer string, returning -1 on + /// failure rather than throwing. + /// + /// Input string. + /// The parsed integer, or -1. public static int ToInt(this string s) { if (!string.IsNullOrEmpty(s) && int.TryParse(s, out var x)) return x; diff --git a/docs/.docfx/docfx.json b/docs/.docfx/docfx.json new file mode 100644 index 000000000..ff7187a8d --- /dev/null +++ b/docs/.docfx/docfx.json @@ -0,0 +1,32 @@ +{ + "metadata": [ + { + "src": [ + { + "files": [ + "libraries/MTConnect.NET-Common/bin/Debug/net8.0/MTConnect.NET-Common.dll", + "libraries/MTConnect.NET-DeviceFinder/bin/Debug/net8.0/MTConnect.NET-DeviceFinder.dll", + "libraries/MTConnect.NET-HTTP/bin/Debug/net8.0/MTConnect.NET-HTTP.dll", + "libraries/MTConnect.NET-JSON/bin/Debug/net8.0/MTConnect.NET-JSON.dll", + "libraries/MTConnect.NET-JSON-cppagent/bin/Debug/net8.0/MTConnect.NET-JSON-cppagent.dll", + "libraries/MTConnect.NET-MQTT/bin/Debug/net8.0/MTConnect.NET-MQTT.dll", + "libraries/MTConnect.NET-Protobuf/bin/Debug/net8.0/MTConnect.NET-Protobuf.dll", + "libraries/MTConnect.NET-Services/bin/Debug/net8.0/MTConnect.NET-Services.dll", + "libraries/MTConnect.NET-SHDR/bin/Debug/net8.0/MTConnect.NET-SHDR.dll", + "libraries/MTConnect.NET-SysML/bin/Debug/net8.0/MTConnect.NET-SysML.dll", + "libraries/MTConnect.NET-TLS/bin/Debug/net8.0/MTConnect.NET-TLS.dll", + "libraries/MTConnect.NET-XML/bin/Debug/net8.0/MTConnect.NET-XML.dll", + "libraries/MTConnect.NET/bin/Debug/net8.0/MTConnect.NET.dll" + ], + "src": "../.." + } + ], + "dest": "../api", + "outputFormat": "markdown", + "namespaceLayout": "flattened", + "memberLayout": "samePage", + "includePrivateMembers": true, + "filter": "filter.yml" + } + ] +} diff --git a/docs/.docfx/filter.yml b/docs/.docfx/filter.yml new file mode 100644 index 000000000..687afa355 --- /dev/null +++ b/docs/.docfx/filter.yml @@ -0,0 +1,16 @@ +apiRules: + - exclude: + uidRegex: ^Ceen($|\.) + type: Namespace + # The legacy JSON v1 codec and the cppagent v2 codec each ship a type + # named JsonProcessFeed{r,R}ate inside MTConnect.Assets.Json.CuttingTools. + # The two pages collide on case-insensitive output paths (and on + # VitePress's module resolver, which uses lowercase lookups), so the + # legacy v1 variant is excluded; the cppagent v2 type is the surface + # callers integrate against and stays in the reference. + - exclude: + uidRegex: ^MTConnect\.Assets\.Json\.CuttingTools\.JsonProcessFeedrate$ + type: Type + - include: + uidRegex: ^MTConnect + type: Namespace diff --git a/docs/.vitepress/config.ts b/docs/.vitepress/config.ts new file mode 100644 index 000000000..06a0ff8b3 --- /dev/null +++ b/docs/.vitepress/config.ts @@ -0,0 +1,283 @@ +import { defineConfig } from 'vitepress'; +import { withMermaid } from 'vitepress-plugin-mermaid'; + +/** + * VitePress config for the MTConnect.NET documentation site. + * + * The site root is `docs/` (the existing top-level documentation + * directory). Mermaid diagrams are enabled site-wide via + * `vitepress-plugin-mermaid`, so every architecture / sequence / + * class-relationship / state-machine / wire-flow diagram is authored + * in Mermaid (no ASCII art, no external image renders for schematic + * content). + * + * @remarks + * The auto-generated reference section (`/reference/`) is produced by + * `build/MTConnect.NET-DocsGen` at docs-build time; do not edit those + * pages by hand. Adding a new section here that should also feed the + * sidebar — extend both the top `nav:` list and the matching entry in + * `sidebar:`. + * + * @see {@link https://vitepress.dev/reference/site-config} + */ +export default withMermaid( + defineConfig({ + title: 'MTConnect.NET', + description: + 'The .NET implementation of the MTConnect Standard — 100% public-surface API coverage, 100% MTConnect Standard compliance.', + lang: 'en-GB', + + // Output directory for `docs:build`. Default is `docs/.vitepress/dist`; + // overriding here is unnecessary unless we deploy from elsewhere. + // outDir: '.vitepress/dist', + + // Base path. Defaults to '/'. If GitHub Pages publishes under a project + // path (e.g. `/MTConnect.NET/`), this will need to be set at deploy + // time. Left as the default for now. + // base: '/', + + cleanUrls: true, + + // Some narrative pages cross-link to the generated API reference, which + // is produced by docfx in CI (`docs/.docfx/docfx.json`) before VitePress + // builds. The dead-link check is permissive so a local build without the + // API output still completes; CI runs docfx first so production builds + // have the full link graph. + ignoreDeadLinks: true, + + head: [ + ['meta', { name: 'theme-color', content: '#1f6feb' }], + ], + + themeConfig: { + // Top nav: Compliance / Configure & Use / API / Concepts / Wire + // formats / Modules / CLI / Cookbook / Troubleshooting. + nav: [ + { text: 'Getting started', link: '/getting-started' }, + { text: 'Compliance', link: '/compliance/' }, + { text: 'Configure & Use', link: '/configure/' }, + { text: 'Concepts', link: '/concepts/' }, + { text: 'API', link: '/api/' }, + { text: 'Reference', link: '/reference/' }, + { text: 'Wire formats', link: '/wire-formats/' }, + { text: 'Modules', link: '/modules/' }, + { text: 'CLI', link: '/cli/' }, + { text: 'Cookbook', link: '/cookbook/' }, + { text: 'Examples', link: '/examples/' }, + { text: 'Troubleshooting', link: '/troubleshooting/' }, + ], + + // Per-section sidebars. The link targets here are the canonical + // entry points for each section; the API sidebar is generated by + // docfx and merged in at build time. + sidebar: { + '/compliance/': [ + { + text: 'MTConnect Standard compliance', + items: [ + { text: 'Overview', link: '/compliance/' }, + { text: 'Per-version compliance matrix', link: '/compliance/per-version-matrix' }, + { text: 'Wire-format compliance', link: '/compliance/wire-format' }, + { text: 'Spec-source-vs-implementation cross-references', link: '/compliance/spec-cross-references' }, + { text: 'Known divergences from the Standard', link: '/compliance/known-divergences' }, + { text: 'Compliance test harness', link: '/compliance/test-harness' }, + ], + }, + ], + '/configure/': [ + { + text: 'Configure & Use', + items: [ + { text: 'Overview', link: '/configure/' }, + { text: 'Install', link: '/configure/install' }, + { text: 'Agent configuration', link: '/configure/agent-config' }, + { text: 'Adapter configuration', link: '/configure/adapter-config' }, + { text: 'Module configuration', link: '/configure/module-config' }, + ], + }, + { + text: 'Integrations', + items: [ + { text: 'InfluxDB', link: '/configure/integrations/influxdb' }, + { text: 'MQTT — Protocol overview', link: '/configure/integrations/mqtt-protocol' }, + { text: 'MQTT — AWS Greengrass (Moquette)', link: '/configure/integrations/mqtt-aws-greengrass-moquette' }, + { text: 'MQTT — AWS Greengrass (Mqtt-Bridge)', link: '/configure/integrations/mqtt-aws-greengrass-mqtt-bridge' }, + { text: 'MQTT — AWS IoT', link: '/configure/integrations/mqtt-aws-iot' }, + { text: 'MQTT — HiveMQ', link: '/configure/integrations/mqtt-hivemq' }, + { text: 'OpenSSL setup', link: '/configure/integrations/openssl' }, + ], + }, + ], + '/concepts/': [ + { + text: 'Concepts', + items: [ + { text: 'Overview', link: '/concepts/' }, + { text: 'Devices', link: '/concepts/devices' }, + { text: 'Components', link: '/concepts/components' }, + { text: 'Data items', link: '/concepts/data-items' }, + { text: 'Observations', link: '/concepts/observations' }, + { text: 'Assets', link: '/concepts/assets' }, + { text: 'Relationships', link: '/concepts/relationships' }, + ], + }, + ], + '/api/': [ + { + text: 'API reference', + items: [{ text: 'Overview', link: '/api/' }], + }, + ], + '/reference/': [ + { + text: 'Auto-generated reference', + items: [ + { text: 'Overview', link: '/reference/' }, + { text: 'HTTP API', link: '/reference/http-api' }, + { text: 'Environment variables', link: '/reference/environment-variables' }, + { text: 'Configuration schema', link: '/reference/configuration' }, + { text: 'CLI reference', link: '/reference/cli' }, + ], + }, + ], + '/wire-formats/': [ + { + text: 'Wire formats', + items: [ + { text: 'Overview', link: '/wire-formats/' }, + { text: 'XML', link: '/wire-formats/xml' }, + { text: 'JSON v1', link: '/wire-formats/json-v1' }, + { text: 'JSON-CPPAGENT (v2)', link: '/wire-formats/json-v2-cppagent' }, + { text: 'JSON-CPPAGENT-MQTT', link: '/wire-formats/json-v2-cppagent-mqtt' }, + { text: 'SHDR', link: '/wire-formats/shdr' }, + ], + }, + ], + '/modules/': [ + { + text: 'Modules', + items: [ + { text: 'Overview', link: '/modules/' }, + ], + }, + { + text: 'Agent modules', + items: [ + { text: 'HTTP server', link: '/modules/http-server' }, + { text: 'MQTT broker', link: '/modules/mqtt-broker' }, + { text: 'MQTT relay', link: '/modules/mqtt-relay' }, + { text: 'MQTT adapter', link: '/modules/mqtt-adapter' }, + { text: 'HTTP adapter', link: '/modules/http-adapter' }, + { text: 'SHDR adapter', link: '/modules/shdr-adapter' }, + ], + }, + { + text: 'Agent processors', + items: [ + { text: 'Python agent processor', link: '/modules/agent-processor-python' }, + ], + }, + { + text: 'Adapter modules', + items: [ + { text: 'SHDR output', link: '/modules/shdr-output' }, + { text: 'MQTT output', link: '/modules/mqtt-output' }, + ], + }, + ], + '/cli/': [ + { + text: 'CLI tools', + items: [ + { text: 'Overview', link: '/cli/' }, + ], + }, + { + text: 'Shipped CLIs', + items: [ + { text: 'Agent', link: '/cli/agent' }, + { text: 'Adapter', link: '/cli/adapter' }, + ], + }, + { + text: 'Contributor CLIs', + items: [ + { text: 'tools/dotnet.sh', link: '/cli/dotnet-sh' }, + { text: 'tools/test.sh', link: '/cli/test-sh' }, + { text: 'SysML importer', link: '/cli/sysml-import' }, + { text: 'Release builder', link: '/development/builder' }, + ], + }, + ], + '/examples/': [ + { + text: 'Examples', + items: [ + { text: 'Overview', link: '/examples/' }, + { text: 'Embedded agent', link: '/examples/agent-embedded' }, + { text: 'HTTP client', link: '/examples/client-http' }, + { text: 'MQTT client', link: '/examples/client-mqtt' }, + { text: 'SHDR client', link: '/examples/client-shdr' }, + ], + }, + ], + '/development/': [ + { + text: 'Repository development', + items: [ + { text: 'Release builder', link: '/development/builder' }, + ], + }, + ], + '/cookbook/': [ + { + text: 'Cookbook', + items: [ + { text: 'Overview', link: '/cookbook/' }, + { text: 'Write an agent', link: '/cookbook/write-an-agent' }, + { text: 'Write an adapter', link: '/cookbook/write-an-adapter' }, + { text: 'Write a module', link: '/cookbook/write-a-module' }, + { text: 'Configure the MQTT relay', link: '/cookbook/configure-mqtt-relay' }, + { text: 'Write a JSON-MQTT consumer', link: '/cookbook/write-a-json-mqtt-consumer' }, + { text: 'Migrate between versions', link: '/cookbook/migrate-versions' }, + ], + }, + ], + '/troubleshooting/': [ + { + text: 'Troubleshooting', + items: [ + { text: 'Overview', link: '/troubleshooting/' }, + { text: 'Common error modes', link: '/troubleshooting/common-error-modes' }, + { text: 'XSD validation failures', link: '/troubleshooting/xsd-validation-failures' }, + { text: 'Schema version mismatches', link: '/troubleshooting/schema-version-mismatches' }, + { text: 'MQTT TLS handshake', link: '/troubleshooting/mqtt-tls-handshake' }, + ], + }, + ], + }, + + socialLinks: [ + { icon: 'github', link: 'https://github.com/TrakHound/MTConnect.NET' }, + ], + + footer: { + message: 'Released under the MIT License.', + copyright: 'Copyright © TrakHound Inc.', + }, + + search: { + provider: 'local', + }, + }, + + // Mermaid plugin options — leave at sensible defaults so diagrams pick + // up the site's light/dark theme automatically. + mermaid: { + // example: securityLevel: 'loose', + }, + mermaidPlugin: { + class: 'mermaid my-mermaid', + }, + }) +); diff --git a/docs/README.md b/docs/README.md new file mode 100644 index 000000000..4be3abac8 --- /dev/null +++ b/docs/README.md @@ -0,0 +1,59 @@ +# MTConnect.NET documentation site + +VitePress-based documentation site for `MTConnect.NET`, rooted at this `docs/` directory. + +## Prerequisites + +- Node.js 18 or newer (Node 20 LTS recommended). +- `npm` (bundled with Node). + +## Local development + +From the repository root: + +```bash +npm install # one-time install of VitePress + the Mermaid plugin +npm run docs:dev # serves at http://localhost:5173 +``` + +The dev server hot-reloads on every save. Edit any `docs/**/*.md` and the open browser tab updates in place. + +## Build a static bundle + +```bash +npm run docs:build # produces docs/.vitepress/dist/ +npm run docs:preview # serves the built bundle locally for a final pass +``` + +The build output lands in `docs/.vitepress/dist/` and is excluded from version control. + +## Mermaid diagrams + +Every architecture / sequence / class-relationship / state-machine / wire-flow diagram in this site is authored in [Mermaid](https://mermaid.js.org/) — no ASCII art, no external image renders for schematic content. Mermaid is enabled via `vitepress-plugin-mermaid` (configured in `docs/.vitepress/config.ts`). + +To author a diagram in any markdown page: + +````markdown +```mermaid +flowchart TD + A[Step one] --> B[Step two] +``` +```` + +Mermaid syntax is documented at . + +## Layout + +- `docs/index.md` — landing page. +- `docs/getting-started.md` — quickstart walkthrough. +- `docs/
/index.md` — the index page for each top-level section. +- `docs/
/.md` — the leaf pages within a section. +- `docs/.vitepress/config.ts` — site config (nav, sidebar, Mermaid plugin, base URL). +- `docs/.vitepress/dist/` — build output (excluded from version control). + +## Authoring conventions + +- Internal links use site-relative paths (`/configure/agent`, not `../configure/agent.md`). +- Code samples include the target language fence (` ```csharp `, ` ```bash `, ` ```yaml `). +- External links use the full URL. +- The site is configured with `cleanUrls: true`; pages are linked without the `.md` suffix. diff --git a/docs/api/index.md b/docs/api/index.md new file mode 100644 index 000000000..6d5fb278f --- /dev/null +++ b/docs/api/index.md @@ -0,0 +1,46 @@ +# API reference + +The API reference documents every public class, interface, record, struct, enum, and delegate in every shipped `MTConnect.NET` NuGet package. Each page is generated from the library's XML doc comments and the compiled assembly metadata, then surfaced under a flat `Namespace.Type.md` layout you can search from the top bar or browse from the sidebar. + +## How the reference is generated + +The pages under `docs/api/` are produced by [docfx](https://dotnet.github.io/docfx/) from the Release `net8.0` build of every shipped library. The build is reproducible — `bash docs/scripts/generate-api-ref.sh` rebuilds the libraries and regenerates the Markdown locally; the same script runs in CI ahead of every VitePress build. + +The configuration lives at `docs/.docfx/docfx.json` and explicitly lists each library DLL the reference covers. Adding a new library is a two-line change there plus a row in the regen script. + +## What each type page contains + +- **Type signature**, namespace, the source assembly, base class, and implemented interfaces. +- **Every public member** — methods, properties, events, fields — with parameter docs, return docs, and exception docs sourced from the library's `` / `` / `` / `` comments. +- **Inherited members** linked back to the declaring type. +- **Code samples** for any member whose XML doc comment includes an `` block. + +## Packages covered + +| Library | Assembly | Audience | +| --- | --- | --- | +| `MTConnect.NET-Common` | `MTConnect.NET-Common.dll` | Agents, devices, components, data items, observations, assets, configurations. | +| `MTConnect.NET-DeviceFinder` | `MTConnect.NET-DeviceFinder.dll` | Network-scan helpers that locate live MTConnect agents on a subnet. | +| `MTConnect.NET-HTTP` | `MTConnect.NET-HTTP.dll` | HTTP client + server, REST endpoints, content negotiation. | +| `MTConnect.NET-JSON` | `MTConnect.NET-JSON.dll` | Legacy JSON v1 codec. | +| `MTConnect.NET-JSON-cppagent` | `MTConnect.NET-JSON-cppagent.dll` | cppagent-parity JSON v2 codec. | +| `MTConnect.NET-MQTT` | `MTConnect.NET-MQTT.dll` | MQTT client + broker integration, topic templates. | +| `MTConnect.NET-Protobuf` | `MTConnect.NET-Protobuf.dll` | Protobuf wire-format codec and gRPC plumbing. | +| `MTConnect.NET-Services` | `MTConnect.NET-Services.dll` | Long-running service host (Windows service / systemd) plumbing. | +| `MTConnect.NET-SHDR` | `MTConnect.NET-SHDR.dll` | SHDR adapters and clients. | +| `MTConnect.NET-SysML` | `MTConnect.NET-SysML.dll` | SysML XMI importer infrastructure consumed by the regen tool. | +| `MTConnect.NET-TLS` | `MTConnect.NET-TLS.dll` | TLS helpers shared by HTTP and MQTT. | +| `MTConnect.NET-XML` | `MTConnect.NET-XML.dll` | XML codec and XSD validation. | +| `MTConnect.NET` | `MTConnect.NET.dll` | Top-level umbrella package and convenience builders. | + +`MTConnect.NET-HTTP-AspNetCore` is the only shipped library currently excluded from the reference. Its project targets `netcoreapp3.1`–`net7.0` and cannot resolve its `net8.0` `ProjectReference` dependencies under the current Debug build, so docfx has no assembly to load. Once the TFM matrix is widened to include `net8.0` the library joins the table here and the regen script picks it up automatically. + +## Finding what you need + +- Use the search box at the top of the site for a type or member by name. +- Use the left-hand sidebar to browse by namespace. +- If you arrived here from a narrative page, the link will resolve to the specific type and member that page references. + +## Spec-version metadata + +Every type added or deprecated under a specific MTConnect spec version carries `[MinimumVersion]` / `[MaximumVersion]` attributes. Those values appear in the type's XML doc summary; the docfx output preserves them. For the per-version spec-coverage matrix at the library level, see [Compliance](/compliance/). diff --git a/docs/cli/adapter.md b/docs/cli/adapter.md new file mode 100644 index 000000000..5f4ce4d90 --- /dev/null +++ b/docs/cli/adapter.md @@ -0,0 +1,178 @@ +# Adapter CLI + +`MTConnect-Adapter` is the standalone adapter host. It loads an `adapter.config.yaml` (or `adapter.config.json`) configuration file, builds an `MTConnectAdapter` per configured output module, wires the configured `DataSource` into the input side, and pumps observations downstream to one or more MTConnect agents. + +The CLI surface is defined by `MTConnectAdapterApplication.Run(args)` in `adapter/MTConnect.NET-Applications-Adapter/MTConnectAdapterApplication.cs`. The shipped `mtconnect.net-adapter` binary in `adapter/MTConnect.NET-Adapter/` is a thin entry point that constructs a `DataSource` and calls `Run(args, true)` on the application class. Embedders that build their own adapter from `MTConnect.NET-Applications-Adapter` get the same CLI surface. + +## Synopsis + +```text +mtconnect.net-adapter [help|install|install-start|start|stop|remove|debug|run|run-service] [configuration_file] +``` + +If no command is given, the adapter runs in `run` mode (foreground, info-level logging). If no configuration file is given, the adapter looks for `adapter.config.yaml` in the executable's directory, copying `adapter.config.default.yaml` into place if it does not exist. + +## Commands + +| Command | Description | +|---|---| +| `help` | Print usage information and exit. | +| `run` | Run the adapter in the foreground at info-level logging. Default when no command is supplied. Blocks until killed. | +| `debug` | Run the adapter in the foreground at **debug-level** logging on the console target. | +| `run-service` | Run the adapter as a Windows service (non-blocking). On non-Windows operating systems the adapter logs that the command is unsupported and exits. | +| `install` | Install the adapter as a Windows service. Windows only. Stops and removes any existing service of the same name first. | +| `install-start` | Install the adapter as a Windows service and start it immediately. Windows only. | +| `start` | Start the previously installed Windows service. Windows only. | +| `stop` | Stop the Windows service. Windows only. | +| `remove` | Stop and remove the Windows service. Windows only. | + +Unlike the [agent CLI](./agent), the adapter does not have a `trace` command and does not have a `reset` command (the adapter does not own a persistent buffer in the way the agent does). + +## Arguments + +| Argument | Description | +|---|---| +| `configuration_file` | Path to the adapter configuration file. Absolute or relative to the executable's directory. If omitted, the adapter looks for `adapter.config.yaml` in the executable's directory and copies `adapter.config.default.yaml` into place if it does not exist. | + +## Example invocations + +Run in the foreground against an explicit config file: + +```bash +./mtconnect.net-adapter run /etc/mtconnect/adapter.config.yaml +``` + +Run with debug-level console logging while bringing up a new data source: + +```bash +./mtconnect.net-adapter debug +``` + +Install the adapter as a Windows service and start it: + +```powershell +.\mtconnect.net-adapter.exe install-start C:\ProgramData\MTConnect\adapter.config.yaml +``` + +Run from source against the default config during development: + +```bash +dotnet run --project adapter/MTConnect.NET-Adapter -- debug +``` + +## Configuration file + +The adapter reads YAML by default (CamelCase keys). Default filenames live alongside the adapter binary: + +| File | Role | +|---|---| +| `adapter.config.yaml` | Active configuration. | +| `adapter.config.json` | Alternative active configuration, JSON format. | +| `adapter.config.default.yaml` | Shipped default. Copied to `adapter.config.yaml` on first run if the active file does not exist. | +| `NLog.config` | NLog configuration shipped alongside the adapter binary. | + +The active configuration is reloaded when `monitorConfigurationFiles: true` is set (the default) and the file is edited at runtime, with a minimum gap of `configurationFileRestartInterval` seconds between restarts. + +### Top-level keys + +Backed by `AdapterApplicationConfiguration` in `libraries/MTConnect.NET-Common/Configurations/`. + +| Key (YAML) | Type | Default | Description | +|---|---|---|---| +| `changeToken` | string | new GUID per save | Internal token regenerated when the adapter rewrites the file. | +| `id` | string | a random 6-character string per fresh config | Unique identifier for this adapter instance. Used when the adapter participates in a topology with several siblings. | +| `deviceKey` | string | `null` | Name or UUID of the MTConnect device the adapter is producing observations for. Must match the device's `name=` or `uuid=` in the downstream agent's `Devices.xml`. | +| `readInterval` | int (ms) | `100` | Interval at which the configured `DataSource` is polled for new values. | +| `writeInterval` | int (ms) | `100` | Interval at which queued observations are flushed to the downstream agent. | +| `filterDuplicates` | bool | `true` | When `true`, observations whose value equals the previous observation for the same data item are dropped at the adapter (the agent does the same on its end, but the early filter saves wire bytes). | +| `outputTimestamps` | bool | `true` | When `true`, the adapter prepends a timestamp to every emitted SHDR line. Set to `false` only if the downstream agent is configured with `ignoreTimestamps: true` and you want the agent's clock to win. | +| `enableBuffer` | bool | `false` | When `true`, the adapter queues observations between `writeInterval` ticks rather than sending each one as it arrives. Send-on-flush gives consistent batching at the cost of up to `writeInterval` ms of latency per observation. | +| `serviceName` | string | `null` (falls back to a per-platform default) | Windows-service short name. Lets multiple adapters coexist on one machine. | +| `serviceAutoStart` | bool | `true` | Windows-service start type. `true` = Automatic, `false` = Manual. | +| `monitorConfigurationFiles` | bool | `true` | Restart the adapter when `adapter.config.yaml` changes on disk. | +| `configurationFileRestartInterval` | int (seconds) | `2` | Minimum gap between auto-restarts triggered by the file watcher. | +| `engine` | map | `{}` | Free-form key/value pairs forwarded to the `DataSource` for source-specific configuration (e.g. a serial port name, a host address, an OPC UA endpoint). Accessed by the data source via `GetEngineProperty(name)`. | +| `modules` | list of single-key maps | `[]` | Each entry instantiates one adapter output module. See [Modules](/modules/) for the per-module schema. | + +### Module list shape + +`modules` is a YAML sequence where each element is a single-key map keyed by the module name. Each module's value object is the module's per-instance configuration. + +```yaml +modules: + - shdr: + port: 7878 + - mqtt: + server: localhost + port: 1883 +``` + +The two adapter output modules shipped today are: + +- **`shdr`** — the SHDR socket server. Backed by `MTConnect.NET-AdapterModule-SHDR`. The downstream agent connects on `port` via a `shdr-adapter` module. See [Modules](/modules/) for the full SHDR key set. +- **`mqtt`** — the MQTT publisher. Backed by `MTConnect.NET-AdapterModule-MQTT`. Publishes observations to `server:port` on the configured topic tree. See [Modules](/modules/) for the full MQTT key set. + +Multiple instances of the same module are allowed; each entry is a distinct module instance. + +### Engine block — data-source-specific settings + +The `engine` map is free-form. Whatever keys you write there become accessible to the `DataSource` implementation via `configuration.GetEngineProperty("keyName")`. The shipped `DataSource` in `adapter/MTConnect.NET-Adapter/DataSource.cs` is a stub — embedders override it. Examples: + +```yaml +engine: + serialPort: COM3 + baudRate: 115200 + parity: None +``` + +```yaml +engine: + opcUaEndpoint: opc.tcp://192.168.1.50:4840 + username: mtconnect +``` + +## Sample shipped default + +The default config shipped at `adapter/MTConnect.NET-Adapter/adapter.config.default.yaml` wires an SHDR module on port `7878` and an MQTT module on `localhost:1883` for the device `OKUMA-Lathe`: + +```yaml +id: PatrickAdapter +deviceKey: OKUMA-Lathe + +modules: + - shdr: + port: 7878 + - mqtt: + server: localhost + port: 1883 +``` + +Edit `deviceKey`, the SHDR `port`, and the MQTT endpoint to match your topology before pointing the adapter at a real data source. + +## NLog configuration + +Logging is routed through NLog. The shipped `NLog.config` defines the following named loggers: + +| Logger name | Used for | +|---|---| +| `application-logger` | Application-level events: config load, service install / start / stop, fatal errors. | +| `adapter-logger` | Adapter-pump events: data-source reads, observation flushes. | +| `module` | Module-loaded, module-start, module-stop, and module-side log events. | + +To raise the console target to debug-level on a single run, use the `debug` command. To raise it permanently, edit `NLog.config`. + +## Exit behavior + +- `run`, `debug` block forever; `Ctrl+C` / SIGINT triggers a graceful shutdown that flushes pending observations and runs every module's `Stop()` hook. +- `run-service` returns control to the service controller; lifecycle is managed by Windows. +- `install`, `install-start`, `start`, `stop`, `remove`, `help` complete and exit. + +## See also + +- [Configure & Use → Configure an adapter](/configure/adapter) — annotated end-to-end `adapter.config.yaml` walkthrough plus data-source bring-up. +- [Configure & Use → Run](/configure/run) — local-dev, Windows-service, and systemd-unit deployment. +- [Modules](/modules/) — per-module configuration schemas referenced by the `modules:` list. +- [API reference → `MTConnect.Applications.MTConnectAdapterApplication`](/api/) — the C# class that backs the CLI. +- [API reference → `MTConnect.Configurations.AdapterApplicationConfiguration`](/api/) — the configuration POCO the YAML deserializes into. +- [API reference → `MTConnect.Adapters.MTConnectAdapter`](/api/) — the inner adapter type that orchestrates `WriteObservations` / `WriteAssets` / `WriteDevices`. +- [Agent CLI](./agent) — the sibling agent host that consumes the adapter's output. diff --git a/docs/cli/agent.md b/docs/cli/agent.md new file mode 100644 index 000000000..352c31e31 --- /dev/null +++ b/docs/cli/agent.md @@ -0,0 +1,173 @@ +# Agent CLI + +`MTConnect-Agent` is the standalone HTTP agent host. It loads an `agent.config.yaml` (or `agent.config.json`) configuration file, builds an `MTConnectAgentBroker`, instantiates every configured agent module, and runs them inside a single process that can be invoked from a terminal, hosted as a Windows service, or run as a systemd unit. + +The CLI surface is defined by `MTConnectAgentApplication.Run(args)` in `agent/MTConnect.NET-Applications-Agents/MTConnectAgentApplication.cs`. The shipped `mtconnect.net-agent` binary in `agent/MTConnect.NET-Agent/` is a thin entry point that calls `Run(args, true)` on this class. Embedders that scaffold their own agent from the `MTConnect.NET-Agent-Template` NuGet template get the same CLI surface for free. + +## Synopsis + +```text +mtconnect.net-agent [help|install|install-start|start|stop|remove|debug|run|run-service] [configuration_file] +``` + +If no command is given, the agent runs in `run` mode (foreground, info-level logging). If no configuration file is given, the agent looks for `agent.config.json` first, then `agent.config.yaml`, then copies `agent.config.default.yaml` into place if neither file exists. + +## Commands + +| Command | Description | +|---|---| +| `help` | Print usage information and exit. | +| `run` | Run the agent in the foreground at info-level logging. Default when no command is supplied. The process blocks until killed with `Ctrl+C` or SIGINT. | +| `debug` | Run the agent in the foreground at **debug-level** logging on the console target. Same lifecycle as `run`. | +| `trace` | Run the agent in the foreground at **trace-level** logging on the console target. Same lifecycle as `run`. | +| `run-service` | Run the agent as a Windows service (non-blocking). On non-Windows operating systems the agent logs that the command is unsupported and exits. | +| `install` | Install the agent as a Windows service. Windows only. Stops and removes any existing service of the same name first. | +| `install-start` | Install the agent as a Windows service and immediately start it. Windows only. | +| `start` | Start the previously installed Windows service. Windows only. | +| `stop` | Stop the Windows service. Windows only. | +| `remove` | Stop and remove the Windows service. Windows only. | +| `reset` | Clear the durable observation buffer, the durable asset buffer, and the file-index directory at `durableBufferPath`. Use after a corrupted shutdown or when a fresh-state restart is wanted. | + +## Arguments + +| Argument | Description | +|---|---| +| `configuration_file` | Path to the agent configuration file. Absolute or relative to the executable's directory. If omitted, the agent looks for `agent.config.json`, then `agent.config.yaml`, in the executable's directory, and copies `agent.config.default.yaml` into place if neither exists. | + +## Example invocations + +Run in the foreground against an explicit config file: + +```bash +./mtconnect.net-agent run /etc/mtconnect/agent.config.yaml +``` + +Run with debug-level console logging while developing a new module: + +```bash +./mtconnect.net-agent debug +``` + +Install the agent as a Windows service named per `serviceName` in the config and start it immediately: + +```powershell +.\mtconnect.net-agent.exe install-start C:\ProgramData\MTConnect\agent.config.yaml +``` + +Clear the durable buffer (e.g. after schema-incompatible config changes): + +```bash +./mtconnect.net-agent reset +``` + +Run from source against an embedded `agent.config.yaml` during development: + +```bash +dotnet run --project agent/MTConnect.NET-Agent -- debug +``` + +## Configuration file + +The agent reads YAML by default (CamelCase keys). JSON is also accepted; when both are present, JSON takes precedence and is converted to YAML on first run. Default filenames live alongside the agent binary: + +| File | Role | +|---|---| +| `agent.config.yaml` | The active configuration. | +| `agent.config.json` | Alternative active configuration, JSON format. | +| `agent.config.default.yaml` | Shipped default. Copied to `agent.config.yaml` on first run if neither active file exists. | +| `NLog.config` | NLog configuration. Copied from `NLog.default.config` on first run if missing. | +| `Devices.xml` | Device-information-model file (or directory) loaded into the agent. Path comes from the `devices` key in the config. | + +The active configuration is reloaded when `monitorConfigurationFiles: true` is set (the default) and the file is edited at runtime, with a minimum gap of `configurationFileRestartInterval` seconds between restarts. + +### Top-level keys + +Backed by `AgentApplicationConfiguration` and the inherited `AgentConfiguration` base. + +| Key (YAML) | Type | Default | Description | +|---|---|---|---| +| `changeToken` | string | new GUID per save | Internal token regenerated whenever the agent rewrites the file. Surfaces in the Agent device's `mtconnect:ChangeToken` data item so consumers can detect config rewrites. | +| `devices` | string | `null` | Path to a single `Devices.xml` file or to a directory containing one or more `*.xml` device files. Absolute, or relative to the executable. | +| `serviceName` | string | `MTConnect.NET-Agent` | Windows-service short name. Lets multiple agents coexist on one machine. | +| `serviceDisplayName` | string | `MTConnect.NET Agent` | Windows-service display name shown in `services.msc`. | +| `serviceDescription` | string | `MTConnect Agent to provide access to device information using the MTConnect Standard` | Windows-service description text. | +| `serviceAutoStart` | bool | `true` | Windows-service start type. `true` = Automatic, `false` = Manual. | +| `observationBufferSize` | uint | `131072` | Maximum number of observations the in-memory ring buffer retains. The default config shipped in `agent.config.default.yaml` overrides this to `150000`. | +| `assetBufferSize` | uint | `1024` | Maximum number of assets retained. Default config overrides to `1000`. | +| `durable` | bool | `false` | When `true`, observation and asset buffers persist to disk and are reloaded on restart. | +| `durableBufferPath` | string | `null` (defaults to a sub-directory of the executable's dir) | Base directory for the durable buffers when `durable: true`. | +| `useBufferCompression` | bool | `false` | Compress the durable buffers on disk. | +| `monitorConfigurationFiles` | bool | `true` | Restart the agent when `agent.config.yaml`, `NLog.config`, or any device file changes on disk. | +| `configurationFileRestartInterval` | int (seconds) | `2` | Minimum gap between auto-restarts triggered by the file watcher. Prevents thrash when an editor writes multiple times in quick succession. | +| `timezoneOutput` | string (IANA tz name) | `null` (use system local) | TimeZone applied to timestamps emitted by the agent. | +| `ignoreTimestamps` | bool | `false` | When `true`, every incoming observation has its timestamp overwritten with the agent's clock. Trades client-side clock accuracy for clock-drift correction. | +| `defaultVersion` | string (e.g. `"2.5"`) | `MTConnectVersions.Max` (`2.5` in the current build) | MTConnect spec version applied to response documents when the request URL does not pin a version. The shipped default config overrides this to `2.2`. | +| `convertUnits` | bool | `true` | Convert observation values to the units declared on the data item when they arrive in a different compatible unit. | +| `ignoreObservationCase` | bool | `false` | Case-insensitive comparison of incoming observation values to the data item's value-space (CONDITION severities, enum members, etc.). | +| `enableValidation` | bool | `false` | Emit per-observation validation diagnostics on the `agent-validation` logger. | +| `inputValidationLevel` | enum: `Ignore` (`0`), `Warning` (`1`), `Remove` (`2`), `Strict` (`3`) | `Warning` | What the agent does when an observation or asset arrives that fails validation. `Ignore` accepts everything; `Warning` accepts and logs; `Remove` rejects but does not log; `Strict` rejects and logs. | +| `enableAgentDevice` | bool | `true` | Whether the agent emits its own meta-device (`Agent`) on `/probe`, exposing availability and the `mtconnect:ChangeToken` data item. | +| `enableMetrics` | bool | `true` | Emit per-minute observation-rate and asset-update-rate metrics on the `agent-metrics` logger. | +| `modules` | list of single-key maps | `[]` | Each entry instantiates one agent module. See [Modules](/modules/) for the per-module schema. | +| `processors` | list of single-key maps | `[]` | Each entry instantiates one observation-pipeline processor. | + +### Module list shape + +`modules` is a YAML sequence where each element is a single-key map keyed by the module name. Each module's value object is the module's per-instance configuration; the module catalog documents each schema. + +```yaml +modules: + - http-server: + port: 5000 + documentFormat: xml + indentOutput: true + - mqtt-relay: + server: localhost + port: 1883 + durableRelay: true + - shdr-adapter: + deviceKey: M12346 + hostname: localhost + port: 7878 +``` + +Multiple instances of the same module are allowed — each entry produces a distinct module instance keyed by its position in the list. See [Modules](/modules/) for the available module names and their per-module config keys. + +### Processor list shape + +`processors` follows the same single-key-map-per-entry shape as `modules`. Each processor is a hook into the observation pipeline that runs between the adapter intake and the buffer write. The processor catalog lives under [API reference → MTConnect.Processors](/api/). + +### Devices file + +The `devices` key points at one `Devices.xml` file or at a directory containing several. The schema is the MTConnect Devices envelope; each device's `` and `` graph drives what the agent exposes on `/probe`. The agent re-reads the device file when `monitorConfigurationFiles: true` is set. See [Configure & Use → Configure an agent](/configure/agent) for an annotated `Devices.xml` example. + +## NLog configuration + +Logging is routed through NLog. The shipped `NLog.default.config` defines the following named loggers: + +| Logger name | Used for | +|---|---| +| `application-logger` | Application-level events: config load, service install / start / stop, fatal errors. | +| `agent-logger` | Agent-broker events: device registration, observation ingest, response generation. | +| `agent-metrics` | Per-minute observation- and asset-rate metrics (when `enableMetrics: true`). | +| `agent-validation` | Per-observation validation diagnostics (when `enableValidation: true`). | +| `module` | Module-loaded, module-start, module-stop, and module-side log events. | +| `processor` | Processor-loaded, processor-applied, and processor-side log events. | + +To raise the console target to `Debug` or `Trace` on a single run without editing `NLog.config`, use the `debug` or `trace` CLI command. To raise it permanently, edit `NLog.config` (the agent will pick the change up automatically when `monitorConfigurationFiles: true`). + +## Exit behavior + +- `run`, `debug`, `trace` block forever; `Ctrl+C` / SIGINT triggers a graceful shutdown that drains the buffers and runs every module's `Stop()` hook. +- `run-service` returns control to the service controller; lifecycle is managed by Windows. +- `install`, `install-start`, `start`, `stop`, `remove`, `reset`, `help` complete and exit. + +## See also + +- [Configure & Use → Configure an agent](/configure/agent) — annotated end-to-end `agent.config.yaml` walkthrough. +- [Configure & Use → Run](/configure/run) — local-dev, Docker, Windows-service, and systemd-unit deployment. +- [Modules](/modules/) — per-module configuration schemas referenced by the `modules:` list. +- [API reference → `MTConnect.Applications.MTConnectAgentApplication`](/api/) — the C# class that backs the CLI. +- [API reference → `MTConnect.Configurations.AgentApplicationConfiguration`](/api/) — the configuration POCO the YAML deserializes into. +- [API reference → `MTConnect.Configurations.AgentConfiguration`](/api/) — the base class that holds the buffer / version / validation knobs. +- [Adapter CLI](./adapter) — the sibling adapter host, run separately from the agent. diff --git a/docs/cli/dotnet-sh.md b/docs/cli/dotnet-sh.md new file mode 100644 index 000000000..a77eb20f9 --- /dev/null +++ b/docs/cli/dotnet-sh.md @@ -0,0 +1,122 @@ +# `tools/dotnet.sh` + +`tools/dotnet.sh` wraps every `dotnet` invocation that contributor scripts make inside the repo. By default it forwards to the host `dotnet` on `PATH`. When passed `--docker` (or with `MTCONNECT_DOTNET_USE_DOCKER=1` exported), it instead runs `dotnet` inside an official `mcr.microsoft.com/dotnet/sdk` container with the repo bind-mounted at `/src`. + +This is a **contributor** tool. End users running the shipped agent or adapter binaries do not need it. + +A PowerShell sibling lives at `tools/dotnet.ps1` with the same semantics and the same flag spelling (`-Docker` instead of `--docker`). + +## Synopsis + +```text +tools/dotnet.sh [--docker | -d] +``` + +Or equivalently with the environment variable: + +```bash +MTCONNECT_DOTNET_USE_DOCKER=1 tools/dotnet.sh +``` + +## Flags + +| Flag | Description | +|---|---| +| `--docker`, `-d` | Run the `dotnet` invocation inside a `mcr.microsoft.com/dotnet/sdk` container instead of using the host `dotnet`. Equivalent to exporting `MTCONNECT_DOTNET_USE_DOCKER=1` for the call. Must be the first argument if passed; subsequent arguments are forwarded verbatim to `dotnet` inside the container. | + +Every other argument is passed straight through to `dotnet`. The wrapper does no parsing of the inner command line. + +## Environment variables + +| Variable | Default | Description | +|---|---|---| +| `MTCONNECT_DOTNET_USE_DOCKER` | `0` | Set to `1` to force docker mode without supplying `--docker` per call. Useful in CI when every step should be containerized. | +| `MTCONNECT_DOTNET_SDK_TAG` | `8.0` | SDK image tag suffix. The wrapper resolves `mcr.microsoft.com/dotnet/sdk:${MTCONNECT_DOTNET_SDK_TAG}` when the full image is not overridden. Set to `9.0` to test against the .NET 9 SDK, `6.0` to test against .NET 6, etc. | +| `MTCONNECT_DOTNET_IMAGE` | `mcr.microsoft.com/dotnet/sdk:${MTCONNECT_DOTNET_SDK_TAG}` | Full container image to run. Override to pin to a digest, use a private registry, or swap in a debug-tagged SDK image. | +| `MTCONNECT_NUGET_VOLUME` | `mtconnect-net-nuget` | Named docker volume mounted at `/root/.nuget/packages` inside the container. Persists the NuGet cache across runs. Set to a different name to isolate per-branch caches. | +| `MTCONNECT_DOTNET_TOOLS_VOLUME` | `mtconnect-net-dotnet-tools` | Named docker volume mounted at `/root/.dotnet/tools` inside the container. Persists `dotnet tool` installations (reportgenerator, etc.) across runs. | +| `MTCONNECT_DOTNET_E2E_DIND` | `0` | Set to `1` to force the docker-in-docker pass-through (host network + bind-mounted `/var/run/docker.sock` + the host's `docker` CLI bind-mounted in) even when the invocation does not look like an E2E run. The wrapper enables this automatically when the dotnet args reference `tests/IntegrationTests`, `tests/E2E/`, an `IntegrationTests.csproj` file, or `tests/Compliance/`. | + +When E2E pass-through is active, the wrapper also exports the following into the container: + +- `MTCONNECT_E2E_DOCKER=true` — gates the `[Category("RequiresDocker")]` test filter. +- `TESTCONTAINERS_RYUK_DISABLED=true` — the Testcontainers Ryuk reaper does not work cleanly inside the SDK image, so the wrapper disables it. Containers spawned by the test run are cleaned up by the test fixtures themselves. +- `MTCONNECT_E2E_HOST_REPO_ROOT=` — Testcontainers code that needs to bind-mount fixtures into spawned containers reads this to translate from in-container `/src` paths to the host path the docker daemon will see. + +## Example invocations + +Native (host `dotnet`): + +```bash +tools/dotnet.sh build MTConnect.NET.sln +tools/dotnet.sh test tests/MTConnect.NET-Common-Tests +tools/dotnet.sh tool restore +``` + +Containerized SDK: + +```bash +tools/dotnet.sh --docker build MTConnect.NET.sln +tools/dotnet.sh -d test tests/MTConnect.NET-Common-Tests --configuration Release +``` + +Containerized against a specific SDK version: + +```bash +MTCONNECT_DOTNET_SDK_TAG=9.0 tools/dotnet.sh --docker build MTConnect.NET.sln +``` + +Containerized E2E run — the wrapper detects the test path and enables docker-in-docker automatically: + +```bash +tools/dotnet.sh --docker test tests/E2E/MTConnect.NET-E2E-Agent +``` + +Forced docker-in-docker for a custom invocation that the auto-detection misses: + +```bash +MTCONNECT_DOTNET_E2E_DIND=1 tools/dotnet.sh --docker test tests/MyCustomDockerTest +``` + +Reusing the wrapper from inside another script (this is how `tools/test.sh` invokes it): + +```bash +DOTNET=(tools/dotnet.sh) +if [[ "${USE_DOCKER}" == "1" ]]; then + export MTCONNECT_DOTNET_USE_DOCKER=1 +fi +"${DOTNET[@]}" tool restore +"${DOTNET[@]}" build MTConnect.NET.sln --configuration Release +``` + +## Behavior + +### Native path (default) + +1. Resolve the repo root by walking up from `tools/dotnet.sh`. +2. `cd` into the repo root (so `dotnet` picks up `Directory.Build.props`, `Directory.Packages.props`, and the `MTConnect.NET.sln` solution file). +3. `exec dotnet "$@"`. + +### Docker path + +1. Resolve the SDK image (`MTCONNECT_DOTNET_IMAGE`, else `mcr.microsoft.com/dotnet/sdk:${MTCONNECT_DOTNET_SDK_TAG}`). +2. Resolve the NuGet and tools volumes by name. +3. If the invocation looks like an E2E run (or `MTCONNECT_DOTNET_E2E_DIND=1` is set), add `--network=host`, mount `/var/run/docker.sock`, bind-mount the host's `docker` CLI binary read-only, and export the three E2E environment variables listed above. +4. Run `docker run --rm` with: + - `/src` bind-mounted to the repo root. + - The named volumes for NuGet and dotnet tools mounted at the standard paths. + - `HOME=/root`, `PATH` extended to include `/root/.dotnet/tools`. + - `DOTNET_NOLOGO=1` and `DOTNET_CLI_TELEMETRY_OPTOUT=1`. +5. `dotnet "$@"` runs inside the container; the process is `exec`-ed so `tools/dotnet.sh`'s own PID is replaced by `docker run`. + +## Platform notes + +- **Linux**: the wrapper uses `cd -P` and `readlink` carefully to be portable; it does not depend on `readlink -f`. Works on Debian / Ubuntu / Fedora out of the box. +- **macOS**: tested under `bash` 3.2 (the system default) and bash 5.x from Homebrew. The wrapper avoids bash-4-only features for the macOS-default-bash path. +- **Windows**: use the PowerShell sibling at `tools/dotnet.ps1` (same flag spelling: `-Docker`). The shell wrapper works inside Git-Bash or WSL too. + +## See also + +- [`tools/test.sh`](./test-sh) — the test entry point that invokes this wrapper for every `dotnet test` run. +- [Configure & Use → Run](/configure/run) — running the shipped agent and adapter (where end users do not need this wrapper). +- [Compliance → Test harness](/compliance/test-harness) — running the per-spec-version conformance suite (uses `tools/test.sh --compliance`, which routes through this wrapper). diff --git a/docs/cli/index.md b/docs/cli/index.md new file mode 100644 index 000000000..4cfc1cb0c --- /dev/null +++ b/docs/cli/index.md @@ -0,0 +1,28 @@ +# CLI tools + +Reference pages for every shipped and in-repo command-line tool that the `MTConnect.NET` codebase exposes. Each page lists the supported subcommands or flags, an example invocation that runs against a real working directory, the config-file knobs the tool honors (with defaults and permissible values), and cross-links into the rest of the docs. + +## Shipped CLIs + +These tools ship as released binaries (or NuGet templates that produce released binaries). End users run them in production. + +- **[Agent](./agent)** — `MTConnect-Agent`. The standalone HTTP agent host. Hosts the `MTConnectAgentBroker`, every configured agent module (HTTP server, MQTT broker, MQTT relay, SHDR adapter, MQTT adapter, HTTP adapter), and the Windows-service / systemd-unit lifecycle wrappers. Reads `agent.config.yaml` (or `agent.config.json`) at startup. +- **[Adapter](./adapter)** — `MTConnect-Adapter`. The standalone adapter host. Pumps observations from a data source (SHDR socket, MQTT topic, or a custom `DataSource` implementation) into a downstream agent. Reads `adapter.config.yaml` at startup. + +## Contributor CLIs + +These tools live in the repo but are not shipped to end users. They exist for contributors working on the codebase itself. + +- **[`tools/dotnet.sh`](./dotnet-sh)** — wraps the `dotnet` CLI so every contributor command runs against either the host `dotnet` on `PATH` or an official `mcr.microsoft.com/dotnet/sdk` container. Used by every other contributor script in the repo. +- **[`tools/test.sh`](./test-sh)** — the local test entry point. Iterates every `tests/**/*.csproj`, optionally pulls in the Compliance tier and the Docker-gated E2E tier, and emits a unified coverage report under `coverage-report/`. +- **[SysML importer](./sysml-import)** — `MTConnect.NET-SysML-Import`. Parses an `MTConnectSysMLModel.xml` (the XMI export of the standard's SysML model) and regenerates the `*.g.cs` source files under `libraries/MTConnect.NET-Common/`, `libraries/MTConnect.NET-XML/`, and `libraries/MTConnect.NET-JSON-cppagent/`. Run by maintainers when a new spec version lands. + +A PowerShell sibling lives alongside each shell script (`tools/dotnet.ps1`, `tools/test.ps1`) with identical semantics and flag names. Each shell-script page calls out the parameter spelling difference; the underlying behavior is the same on Windows, macOS, and Linux. + +## Cross-references + +- [Configure & Use → Configure an agent](/configure/agent) — how to author the `agent.config.yaml` file the agent CLI reads. +- [Configure & Use → Configure an adapter](/configure/adapter) — how to author the `adapter.config.yaml` file the adapter CLI reads. +- [Configure & Use → Run](/configure/run) — how to invoke the agent / adapter in development, in Docker, or as a Windows service / systemd unit. +- [Modules](/modules/) — the per-module configuration the agent CLI loads at startup. +- [API reference](/api/) — the C# types that back each CLI (e.g. `MTConnectAgentApplication`, `MTConnectAdapterApplication`, `AgentApplicationConfiguration`, `AdapterApplicationConfiguration`). diff --git a/docs/cli/sysml-import.md b/docs/cli/sysml-import.md new file mode 100644 index 000000000..59f1c7589 --- /dev/null +++ b/docs/cli/sysml-import.md @@ -0,0 +1,105 @@ +# SysML importer + +`MTConnect.NET-SysML-Import` is the in-repo code-generator that turns an XMI export of the MTConnect SysML model into the `*.g.cs` source files under `libraries/MTConnect.NET-Common/`, `libraries/MTConnect.NET-XML/`, and `libraries/MTConnect.NET-JSON-cppagent/`. It is the bridge between the standard's normative model (`mtconnect/mtconnect_sysml_model`) and the .NET library's typed surface. + +This tool is **not shipped** as a binary. It lives in `build/MTConnect.NET-SysML-Import/` and is run by maintainers when: + +- A new spec version is tagged in `mtconnect/mtconnect_sysml_model` and the library is being moved onto it. +- A code-side change to the generator templates lands and the `*.g.cs` files need to be regenerated. +- A new generator-output target is added (e.g. a new wire-format codec). + +End users do not run this tool. End users consume the regenerated `*.g.cs` files transparently through the shipped NuGet packages. + +## Source + +- Project: `build/MTConnect.NET-SysML-Import/MTConnect.NET-SysML-Import.csproj` +- Entry point: `build/MTConnect.NET-SysML-Import/Program.cs` +- Renderer templates: `build/MTConnect.NET-SysML-Import/CSharp/`, `build/MTConnect.NET-SysML-Import/Xml/`, `build/MTConnect.NET-SysML-Import/Json-cppagent/` +- Parser library: `libraries/MTConnect.NET-SysML/` (the `MTConnect.SysML` namespace — XMI loader plus the in-memory `MTConnectModel`). + +## Current CLI surface + +`Program.cs` is a top-level statement file with **hardcoded paths**, not a parameterized CLI. Running it executes four steps in sequence against the input file and the output directories listed at the top of `Program.cs`: + +1. **Parse XMI** — `MTConnectModel.Parse(xmlPath)` reads the XMI export. +2. **Render JSON dump** — serializes the parsed model to a JSON file (currently at `C:\temp\mtconnect-model.json`). Useful for inspecting what the parser saw. +3. **Render `MTConnect.NET-Common` C# classes** — `CSharpTemplateRenderer.Render(model, outputPath)` writes `*.g.cs` files into `libraries/MTConnect.NET-Common/`. +4. **Render `MTConnect.NET-JSON-cppagent` codec classes** — `JsonCppAgentTemplateRenderer.Render(model, outputPath)` writes `*.g.cs` files into `libraries/MTConnect.NET-JSON-cppagent/`. +5. **Render `MTConnect.NET-XML` codec classes** — `XmlTemplateRenderer.Render(model, outputPath)` writes `*.g.cs` files into `libraries/MTConnect.NET-XML/`. + +The three paths a maintainer typically needs to edit before running the tool are at the top of `Program.cs`: + +| Variable | Purpose | Current default | +|---|---|---| +| `xmlPath` | XMI input file path. The `MTConnectSysMLModel.xml` file produced by exporting the standard's SysML model. | `D:\TrakHound\MTConnect\Standard\v2.5\MTConnectSysMLModel.xml` | +| The JSON dump path inside `RenderJsonFile()` | Where to write the in-memory model as JSON (for inspection / diffing). | `C:\temp\mtconnect-model.json` | +| The `outputPath` literals inside `RenderCommonClasses()` / `RenderJsonComponents()` / `RenderXmlComponents()` | Relative paths from the executable to each target library, computed against `AppDomain.CurrentDomain.BaseDirectory`. | `../../../../../libraries/MTConnect.NET-Common`, `../../../../../libraries/MTConnect.NET-JSON-cppagent`, `../../../../../libraries/MTConnect.NET-XML` (resolved from `bin/{Configuration}/{TFM}/` so they land in the source tree). | + +A future change may refactor `Program.cs` to read `--xmi `, `--output `, and `--json-dump ` from `args[]`; this page will be updated when that lands. Until then, the workflow is: edit the three constants, save, run, commit the regenerated `*.g.cs`. + +## Example workflow + +The full maintainer workflow to advance the library onto a new spec version: + +```bash +# 1. Fetch the new XMI from mtconnect/mtconnect_sysml_model +git -C ~/git/mtconnect/mtconnect_sysml_model pull +cp ~/git/mtconnect/mtconnect_sysml_model/MTConnectSysMLModel.xml \ + ~/MTConnect/Standard/v2.6/MTConnectSysMLModel.xml + +# 2. Edit build/MTConnect.NET-SysML-Import/Program.cs: +# point xmlPath at the new v2.6 file. + +# 3. Run the importer +dotnet run --project build/MTConnect.NET-SysML-Import + +# 4. Verify the regenerated *.g.cs files compile + tests pass +tools/test.sh + +# 5. Diff the regenerated output to confirm only spec-driven changes landed +git diff --stat libraries/MTConnect.NET-Common/**/*.g.cs + +# 6. Commit the regeneration in a single commit per spec version +git add libraries/**/*.g.cs +git commit -m "build(sysml): regenerate against v2.6 XMI" +``` + +On Windows the same workflow works under PowerShell; the only path that needs editing is the `xmlPath` constant in `Program.cs`, which is currently spelled as a Windows-style path. + +## Configuration + +The tool has no configuration file. All inputs and outputs are literal strings in `Program.cs`. The renderer templates themselves are checked in under `build/MTConnect.NET-SysML-Import/CSharp/`, `build/MTConnect.NET-SysML-Import/Xml/`, and `build/MTConnect.NET-SysML-Import/Json-cppagent/`; editing a template changes what the next regeneration emits. + +## Output discipline + +- The regenerator overwrites every `*.g.cs` file it produces. Files that are not regenerated (because the corresponding SysML element disappeared in the new spec version) are **not** deleted — the maintainer reviews the diff and removes orphans manually. +- Hand-written files alongside the generated ones use the convention `.cs` (hand-written) versus `.g.cs` (generated). The hand-written file typically adds members the generator does not produce (e.g. helper methods, secondary constructors); both files live in the same `partial class`. +- `git diff libraries/**/*.g.cs` after a regeneration is the authoritative review surface for spec-version advancement. + +## Verification + +After a regeneration: + +```bash +# Full unit + integration suite +tools/test.sh + +# Compliance harness — the per-spec-version conformance tests +tools/test.sh --compliance + +# Lint + formatter pass to keep the regenerator's output style consistent +dotnet format MTConnect.NET.sln --verify-no-changes +``` + +A regeneration is considered clean when (a) the test suite is green at every previously-green configuration, (b) the formatter reports no changes needed, and (c) the diff against the previous state explains every changed line in terms of a specific SysML model element. + +## See also + +- [Configure & Use → Run](/configure/run) — running the agent against the regenerated library to verify end-to-end behavior. +- [Compliance](/compliance/) — the per-version compliance matrix that the regenerator advances. +- [API reference → `MTConnect.SysML.MTConnectModel`](/api/) — the in-memory model the XMI parser produces and the renderers walk. +- [API reference → `MTConnect.SysML.CSharp.CSharpTemplateRenderer`](/api/) — the C# renderer that produces `MTConnect.NET-Common`. +- [API reference → `MTConnect.SysML.Xml.XmlTemplateRenderer`](/api/) — the XML renderer that produces `MTConnect.NET-XML`. +- [API reference → `MTConnect.SysML.Json_cppagent.JsonCppAgentTemplateRenderer`](/api/) — the JSON v2 renderer that produces `MTConnect.NET-JSON-cppagent`. +- [`tools/test.sh`](./test-sh) — runs after a regeneration to verify the suite stays green. +- [`tools/dotnet.sh`](./dotnet-sh) — wraps the `dotnet run` invocation if the regeneration is being done inside a containerized SDK. diff --git a/docs/cli/test-sh.md b/docs/cli/test-sh.md new file mode 100644 index 000000000..0cca478c4 --- /dev/null +++ b/docs/cli/test-sh.md @@ -0,0 +1,129 @@ +# `tools/test.sh` + +`tools/test.sh` is the local test entry point for `MTConnect.NET`. It iterates every `tests/**/*.csproj` (so new test projects are picked up automatically without script edits), optionally adds the Compliance and Docker-gated E2E tiers, runs them through [`tools/dotnet.sh`](./dotnet-sh) so the same script works against the host `dotnet` or a containerized SDK, and produces a unified coverage report under `coverage-report/`. + +This is a **contributor** tool. End users running the shipped agent or adapter binaries do not need it. + +A PowerShell sibling lives at `tools/test.ps1` with the same semantics and the same flag names (`-Docker`, `-Compliance`, `-E2E`, `-Only` instead of `--docker`, `--compliance`, `--e2e`, `--only`). + +## Synopsis + +```text +tools/test.sh [--docker] [--compliance] [--e2e] [--only ] [--help] +``` + +## Flags + +| Flag | Short | Description | +|---|---|---| +| `--docker` | `-d` | Run every `dotnet` invocation through `tools/dotnet.sh --docker`, i.e. inside the `mcr.microsoft.com/dotnet/sdk` container. Equivalent to exporting `MTCONNECT_DOTNET_USE_DOCKER=1` before the call. | +| `--compliance` | `-c` | Include the MTConnect compliance harness under `tests/Compliance/**` in addition to the default unit + integration tier. | +| `--e2e` | `-e` | Force the E2E / Docker-gated suites. Sets `MTCONNECT_E2E_DOCKER=true` and runs the Testcontainers-backed tests under `tests/IntegrationTests` and `tests/E2E/**`. | +| `--only ` | `-o` | Run only test projects whose path matches `PATTERN` (case-insensitive `grep -E` regex). Use to narrow the run to one library while iterating. | +| `--help` | `-h` | Print the usage block embedded at the top of the script and exit. | + +## Environment variables + +| Variable | Default | Description | +|---|---|---| +| `MTCONNECT_DOTNET_USE_DOCKER` | unset | When set to `1`, behaves as if `--docker` were passed. | +| `MTCONNECT_E2E_DOCKER` | unset (treated as `false`) | When set to `true` / `yes` / `on` / `1`, drops the default `Category!=RequiresDocker` filter so Docker-gated tests run. `--e2e` sets this for you. | + +The script also forwards every variable that [`tools/dotnet.sh`](./dotnet-sh) honors (`MTCONNECT_DOTNET_SDK_TAG`, `MTCONNECT_DOTNET_IMAGE`, `MTCONNECT_NUGET_VOLUME`, `MTCONNECT_DOTNET_TOOLS_VOLUME`, `MTCONNECT_DOTNET_E2E_DIND`) to the underlying `dotnet` invocations. + +## Tier semantics + +The script splits tests into three tiers based on path: + +1. **Unit + integration tier** — every `tests/**/*.csproj` excluding `tests/Compliance/**` and `tests/E2E/**`. Always runs. Filter `Category!=RequiresDocker` is applied unless `--e2e` is set. +2. **Compliance tier** — every `tests/Compliance/**/*.csproj`. Skipped unless `--compliance` is set. No category filter applied. +3. **E2E tier** — every `tests/IntegrationTests/**/*.csproj` plus `tests/E2E/**/*.csproj`. Skipped unless `MTCONNECT_E2E_DOCKER` evaluates truthy (which `--e2e` arranges). + +When `--only ` is supplied, the unit + integration tier is filtered to projects whose path matches the regex. The Compliance and E2E tiers are not filtered by `--only` (they are infrastructure-gated, not pattern-gated). + +## Example invocations + +Default — unit + integration on the host `dotnet`: + +```bash +tools/test.sh +``` + +Add the Compliance harness: + +```bash +tools/test.sh --compliance +``` + +Run only the XML and SHDR test projects: + +```bash +tools/test.sh --only 'XML|SHDR' +``` + +Containerized full run including E2E: + +```bash +tools/test.sh --docker --e2e +``` + +Containerized full run including E2E and Compliance: + +```bash +tools/test.sh --docker --compliance --e2e +``` + +Run a single test project quickly while iterating on a library: + +```bash +tools/test.sh --only 'MTConnect.NET-Common-Tests' +``` + +## Output + +The script writes the following under the repo root: + +| Path | Contents | +|---|---| +| `TestResults//` | Per-project Cobertura coverage XMLs and TRX result files, one directory per test project. | +| `coverage-report/` | Merged coverage report from `reportgenerator`. Contains HTML browseable output (`index.html`), a Cobertura merged XML, a Markdown summary, and a plain-text summary. | +| `coverage-report/Summary.txt` | Plain-text coverage summary. Printed to stdout at the end of a successful run. | +| `coverage/` | (Reserved.) Cleared at the start of every run. | + +The `TestResults/`, `coverage/`, and `coverage-report/` directories are deleted at the start of every run, so a partial previous run cannot pollute the next one. + +## Behavior + +1. Resolve the repo root by walking up from `tools/test.sh`. +2. Parse flags; honor `MTCONNECT_DOTNET_USE_DOCKER` and `MTCONNECT_E2E_DOCKER` env-vars. +3. Wipe `TestResults/`, `coverage/`, `coverage-report/` and recreate `TestResults/`. +4. `tools/dotnet.sh tool restore` — pull `reportgenerator` and any other local dotnet tools listed in `.config/dotnet-tools.json`. +5. Enumerate the unit + integration tier projects, apply `--only` if supplied, and run each with: + ```bash + tools/dotnet.sh test \ + --configuration Release \ + [--settings tests/coverlet.runsettings] \ + [--filter Category!=RequiresDocker] \ + --collect:"XPlat Code Coverage" \ + --results-directory TestResults/ + ``` +6. If `--compliance` was set, enumerate `tests/Compliance/**/*.csproj` and run each with the same options minus the category filter. +7. If E2E is enabled, enumerate `tests/IntegrationTests/**/*.csproj` and `tests/E2E/**/*.csproj` and run each with the same options minus the category filter. +8. Run `tools/dotnet.sh tool run reportgenerator` against every `TestResults/**/coverage.cobertura.xml`, writing the merged report to `coverage-report/` in HTML, text, Markdown, and Cobertura formats. +9. If `coverage-report/Summary.txt` exists, print it. + +## Failure handling + +The script runs under `set -euo pipefail`. Any failing `dotnet test` invocation aborts the run with a non-zero exit code; the coverage report is **not** produced in that case (so a partially-run suite cannot pretend to be a clean coverage measurement). To debug a specific failing project, use `--only` to narrow the run to that project plus its peers and re-run. + +## Platform notes + +- **Linux + macOS**: native run. The script uses `cd -P` and `readlink` carefully to be portable to bash 3.2 (the macOS default). +- **Windows**: use the PowerShell sibling at `tools/test.ps1` (same flag names: `-Docker`, `-Compliance`, `-E2E`, `-Only`). The shell script also works inside Git-Bash or WSL. + +## See also + +- [`tools/dotnet.sh`](./dotnet-sh) — the `dotnet` wrapper this script uses for every invocation. +- [Compliance → Test harness](/compliance/test-harness) — how to interpret the Compliance-tier output specifically. +- [SysML importer](./sysml-import) — runs `tools/test.sh` after every regeneration to verify the regenerated `*.g.cs` files compile and the suite stays green. +- [API reference](/api/) — the public surface that the tests under `tests/` exercise. diff --git a/docs/compliance/index.md b/docs/compliance/index.md new file mode 100644 index 000000000..521d9e717 --- /dev/null +++ b/docs/compliance/index.md @@ -0,0 +1,41 @@ +# MTConnect Standard compliance + +`MTConnect.NET` targets **100% MTConnect Standard compliance** across every advertised spec version from v1.0 through v2.7. This section answers the question "if I write to the spec using `MTConnect.NET`, am I conformant?" without requiring you to read the source. + +## What this section covers + +- **[Per-version compliance matrix](./per-version-matrix)** — which spec versions are supported, with a per-envelope (Streams / Devices / Assets / Error) status per version. +- **[Wire-format compliance](./wire-format)** — which on-the-wire codecs are byte-for-byte cppagent-parity (XML, JSON-CPPAGENT v2 array-of-wrappers, JSON-CPPAGENT-MQTT) and which deviate, with the deviations documented and justified. +- **[Spec-source-vs-implementation cross-references](./spec-cross-references)** — for every code path that implements a normative spec rule, the citation that grounds it (SysML XMI element, XSD type, prose paragraph). +- **[Known divergences from the Standard](./known-divergences)** — places where the Standard contradicts itself, with the artifact `MTConnect.NET` follows named explicitly and the upstream maintainer report linked. +- **[Compliance test harness](./test-harness)** — how to run the compliance tier of the test suite against any deployment, with sample output and how to interpret the failure categories. + +## How compliance is verified in `MTConnect.NET` + +```mermaid +flowchart TD + Spec[MTConnect Standard] --> XMI[SysML XMI model] + Spec --> XSD[XSDs per envelope] + Spec --> Prose[Prose Parts 1-4] + Spec --> CPP[cppagent reference] + XMI -.generates.-> Generator[MTConnect.NET-SysML-Import] + Generator -.emits.-> GCS[.g.cs files] + GCS --> Lib[MTConnect.NET libraries] + XSD -.validates.-> Wire[Wire output] + CPP -.parity check.-> Wire + Lib -.serializes.-> Wire +``` + +The SysML XMI model is the source of truth for type definitions, `MinimumVersion` / `MaximumVersion` metadata, controlled-vocabulary enumerations, and structural constraints. The `MTConnect.NET-SysML` generator walks the XMI and emits source files that the libraries compile against. The XSDs validate every wire envelope at build time and at run time. The cppagent reference output is used as the parity oracle for the JSON-CPPAGENT v2 codec. + +## When the Standard contradicts itself + +The Standard occasionally disagrees with itself — XMI declares one thing, the XSD encodes another, the prose says a third, and the cppagent reference does a fourth. When this happens, this site states the divergence explicitly, names which artifact `MTConnect.NET` follows, and links to the maintainer-bound writeup that asks the Standard to resolve the contradiction. See [Known divergences from the Standard](./known-divergences) for the running list. + +The library's compliance is not blocked by the Standard's internal disagreements; the chosen authority is documented and stable. + +## See also + +- [Wire formats](/wire-formats/) — the codec-level reference for XML, JSON v1, JSON-CPPAGENT v2, JSON-CPPAGENT-MQTT, and SHDR. +- [API reference](/api/) — per-type pages carry "Introduced in" and "Deprecated in" badges that surface the spec-version metadata directly. +- [Concepts](/concepts/) — the data-model overview that grounds the compliance vocabulary. diff --git a/docs/compliance/known-divergences.md b/docs/compliance/known-divergences.md new file mode 100644 index 000000000..4464a8d33 --- /dev/null +++ b/docs/compliance/known-divergences.md @@ -0,0 +1,89 @@ +# Known divergences from the Standard + +The MTConnect Standard is published through four artifacts — SysML XMI, XSDs, prose, cppagent reference — and they occasionally disagree. This page catalogues the divergences `MTConnect.NET` has identified, where they were filed upstream for resolution, and which artifact the library currently follows. + +Every divergence has been filed against the standard body's tracker at [projects.mtconnect.org](https://projects.mtconnect.org/). The Redmine ticket numbers below are the canonical references; visit them for the standard maintainers' resolution timeline. + +## ASSET_COUNT default representation + +**Disagreement**: SysML XMI / XSD vs cppagent. + +The MTConnect Standard's three formal sources disagree on whether an `ASSET_COUNT` DataItem defaults to `representation="VALUE"` (scalar) or `representation="DATA_SET"`: + +- **SysML XMI** declares `AssetCount.result : integer` as a `uml:DataType`, not a `uml:Class`. The spec's own rule ("if `DataItem::representation` is not specified, it MUST be determined to be `VALUE`") yields **VALUE**. +- **XSD** declares the canonical `AssetCount` element as `substitutionGroup='IntegerEvent'` with `xs:simpleContent` — a scalar. Parallel `AssetCountDataSet` and `AssetCountTable` element declarations co-exist as opt-in alternates. → **VALUE**. +- **cppagent reference** `Agent::verifyDevice` auto-injects `representation="DATA_SET"` when no `ASSET_COUNT` DataItem is declared and `schemaVersion >= 2.0`. → **DATA_SET**. + +**Library posture**: follows SysML XMI and XSD — `ASSET_COUNT` defaults to `VALUE`. The library does NOT auto-inject `representation="DATA_SET"` on devices that omit `ASSET_COUNT`. Consumers who need cppagent-parity DATA_SET behavior can author the DataItem with `representation="DATA_SET"` explicitly in the device model. + +**Filed**: [Redmine #3890](https://projects.mtconnect.org/issues/3890) (Agent Working Group). + +## v2.6 SysML XMI byte-identical to v2.7 + +**Disagreement**: spec release versioning. + +The published v2.6 SysML XMI file (`MTConnectSysMLModel_V2.6.xml`) is byte-identical to v2.7. v2.6 and v2.7 should differ — the spec release cadence assumes each major increment has at least one substantive XMI change — and the byte-identical publication suggests a release-engineering mistake at the standard body, not a deliberate "no-change" version. + +**Library posture**: `MTConnectVersions.Version26` and `Version27` are both shipped as distinct constants because the spec body advertises both as released versions. Any type's `MinimumVersion = Version26` is treated as equivalent to `Version27` for serialization gating. + +**Filed**: [Redmine #3892](https://projects.mtconnect.org/issues/3892) (SysML Model Related Issues). + +## DataSet vs Table result class disagreement + +**Disagreement**: SysML XMI vs XSD. + +For DataItems with `representation="DATA_SET"` or `representation="TABLE"`, the SysML XMI declares the `result` property's type as a single `DataSet` class shared between the two representations, while the XSD declares two distinct complex types (`DataSetType` and `TableType`) with non-overlapping element shapes. + +**Library posture**: follows the XSD's two-class shape — `DataSetEntry` and `TableEntry` are distinct classes ([`MTConnect.Observations.DataSetEntry`](/api/MTConnect.Observations/DataSetEntry), [`MTConnect.Observations.TableEntry`](/api/MTConnect.Observations/TableEntry)). The on-the-wire output is XSD-validated; consumers parsing the XML never see ambiguity. + +**Filed**: [Redmine #3893](https://projects.mtconnect.org/issues/3893) (SysML Model Related Issues). + +## Feature persistent-id typo across SysML and XSD + +**Disagreement**: spec internal consistency. + +A typo in the property name `persistentId` is preserved as `persisitentId` across both the SysML XMI and the XSDs from v1.4 through the latest published release. The typo is in the same character position on both artifacts, suggesting a copy-and-paste origin rather than independent transcription. + +**Library posture**: the library serializes the typo as-published, with no silent correction. Consumers receive `persisitentId` on the wire because that is what the XSD requires; a future spec release that fixes the typo will trigger a coordinated bump on both sides. + +**Filed**: [Redmine #3894](https://projects.mtconnect.org/issues/3894) (SysML Model Related Issues). + +## Component class hierarchy SysML vs XSD + +**Disagreement**: SysML XMI vs XSD. + +A subset of Component classes have a different parent class in SysML than they do in the XSD. For example, `LinearComponent` derives from `Axis` in SysML and from `AxisType` (the XSD-only intermediate) in the XSD. The hierarchy difference does not affect the wire shape — both forms produce the same element names — but it affects type-system code generators that compile against both artifacts. + +**Library posture**: the source generator follows SysML for the C# class hierarchy and lets the XSD handle the wire shape independently. The generated `LinearComponent` inherits from `AxisComponent` in C#, and the XSD-side `LinearType` deriving from `AxisType` is handled at serialization time by the XML formatter. + +**Filed**: [Redmine #3891](https://projects.mtconnect.org/issues/3891) (SysML Model Related Issues). + +## JSON wire format not normative — no JSON Schema generator + +**Disagreement**: missing normative artifact. + +The MTConnect Standard's `Part_5` prose describes the JSON wire format descriptively, but no normative JSON Schema is published. Consumers parsing JSON output today rely on the cppagent reference's byte shape rather than a versioned schema. The library follows cppagent for the JSON-CPPAGENT codec but cannot validate its output against a missing-from-the-standard schema. + +**Library posture**: the JSON-CPPAGENT codec is byte-tested against golden cppagent output; the JSON v1 codec is regression-tested against itself. A normative JSON Schema, if the standard body publishes one in a future release, would convert the byte-parity tests into schema-validated tests. + +**Filed**: [Redmine #3889](https://projects.mtconnect.org/issues/3889) (Agent Working Group). + +## How divergences are tracked + +Every divergence flows through the same pipeline: + +1. **Discovery** — a test, a code review, or a consumer report surfaces a spec inconsistency. +2. **Verification** — the divergence is reproduced against every published version of the affected artifact. +3. **Source citation** — the exact line numbers / element IDs / prose sections are recorded for every artifact involved. +4. **Library posture decision** — the library follows the artifact that wins under the [source-of-truth hierarchy](/compliance/spec-cross-references#source-of-truth-hierarchy). +5. **Upstream filing** — a Redmine ticket is filed against the standard body. +6. **Audit trail** — the ticket URL is referenced from this page and from the test fixtures that pin the library's posture. + +When the standard body resolves a ticket (either accepting the library's posture or amending the standard), the library follows the resolution. Where the resolution requires a wire-format change, the change is gated on the spec version the resolution targets (existing wire output for earlier versions is unchanged). + +## Where to next + +- [Per-version matrix](/compliance/per-version-matrix) — version-by-version envelope coverage. +- [Wire-format compliance](/compliance/wire-format) — XML / JSON / SHDR posture. +- [Spec cross-references](/compliance/spec-cross-references) — the source-of-truth hierarchy that drives every posture decision above. +- [Test harness](/compliance/test-harness) — how the divergence-pinning tests run locally. diff --git a/docs/compliance/per-version-matrix.md b/docs/compliance/per-version-matrix.md new file mode 100644 index 000000000..58813eca8 --- /dev/null +++ b/docs/compliance/per-version-matrix.md @@ -0,0 +1,97 @@ +# Per-version compliance matrix + +`MTConnect.NET` is built against the MTConnect Standard from v1.0 through v2.7. Every shipped envelope — Devices, Streams, Assets, Error — validates against the corresponding XSD at every version listed below. Every spec-defined type that appears at a given version is present in the library at that version, gated by the type's `MinimumVersion` / `MaximumVersion` metadata. + +## Spec versions supported + +The library tracks every published MTConnect spec version. The version constants live in [`MTConnect.MTConnectVersions`](/api/MTConnect/MTConnectVersions), and `MTConnectVersions.Max` advertises the latest one the library can serialize for. + +| MTConnect version | Released by MTConnect | Library constant | Streams XSD | Devices XSD | Assets XSD | Error XSD | +|---|---|---|---|---|---|---| +| v1.0 | 2008 | `MTConnectVersions.Version10` | yes | yes | n/a | yes | +| v1.1 | 2010 | `MTConnectVersions.Version11` | yes | yes | n/a | yes | +| v1.2 | 2012 | `MTConnectVersions.Version12` | yes | yes | yes | yes | +| v1.3 | 2014 | `MTConnectVersions.Version13` | yes | yes | yes | yes | +| v1.4 | 2017 | `MTConnectVersions.Version14` | yes | yes | yes | yes | +| v1.5 | 2018 | `MTConnectVersions.Version15` | yes | yes | yes | yes | +| v1.6 | 2019 | `MTConnectVersions.Version16` | yes | yes | yes | yes | +| v1.7 | 2020 | `MTConnectVersions.Version17` | yes | yes | yes | yes | +| v1.8 | 2020 | `MTConnectVersions.Version18` | yes | yes | yes | yes | +| v2.0 | 2021 | `MTConnectVersions.Version20` | yes | yes | yes | yes | +| v2.1 | 2022 | `MTConnectVersions.Version21` | yes | yes | yes | yes | +| v2.2 | 2023 | `MTConnectVersions.Version22` | yes | yes | yes | yes | +| v2.3 | 2024 | `MTConnectVersions.Version23` | yes | yes | yes | yes | +| v2.4 | 2024 | `MTConnectVersions.Version24` | yes | yes | yes | yes | +| v2.5 | 2025 | `MTConnectVersions.Version25` | yes | yes | yes | yes | +| v2.6 | 2025 | `MTConnectVersions.Version26` | yes | yes | yes | yes | +| v2.7 | 2025 | `MTConnectVersions.Version27` | yes | yes | yes | yes | + +Assets are not part of the v1.0 / v1.1 envelope set; the Assets envelope enters at v1.2 per the spec's XSD release history ([schemas.mtconnect.org](https://schemas.mtconnect.org/)). + +Note: v1.9 was never released — the MTConnect Standard's version numbering jumped from v1.8 to v2.0. The library matches: no `Version19` constant exists. + +## Per-envelope semantics + +Each cell in the matrix above means: the agent can be asked to emit the named envelope at the named spec version, and the output validates against the matching `MTConnect_.xsd` schema published by the standard body. The version-aware serializers ([`Device.Process`](/api/MTConnect.Devices/Device#Process), [`DataItem.Process`](/api/MTConnect.Devices/DataItem#Process), [`Composition.Process`](/api/MTConnect.Devices/Composition#Process), and the per-envelope JSON / XML codecs) prune properties, DataItems, Components, and Assets whose `MinimumVersion` is above the target version, and prune any whose `MaximumVersion` is below it. + +## Type introduction inventory + +A subset of spec-version-introduced types the matrix tracks (the full inventory lives on each type's [API reference page](/api/), generated from the SysML `introducedAtVersion` tag): + +- **v1.2**: Assets envelope; `Composition` introduced; `Description.Model` introduced. +- **v1.3**: `References` element on Components; `Configuration` element under Components. +- **v1.4**: `Composition` ships as a first-class element under Components; `Specification` element; `Constraints` on DataItems; `Filter` element on DataItems. +- **v1.5**: `DATA_SET` representation introduced; `DataItemRelationship` introduced; `ComponentRelationship` introduced. +- **v1.6**: `TABLE` representation introduced; `CoordinateSystem` element introduced (deprecating the `coordinateSystem` enum); `Reset` element. +- **v1.7**: Agent self-describing `Agent` Device introduced; `SpecificationRelationship`; `PEER` `ComponentRelationship` type; `MTConnectVersion` attribute on Device. +- **v1.8**: `coordinateSystemIdRef` attribute on DataItem. +- **v2.0**: `DATA_SET` becomes the canonical representation for several types (`PART_COUNT`, `ASSET_COUNT`); MQTT topic templates introduced in the spec's `Part_5` (Network). +- **v2.1**: extended `Quality` enum entries. +- **v2.2**: `Hash` attribute on Header and on Device; `ComponentConfigurationParameters` Asset. +- **v2.3**: `Quality` field on Observation made first-class. +- **v2.4**: Rich-template Pallet measurements (`HeightMeasurement`, `WidthMeasurement`, `LoadedHeightMeasurement`, etc.) replace free-form `Measurement`. +- **v2.5**: spec-internal cleanup; no new wire-format-visible types. +- **v2.6**: per the spec's `Part_3` cleanup; v2.6 SysML XMI is byte-identical to v2.7 per the spec's own publication (see [Compliance: Known divergences](/compliance/known-divergences)). +- **v2.7**: spec cleanup; multiple minor enum and attribute additions. + +Every introduction is auditable through the generated `.g.cs` files under `libraries/MTConnect.NET-Common/`, which carry the per-type `MinimumVersion` value sourced from the SysML model's `introducedAtVersion` ([`mtconnect/mtconnect_sysml_model`](https://github.com/mtconnect/mtconnect_sysml_model)). + +## Header fields per version + +The `Header` element gains attributes over time. The library populates them based on the target version; the [`MTConnectAgentInformation`](/api/MTConnect.Agents/MTConnectAgentInformation) class is the source. + +| Attribute | Introduced at | Notes | +|---|---|---| +| `creationTime` | v1.0 | UTC ISO 8601. | +| `sender` | v1.0 | agent hostname or configured value. | +| `instanceId` | v1.0 | agent's `InstanceId`; resets on a buffer wipe. | +| `version` | v1.0 | agent's software version (not the MTConnect spec version). | +| `assetBufferSize` | v1.2 | matches the agent's `assetBufferSize` config. | +| `assetCount` | v1.2 | live count of assets in the buffer. | +| `bufferSize` | v1.0 | matches the agent's `observationBufferSize` config. | +| `nextSequence` | v1.0 | next sequence the agent will assign. | +| `firstSequence` | v1.0 | lowest sequence still in the buffer. | +| `lastSequence` | v1.0 | highest sequence currently in the buffer. | +| `schemaVersion` | v1.4 | the MTConnect spec version of the response (e.g. `"2.5"`). | +| `validation` | v1.7 | true if the agent validates incoming Devices against the XSD. | +| `Hash` | v2.2 | SHA-1 over the model; consumers detect a model change without re-parsing. | +| `deviceModelChangeTime` | v1.7 | timestamp of the last model change. | + +Source: `MTConnectStreams_.xsd` element `MTConnectStreamsType/Header` ([schemas.mtconnect.org](https://schemas.mtconnect.org/)); SysML `Header` class ([`mtconnect/mtconnect_sysml_model`](https://github.com/mtconnect/mtconnect_sysml_model)). + +## How the agent picks a version + +When a consumer queries `/probe`, `/current`, `/sample`, or `/asset`, the agent picks the response version as follows: + +1. If the request URL carries a `?version=` parameter, the agent uses that. +2. Otherwise the agent uses the configured `defaultVersion` from `agent.config.yaml`. +3. If neither is set, the agent uses `MTConnectVersions.Max`. + +Requesting a version older than `MTConnectVersions.Version10` returns an Error envelope; requesting a version newer than `Max` returns an Error envelope as well. + +## Where to next + +- [Wire-format compliance](/compliance/wire-format) — which on-the-wire codecs are byte-for-byte cppagent-parity. +- [Spec cross-references](/compliance/spec-cross-references) — how every claim above is grounded in an XMI / XSD / prose citation. +- [Known divergences](/compliance/known-divergences) — where the standard contradicts itself and how the library handles each case. +- [Test harness](/compliance/test-harness) — how to run the compliance tier locally. diff --git a/docs/compliance/spec-cross-references.md b/docs/compliance/spec-cross-references.md new file mode 100644 index 000000000..477d8841e --- /dev/null +++ b/docs/compliance/spec-cross-references.md @@ -0,0 +1,94 @@ +# Spec source-of-truth and cross-references + +The MTConnect Standard ships through four artifacts. When the artifacts disagree, the library follows an explicit hierarchy. This page describes that hierarchy, the cross-reference pattern used in the code and tests, and how to audit any individual claim against the spec. + +## The four artifacts + +```mermaid +flowchart TD + Spec[MTConnect Standard] --> XMI[SysML XMI model] + Spec --> XSD[XSDs per envelope] + Spec --> Prose[Prose Parts 1 - 5] + Spec --> CPP[cppagent reference implementation] + XMI -. generates .-> Generator[MTConnect.NET source generator] + Generator -. emits .-> GCS[.g.cs files] + GCS --> Lib[MTConnect.NET libraries] + XSD -. validates .-> Wire[Wire-format output] + CPP -. parity check .-> Wire + Lib -. serializes .-> Wire +``` + +1. **SysML XMI** — `https://github.com/mtconnect/mtconnect_sysml_model`. The most-authoritative source for the type system: class hierarchy, properties, enum values, version introduction. Published per spec release as `MTConnectSysMLModel_V.xml`. +2. **XSDs** — `https://schemas.mtconnect.org/schemas/MTConnect_.xsd`. The authoritative source for envelope wire shape: element names, attribute lists, occurrence constraints. +3. **Prose** — the published Standard documents at [docs.mtconnect.org](https://docs.mtconnect.org/). Authoritative for semantic intent: what an enum value means, what a normative MUST applies to. +4. **cppagent** — `https://github.com/mtconnect/cppagent`. The reference implementation. Authoritative for the JSON-CPPAGENT wire shape (since the spec does not normatively define the JSON envelope's bytes). Non-normative for XML, where the XSD is the authority. + +## Source-of-truth hierarchy + +Per the MTConnect maintainer working group's published guidance, **XMI is the normative artifact** for the type system. When XMI and the XSD disagree on a type's structure, XMI wins; the XSD is regenerated from XMI in the next spec release. When XMI and the prose disagree on a semantic intent, XMI wins for the type-system shape and prose wins for the runtime semantic — but only where the prose explicitly states a MUST that the XMI cannot encode (e.g. `Result MUST be UNAVAILABLE when no valid value is determined`). + +When cppagent and XMI disagree, **cppagent is the reference but is non-normative**. The library defers to XMI for the type system and uses cppagent only as the byte-shape reference for the JSON-CPPAGENT codec where the XSD has no opinion. The known cases where cppagent contradicts XMI are cataloged at [Known divergences](/compliance/known-divergences). + +| Question | Wins | +|---|---| +| Does a class exist at version V? | XMI | +| Does a class have property P? | XMI | +| Is property P a `uml:DataType` or a `uml:Class`? | XMI | +| What does enum value E mean? | XMI; prose if XMI is silent | +| What attributes does element X carry on the wire? | XSD | +| Is element X required or optional? | XSD; XMI if XSD ambiguous | +| What MUST an agent return when no value is available? | Prose (`Part_2.0` §3) | +| What does the JSON wire shape look like for X? | cppagent (JSON-CPPAGENT codec) | +| What does the XML wire shape look like for X? | XSD | +| What does an SHDR line look like for X? | Prose (`Part_5.0`) | + +## Citation pattern in the library + +Every test that asserts spec behavior cites the source. The pattern is documented in the codebase as a comment block on the relevant fixture; examples: + +```csharp +// AssetCount is declared as a scalar IntegerEvent (representation=VALUE) +// across every published v2.x. Sources: +// - SysML XMI: AssetCount packagedElement, result : integer (uml:DataType). +// https://github.com/mtconnect/mtconnect_sysml_model +// - XSD: AssetCount element substitutes IntegerEvent, xs:simpleContent. +// https://schemas.mtconnect.org/schemas/MTConnectStreams_2.5.xsd +// - Prose: Part_2.0 §11.5 "Asset events". +// https://docs.mtconnect.org/ +// The cppagent reference auto-injects representation="DATA_SET" but is +// non-normative; the library follows XMI / XSD per the hierarchy above. +// Tracked upstream: https://projects.mtconnect.org/issues/3890 +``` + +Three rules for the citation block: + +1. **At least one of XMI / XSD / prose is cited per spec assertion.** Mechanical assertions (a constant has a specific value) cite XMI. Structural assertions (an envelope carries an attribute) cite XSD. Semantic assertions (an enum value means X) cite prose. +2. **The URL is a permanent link.** Either a tagged release (`/blob/v2.7/MTConnectSysMLModel_V2.7.xml`) or a schemas.mtconnect.org canonical URL. Tip-of-trunk URLs are forbidden because they drift. +3. **The cppagent reference is cited where it is the source-of-truth (JSON-CPPAGENT codec) and as a disagreement reference where it diverges from the normative source.** + +## How to audit a single claim + +A consumer who reads "`MTConnect.NET` claims X about the spec" can audit it by: + +1. Finding the X claim in the relevant doc page or in the relevant test fixture. +2. Following the cited URL to the authoritative artifact. +3. Verifying the cited element / class / section actually says what the citation claims. + +The compliance test harness (see [Test harness](/compliance/test-harness)) automates step 3 for a battery of pinned assertions: each test cites its source in a fixture comment, runs the assertion, and fails if the assertion drifts from the source's current value. + +## Per-version XMI cite pattern + +The XMI model is published per spec version. The library cites the version it asserts at: + +- For "class C exists at version V": cite `MTConnectSysMLModel_V.xml`'s `packagedElement` for class C. +- For "class C was introduced at version V": cite class C's `introducedAtVersion` tag in `MTConnectSysMLModel_V.xml` (introductions persist in every later release's XMI). +- For "class C was deprecated at version W": cite class C's `deprecatedAtVersion` tag. + +The introduction-version metadata is harvested into the generated `.g.cs` files; every `MinimumVersion` / `MaximumVersion` property value on every shipped class is traceable back to a SysML XMI tag. + +## Where to next + +- [Per-version matrix](/compliance/per-version-matrix) — the per-version envelope and type coverage. +- [Wire-format compliance](/compliance/wire-format) — XSD validation and cppagent parity testing. +- [Known divergences](/compliance/known-divergences) — the documented cases where the artifacts disagree. +- [Test harness](/compliance/test-harness) — running the compliance tier locally. diff --git a/docs/compliance/test-harness.md b/docs/compliance/test-harness.md new file mode 100644 index 000000000..503a456e1 --- /dev/null +++ b/docs/compliance/test-harness.md @@ -0,0 +1,116 @@ +# Compliance test harness + +`MTConnect.NET` ships a compliance tier in its test suite — a battery of tests that validate the library's behavior against the MTConnect Standard's published artifacts (XSDs, SysML XMI, cppagent reference output). This page walks through running the tier locally, interpreting its output, and adding new pinning tests. + +## What the tier covers + +The compliance tier validates four claim levels: + +- **XSD validation** — every wire-format output of every Streams / Devices / Assets / Error envelope at every spec version v1.0 through v2.7 validates against the matching `MTConnect_.xsd`. +- **SysML XMI parity** — every type's `MinimumVersion` / `MaximumVersion` / property set matches the SysML model. +- **cppagent JSON parity** — every JSON-CPPAGENT and JSON-CPPAGENT-MQTT output is byte-identical to a captured cppagent reference output for the same model. +- **SHDR prose conformance** — every example SHDR line in `Part_5.0` round-trips through the SHDR parser and writer. + +The tier is opt-in. The default `dotnet test` run skips it because the embedded XSDs make the tier slower than the unit + integration tiers. + +## Running the tier + +The repo's wrapper script handles tier selection: + +```sh +./tools/test.sh -c +# or +./tools/test.sh --compliance +``` + +The flag flips the `RUN_COMPLIANCE` gate in `tools/test.sh`. The script then: + +1. Runs the default unit + integration tier. +2. Enumerates every `*.csproj` under `tests/Compliance/`. +3. Runs `dotnet test --configuration Release --collect:"XPlat Code Coverage"` on each. +4. Writes results to `TestResults//`. +5. Runs `reportgenerator` to produce a combined coverage report at `coverage-report/`. + +The Windows-side equivalent is `./tools/test.ps1 -Compliance`. + +To run just the compliance tier without the unit tier, pass the `--only` filter: + +```sh +./tools/test.sh -c --only Compliance +``` + +## What you should see + +A successful run prints, per compliance project: + +```text +Passed! - Failed: 0, Passed: , Skipped: 0, Total: +``` + +The combined coverage report at `coverage-report/Summary.txt` shows line, branch, and method coverage. The compliance tier targets 100 % of the wire-format codecs and the version-aware serializers. + +## Failure categories + +When a compliance test fails, the failure category is encoded in the test class name and the assertion message: + +- **`XsdValidationTests__`** — output failed XSD validation. The assertion message includes the XSD line number that rejected the output. Resolution: fix the codec; the XSD is the wire-shape authority. See [Troubleshooting: XSD validation failures](/troubleshooting/xsd-validation-failures) for the diagnostic flow. +- **`SysMLParityTests_`** — a class's `MinimumVersion` or property set drifted from the SysML model. Resolution: re-run the source generator against the latest XMI; the `.g.cs` files should regenerate to match. +- **`CppAgentParityTests_`** — JSON output diverged from cppagent's reference. Resolution: inspect the byte diff; either fix the codec (if the divergence is unintentional) or update the captured golden file and document the divergence at [Known divergences](/compliance/known-divergences). +- **`ShdrConformanceTests`** — SHDR parser or writer failed a `Part_5.0` example. Resolution: fix the SHDR codec; the spec prose is the authority. + +## Interpreting a typical run + +Sample output for one envelope at one version: + +```text +[12:34:56 INF] Running XsdValidationTests_Streams_v2_5... +[12:34:56 INF] Loading MTConnectStreams_2.5.xsd from embedded resources. +[12:34:56 INF] Validating golden fixture streams_v2_5_minimal.xml... +[12:34:56 INF] Validating golden fixture streams_v2_5_dataset.xml... +[12:34:56 INF] Validating golden fixture streams_v2_5_condition.xml... +[12:34:56 INF] Validating golden fixture streams_v2_5_table.xml... +Passed! - Failed: 0, Passed: 4, Skipped: 0, Total: 4 +``` + +Per envelope per version, the suite runs the same battery of golden fixtures (minimal, with-dataset, with-condition, with-table, with-timeseries, with-asset-events). A version-introduction regression (a type that should be elided at v1.0 but appeared in the output) fails the golden-fixture comparison loudly. + +## Adding a new pinning test + +When the library asserts a new spec behavior — a type added in a newer spec version, a Known divergence resolution, a wire-format change — add a test to the relevant compliance project. The test class: + +```csharp +using NUnit.Framework; + +namespace MTConnect.Compliance.Tests; + +[TestFixture] +public class MyNewSpecAssertion +{ + // Source: SysML class introduced at version V. + // https://github.com/mtconnect/mtconnect_sysml_model/blob/v/MTConnectSysMLModel_V.xml + // Cross-reference: Part_3.0 prose §N. + // https://docs.mtconnect.org/ + [Test] + public void Class_X_MinimumVersion_Is_V() + { + var minVer = typeof(MTConnect.Devices.X).GetField("DefaultMinimumVersion", + System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.NonPublic) + ?.GetValue(null) as System.Version; + + Assert.That(minVer, Is.EqualTo(new System.Version(V_major, V_minor))); + } +} +``` + +The test must cite its source — XMI / XSD / prose URL — in the fixture comment. Tests without source references are blocked at review. + +## Running the tier in CI + +The repo's CI workflow runs the unit + integration tier on every PR and the full compliance + E2E tier nightly. The compliance tier is gated in CI by the same `--compliance` flag, set as an environment variable. PRs that touch wire-format code paths trigger the full tier on the PR itself. + +## Where to next + +- [Per-version matrix](/compliance/per-version-matrix) — which spec versions the tier exercises. +- [Wire-format compliance](/compliance/wire-format) — what each format's compliance claim level means. +- [Spec cross-references](/compliance/spec-cross-references) — the citation pattern every test fixture follows. +- [Troubleshooting: XSD validation failures](/troubleshooting/xsd-validation-failures) — when the XSD validator rejects a model. diff --git a/docs/compliance/wire-format.md b/docs/compliance/wire-format.md new file mode 100644 index 000000000..d089aa2be --- /dev/null +++ b/docs/compliance/wire-format.md @@ -0,0 +1,76 @@ +# Wire-format compliance + +`MTConnect.NET` ships five wire formats. Each ones' on-the-wire shape is documented and validated against an authoritative source: an XSD for XML, the cppagent reference for the v2 JSON codec, and the spec prose for the SHDR adapter protocol. This page states each format's compliance posture — byte-for-byte parity with the reference, partial parity, or intentional divergence — and points at the test fixtures and source files that pin the claim. + +## Summary + +| Wire format | Reference | Posture | Codec class | +|---|---|---|---| +| XML | `MTConnect_.xsd` from [schemas.mtconnect.org](https://schemas.mtconnect.org/) | XSD-validated, every envelope, every version v1.0 — v2.7 | [`MTConnect.Formatters.Xml.XmlFormatter`](/api/MTConnect.Formatters.Xml/XmlFormatter) | +| JSON v1 | Library-defined (no normative JSON Schema exists) | Stable on the library, mirrors XML's object structure | [`MTConnect.Formatters.Json.JsonFormatter`](/api/MTConnect.Formatters.Json/JsonFormatter) | +| JSON-CPPAGENT (v2) | cppagent's `application/mtconnect+json` output | Byte-for-byte cppagent-parity (array-of-wrappers canonical shape) | [`MTConnect.Formatters.JsonCppAgent.JsonCppAgentFormatter`](/api/MTConnect.Formatters.JsonCppAgent/JsonCppAgentFormatter) | +| JSON-CPPAGENT-MQTT | cppagent's MQTT topic broker output | Byte-for-byte cppagent-parity (per-DataItem topic shape) | [`MTConnect.Formatters.JsonCppAgentMqtt.JsonCppAgentMqttFormatter`](/api/MTConnect.Formatters.JsonCppAgentMqtt/JsonCppAgentMqttFormatter) | +| SHDR | `Part_5.0` Network spec prose | Spec-compliant; both as adapter producer and as adapter consumer | [`MTConnect.Shdr.ShdrAdapter`](/api/MTConnect.Shdr/ShdrAdapter) | + +## XML + +The XML output of every Streams / Devices / Assets / Error envelope validates against the matching `MTConnect_.xsd` schema from [schemas.mtconnect.org](https://schemas.mtconnect.org/). The compliance test harness loads each shipped XSD as an embedded resource and validates a battery of golden-file fixtures against it (see [Test harness](/compliance/test-harness)). The XSDs are vendored unchanged into the test project, byte-identical to the upstream copies. Formatter pass: [`MTConnect.Formatters.Xml.XmlFormatter`](/api/MTConnect.Formatters.Xml/XmlFormatter) emits with `XmlWriterSettings.Indent = true` by default, configurable through the `IndentOutput` flag on each Module's configuration. + +The library's XSD validator deliberately uses a permissive parser configuration to remain cross-platform. The .NET BCL ships an XSD 1.0 validator; a small set of XSD 1.1-only assertions in the published schemas (such as `xs:assert` for the `representation` enum) are not enforced at parse time, but the library injects the equivalent runtime checks. See [Troubleshooting: XSD validation failures](/troubleshooting/xsd-validation-failures) for the diagnostic pattern when a model fails validation locally that succeeded against an XSD 1.1 validator. + +## JSON v1 + +JSON v1 is `MTConnect.NET`'s in-house JSON shape, predating the MTConnect Standard's adoption of a JSON wire format. It mirrors the XML object structure one-to-one — `` becomes `Streams`, every attribute becomes a field, every nested element becomes a nested object. The format is documented at [Wire formats: JSON v1](/wire-formats/json-v1) and remains a supported output for consumers that depend on it. The MTConnect Standard does not declare a normative JSON Schema (the JSON wire format in `Part_5` is descriptive prose, not a normative schema — see [Redmine #3889](https://projects.mtconnect.org/issues/3889)); the library's JSON v1 codec is the canonical shape against itself and is regression-tested with golden fixtures. + +## JSON-CPPAGENT (v2) + +The JSON-CPPAGENT codec is the library's byte-for-byte parity target with the [cppagent](https://github.com/mtconnect/cppagent) reference implementation's `application/mtconnect+json` output. The canonical shape is an array of single-key wrappers — each observation is wrapped in `{"": {...}}` — which the cppagent v2 codec adopted in 2023. + +Round-trip parity test fixtures live in `tests/MTConnect.NET-Common-Tests/CppAgentParity/` (golden files captured from a published cppagent build, byte-compared against `MTConnect.NET`'s output). A successful run is the gate that any consumer parsing cppagent's output can swap in `MTConnect.NET`'s agent and observe no change. + +Documented at [Wire formats: JSON-CPPAGENT](/wire-formats/json-cppagent). + +## JSON-CPPAGENT-MQTT + +The JSON-CPPAGENT-MQTT codec is the per-DataItem MQTT topic broker shape: every DataItem publishes to a topic of the form `/Device//` with a JSON-CPPAGENT-formatted payload. The cppagent reference's MQTT broker (introduced in cppagent v2) defines the topic template; `MTConnect.NET`'s [MqttRelay](/modules/) and [MqttBroker](/modules/) modules both speak this format. + +Compliance is enforced by golden-file fixtures of cppagent's published MQTT output and round-trip parity tests. Documented at [Wire formats: JSON-CPPAGENT-MQTT](/wire-formats/json-cppagent-mqtt). + +## SHDR + +The SHDR protocol is the legacy text-line adapter protocol described in `Part_5.0` Network of the MTConnect Standard ([docs.mtconnect.org](https://docs.mtconnect.org/)). A line is `timestamp|dataItemKey|value` with subsequent `|key|value` repeats for compound observations. `MTConnect.NET` implements SHDR both as an adapter (the agent reads SHDR lines from a TCP socket) and as a producer (the standalone adapter app emits SHDR lines from a custom data source). + +Compliance is enforced by: + +- A round-trip parser test against every example line in `Part_5.0`'s prose (each test fixture cites the spec section it pins). +- A heartbeat-and-reconnect state-machine test against the `Part_5.0` mandated SHDR connection lifecycle (PING / PONG, asterisk heartbeat). + +Documented at [Wire formats: SHDR](/wire-formats/shdr). + +## Variants of "compliant" + +Three claim levels in this section: + +- **XSD-validated** — for XML envelopes. The output is fed through the matching XSD; a parse-clean result is sufficient. +- **Byte-for-byte parity** — for the JSON-CPPAGENT and JSON-CPPAGENT-MQTT codecs. The output is byte-compared against a captured cppagent reference output of the same model. +- **Spec-compliant prose** — for SHDR. The behavior is exercised against test fixtures that pin the spec's stated examples and state machines. + +Each claim is auditable: the test fixtures cite the source ([Compliance: Spec cross-references](/compliance/spec-cross-references)), and the test harness records pass / fail per claim level. + +## Cross-implementation matrix + +A consumer asks "will this work against MTConnect.NET the same way it works against cppagent?" The answer: + +| Wire format | cppagent v2.5+ | MTConnect.NET | Round-trip parity? | +|---|---|---|---| +| XML | yes | yes | yes (XSD-validated both sides) | +| JSON v1 | no (cppagent never shipped JSON v1) | yes | n/a | +| JSON-CPPAGENT v2 | yes | yes | yes (golden-file byte-parity) | +| JSON-CPPAGENT-MQTT | yes | yes | yes (golden-file byte-parity) | +| SHDR | yes | yes | yes (per `Part_5.0` prose) | + +## Where to next + +- [Per-version matrix](/compliance/per-version-matrix) — which MTConnect spec versions each wire format supports. +- [Test harness](/compliance/test-harness) — how to run the compliance tier locally. +- [Wire formats: index](/wire-formats/) — per-format envelope shapes and sample payloads. diff --git a/docs/concepts/assets.md b/docs/concepts/assets.md new file mode 100644 index 000000000..3e7b53083 --- /dev/null +++ b/docs/concepts/assets.md @@ -0,0 +1,141 @@ +# Assets + +An **Asset** is a non-observation entity the device tracks: a cutting tool, a pallet, a fixture, a raw-material billet, an uploaded file. Assets exist outside the time-series stream — they are addressable by `AssetId`, they carry their own version history, and they are retrievable from the agent's `/asset/` endpoint independently of any DataItem. + +`MTConnect.NET` represents an Asset with [`MTConnect.Assets.Asset`](/api/MTConnect.Assets/Asset) implementing `IAsset`, and ships one concrete subclass per spec-defined Asset type: + +- [`CuttingToolAsset`](/api/MTConnect.Assets.CuttingTools/CuttingToolAsset) and its archetype variant `CuttingToolArchetypeAsset`. +- [`PalletAsset`](/api/MTConnect.Assets.Pallet/PalletAsset). +- [`FileAsset`](/api/MTConnect.Assets.Files/FileAsset) and its archetype variant `FileArchetypeAsset`. +- [`RawMaterialAsset`](/api/MTConnect.Assets.RawMaterials/RawMaterialAsset). +- [`FixtureAsset`](/api/MTConnect.Assets.Fixture/FixtureAsset). +- [`ComponentConfigurationParametersAsset`](/api/MTConnect.Assets.ComponentConfigurationParameters/ComponentConfigurationParametersAsset). +- [`QIFDocumentWrapperAsset`](/api/MTConnect.Assets.QIF/QIFDocumentWrapperAsset). + +## Identity + +Every Asset carries: + +- **`AssetId`** — globally unique, set once when the asset is authored. Used to retrieve the asset via `/asset/`. +- **`DeviceUuid`** — the Device the asset is associated with. +- **`Type`** — `"CuttingTool"`, `"Pallet"`, `"File"`, etc. Matches the `TypeId` constant on the concrete subclass. +- **`Timestamp`** — when the asset was last updated. +- **`Removed`** — flag set true when the agent receives an `AssetRemoved` instruction; the asset stays in the buffer with `Removed=true` until the buffer recycles it. +- **`Hash`** — SHA-1 over the asset's identity and content; consumers detect a change without re-parsing the body. + +```csharp +public partial class Asset : IAsset +{ + public string AssetId { get; set; } + public string DeviceUuid { get; set; } + public string Type { get; set; } + public DateTime Timestamp { get; set; } + public bool Removed { get; set; } + public string Hash { get; } + public MTConnectEntityType EntityType => MTConnectEntityType.Asset; +} +``` + +## CuttingTool + +The richest Asset type. A `CuttingToolAsset` describes one physical cutting tool with its serial number, life-cycle state, measurements, and per-edge `CuttingItem` records. The library exposes the spec's full structure: + +```csharp +using MTConnect.Assets.CuttingTools; +using MTConnect.Assets.CuttingTools.Measurements; + +var tool = new CuttingToolAsset +{ + AssetId = "TOOL-001234", + DeviceUuid = device.Uuid, + SerialNumber = "ABC-1234", + ToolId = "T1", + Description = "12mm carbide endmill, 4-flute", +}; + +var lifeCycle = new CuttingToolLifeCycle +{ + CutterStatus = CutterStatusType.NEW, + Location = new Location { Type = "POT", PositiveOverlap = "0", NegativeOverlap = "0" }, +}; +lifeCycle.AddMeasurement(new CuttingDiameterMaxMeasurement { Value = 12.0m }); +tool.CuttingToolLifeCycle = lifeCycle; +``` + +The `CuttingToolArchetypeAsset` variant (`Type == "CuttingToolArchetype"`) describes the tool's design-time blueprint — the shape every instance of the part-number-X conforms to — and the `CuttingToolAsset` references its archetype via `CuttingToolArchetypeReference`. Source: SysML `CuttingToolAsset` and `CuttingToolArchetype` classes ([`mtconnect/mtconnect_sysml_model`](https://github.com/mtconnect/mtconnect_sysml_model)). + +## Pallet + +A `PalletAsset` describes a pallet on a transfer system: its dimensions, its loaded vs unloaded shape, the work-piece(s) currently on it. The MTConnect Standard introduced typed measurements for pallets in v2.4, replacing the earlier free-form `Measurement` element with concrete classes: + +- `HeightMeasurement`, `WidthMeasurement`, `LengthMeasurement`, `WeightMeasurement`, `SwingMeasurement` — pallet-empty geometry. +- `LoadedHeightMeasurement`, `LoadedWidthMeasurement`, `LoadedLengthMeasurement`, `LoadedWeightMeasurement`, `LoadedSwingMeasurement` — pallet-with-workpiece geometry. + +Each measurement is a separate concrete class with a `Value` (decimal), an optional `NativeUnits`, an optional `Code`, and `Units` defaulted from the spec ([`MTConnect.Assets.Pallet.HeightMeasurement`](/api/MTConnect.Assets.Pallet/HeightMeasurement) etc.). Older models with a free-form `Measurement` child still deserialize for backward compatibility. + +```csharp +using MTConnect.Assets.Pallet; + +var pallet = new PalletAsset +{ + AssetId = "PALLET-7", + DeviceUuid = device.Uuid, + Type = PalletAsset.TypeId, +}; +pallet.Measurements = new IMeasurement[] +{ + new HeightMeasurement { Value = 200m }, + new WidthMeasurement { Value = 400m }, + new LoadedHeightMeasurement { Value = 250m }, +}; +``` + +## File + +A `FileAsset` describes a file the device wants to publish: a CAD model, a control program, a calibration table, a measurement output. The asset carries: + +- `FileLocation` — where to fetch the bytes. +- `FileProperty` — typed metadata (size, MIME type, etc.). +- `FileComment` — free-form notes. +- `Destination` — where the consumer should place the file. +- `ApplicationCategory` and `ApplicationType` — what the file is for. + +The `FileArchetypeAsset` variant describes the file-class's design-time shape (a "G-code file" archetype with declared properties), and the `FileAsset` instance references the archetype. Source: SysML `File` and `FileArchetype` classes ([`mtconnect/mtconnect_sysml_model`](https://github.com/mtconnect/mtconnect_sysml_model)). + +## RawMaterial + +A `RawMaterialAsset` describes the raw material the device is consuming: stock dimensions, material composition, form (`BAR`, `BLOCK`, `SHEET`, etc. — enum `Form`). Carries optional `MaterialLifeCycle` records that track quantity consumed over time. Source: SysML `RawMaterial` class. + +## Fixture, ComponentConfigurationParameters, QIF + +Three less-common asset types, each shipped as a distinct subclass: + +- `FixtureAsset` — a workholding fixture's identity and configuration. +- `ComponentConfigurationParametersAsset` — a snapshot of a Component's parameter set. Introduced in v2.2. +- `QIFDocumentWrapperAsset` — wraps a [QIF](https://qifstandards.org/) measurement document. + +## Asset registration and lifecycle + +The agent maintains an asset buffer separate from the observation buffer. Assets are added through: + +```csharp +agent.AddAsset(deviceUuid, asset); +``` + +The buffer's size is bounded by `assetBufferSize` (default `1000` in `agent.config.yaml`); when full, the buffer evicts the least-recently-updated asset. Removal is logical: setting an asset's `Removed` flag (or sending `AssetRemoved` as an EVENT observation on the `AssetRemoved` DataItem) marks the asset removed without freeing its slot, so a consumer querying `/asset?removed=true` still sees the soft-deleted assets. + +Every asset change drives an `AssetChanged` EVENT observation on the Device's `AssetChanged` DataItem (auto-installed on the Agent Device). Consumers subscribe to that DataItem to know when to re-fetch `/asset/`. Source: `Part_4.0` Assets §3 ([docs.mtconnect.org](https://docs.mtconnect.org/)). + +## AssetCount representation + +The agent exposes an `AssetCount` DataItem that reports the count of each Asset type the agent currently holds. The Standard's three normative sources disagree on whether this DataItem is a scalar EVENT (`VALUE`) or a `DATA_SET`. `MTConnect.NET` follows the SysML XMI and the XSD, both of which declare a scalar EVENT — the cppagent reference auto-injects `representation="DATA_SET"`, but XMI is the source of truth. The library's posture is documented at [Compliance: Known divergences](/compliance/known-divergences) and tracked upstream at [Redmine #3890](https://projects.mtconnect.org/issues/3890). + +## Wire shape + +Assets serialize through the `MTConnectAssets_.xsd` envelope. The XML codec lives in `MTConnect.NET-XML`; the JSON-CPPAGENT codec in `MTConnect.NET-JSON-cppagent`. The `/asset` endpoint returns one Asset per query, or the union of every asset matching the filter. See [Wire formats](/wire-formats/) for the envelope shape. + +## Where to next + +- [`IAsset` API reference](/api/MTConnect.Assets/IAsset). +- [Cookbook: Write an agent](/cookbook/write-an-agent) — agents that emit Assets. +- [Compliance: Per-version matrix](/compliance/per-version-matrix) — which Asset types ship in which spec version. diff --git a/docs/concepts/components.md b/docs/concepts/components.md new file mode 100644 index 000000000..01c05ce53 --- /dev/null +++ b/docs/concepts/components.md @@ -0,0 +1,128 @@ +# Components + +A **Component** is a recursively-nested machine piece under a [Device](/concepts/devices). Components model the physical and logical breakdown of equipment — an Axis, a Path, a Spindle, a Coolant subsystem, a Door — and they carry the [DataItems](/concepts/data-items) that observe each piece. `MTConnect.NET` represents a Component with the [`MTConnect.Devices.Component`](/api/MTConnect.Devices/Component) class implementing `IComponent`, and ships one concrete subclass per Component type defined in the MTConnect SysML model (`AxisComponent`, `ControllerComponent`, `LinearComponent`, `RotaryComponent`, `SpindleComponent`, and so on, generated from the SysML XMI into `.g.cs` files under `libraries/MTConnect.NET-Common/Devices/Components/`). + +## The Component tree + +A Component nests under either a Device or another Component. The tree is unconstrained in depth; the MTConnect Standard does not cap it. Every Component carries: + +- **`Id`** — locally unique within the Device. Used to compose paths (`mill-01.path.axes.x`). +- **`Name`** — display name. +- **`Type`** — the `TypeId` of the concrete Component class (`"Axis"`, `"Controller"`, `"Spindle"`). +- **`Parent`** — the `IContainer` (Device or Component) that owns it. +- **`Components`** — children Components. +- **`Compositions`** — child Compositions (see below). +- **`DataItems`** — DataItems attached directly to this Component. + +```mermaid +classDiagram + direction TB + IContainer <|-- Device + IContainer <|-- Component + Component <|-- AxisComponent + Component <|-- ControllerComponent + Component <|-- PathComponent + Component <|-- SpindleComponent + Component <|-- AxesComponent + Component <|-- ControllersComponent + Device "1" o-- "*" Component : Components + Device "1" o-- "*" Composition : Compositions + Device "1" o-- "*" DataItem : DataItems + Component "1" o-- "*" Component : Components + Component "1" o-- "*" Composition : Compositions + Component "1" o-- "*" DataItem : DataItems + Component "1" --> "1" IContainer : Parent + class IContainer { + +string Id + +string Uuid + +string Name + } + class Component { + +string Type + +IContainer Parent + +Version MinimumVersion + +Version MaximumVersion + } +``` + +The `Type` string is canonical — it is the camel-case `TypeId` constant on the concrete class — and matches the element name the XSD expects on the wire. `AxisComponent.TypeId == "Axis"`, `ControllerComponent.TypeId == "Controller"`, etc. The MTConnect SysML model is the source of truth for the Component class hierarchy ([`mtconnect/mtconnect_sysml_model`](https://github.com/mtconnect/mtconnect_sysml_model)); generated `.g.cs` files carry the `MinimumVersion` / `MaximumVersion` introducing each Component. + +## Organizer Components + +A few Components exist solely as containers for siblings of the same logical kind: an `Axes` Organizer holds `Axis` children, a `Controllers` Organizer holds `Controller` children, an `Auxiliaries` Organizer holds auxiliary subsystems. The MTConnect Standard treats Organizers as required wrappers — an `Axis` must live under an `Axes`, not directly under a `Device` — and `MTConnect.NET` enforces this in [`Device.AddComponent`](/api/MTConnect.Devices/Device#AddComponent) and `Component.AddComponent`: passing a non-organizer Component whose type has an associated Organizer triggers auto-creation of the Organizer wrapper if none is present. + +```csharp +using MTConnect.Devices; +using MTConnect.Devices.Components; + +var device = new Device { Id = "mill", Type = Device.TypeId }; +var xAxis = new LinearComponent { Id = "x", Name = "X" }; + +device.AddComponent(xAxis); +// device.Components -> [AxesComponent { Id = "ax", Components = [xAxis] }] +// The Axes organizer was created automatically. +``` + +The Organizer lookup runs through [`MTConnect.Devices.Organizers`](/api/MTConnect.Devices/Organizers), a static table that maps a Component type to its required Organizer type. `IComponent.IsOrganizer` flags Organizer instances so traversal code can skip past them when presenting a "logical" device tree to a UI. + +## Compositions + +A **Composition** is a finer-grained part underneath a Component — the bearing inside an Axis, the chip conveyor inside a coolant system, the door panel inside a Door Component. Compositions exist from MTConnect v1.4 onward (the `Composition` class's `DefaultMinimumVersion` is `MTConnectVersions.Version14`), and they share the DataItem-bearing pattern with Components: + +- A Composition has an `Id`, a `Name`, a `Type`, and a `DataItems` collection. +- A Composition has no nested `Components` — the tree of structural breakdown stops at the Composition level. +- A Composition has a `Parent` of type `IContainer`. + +Compositions are valuable when the granularity below a Component is observable but does not warrant a full Component sub-tree. The classic case: a `LinearComponent` representing an axis has DataItems for `POSITION` and `LOAD`, but the axis's `Motor` Composition has its own `TEMPERATURE` DataItem. Modeling the motor as a Component would add nesting noise; a Composition is the right granularity. + +```csharp +using MTConnect.Devices; +using MTConnect.Devices.Components; +using MTConnect.Devices.Compositions; + +var spindle = new SpindleComponent { Id = "spindle" }; +var motor = new MotorComposition { Id = "motor", Name = "Spindle motor" }; +motor.AddDataItem(new TemperatureDataItem(motor.Id)); +spindle.AddComposition(motor); +``` + +The wire shape on `/probe` reflects the nesting: + +```xml + + + + + + + + + +``` + +## Querying the tree + +`Component` mirrors the lookup helpers on `Device`: + +- `GetComponents()` — every Component beneath this one, recursively. +- `GetComponent(name?, searchType?)` — typed lookup. `SearchType.Child` searches direct children; `SearchType.AnyLevel` searches the whole sub-tree. +- `GetCompositions()` / `GetComposition(...)` — same shape, Composition-typed. +- `GetDataItems()` — every DataItem under this Component, including those on its Compositions and recursive sub-Components. + +Typed lookup is the recommended path. Passing a concrete generic type pulls the `TypeId` constant from the type reflection-free at the call site: + +```csharp +var spindle = device.GetComponent(); +var motorTemp = spindle.GetDataItem(); +``` + +## Version gating + +Every Component class declares `MinimumVersion` and (optionally) `MaximumVersion`. When `Device.Process(IDevice, Version)` serializes the model for a target version, Components whose `MinimumVersion` is above the target are pruned and Components whose `MaximumVersion` is below the target are pruned. This is how the same model serves both a v1.6 consumer and a v2.5 consumer from one in-memory tree — the serializer prunes against the requested version's compatibility window, never against the model's declared version. The SysML model is consulted for every type's introduction version; see [Compliance: Spec cross-references](/compliance/spec-cross-references) for the citation pattern. + +## Where to next + +- [DataItems](/concepts/data-items) — the primitive observable points hanging off Components. +- [Relationships](/concepts/relationships) — cross-Component links (parent, coordinate-system, ID-references). +- [`IComponent` API reference](/api/MTConnect.Devices/IComponent). +- [Cookbook: Write an agent](/cookbook/write-an-agent) — building a model from scratch. diff --git a/docs/concepts/data-items.md b/docs/concepts/data-items.md new file mode 100644 index 000000000..fc6587425 --- /dev/null +++ b/docs/concepts/data-items.md @@ -0,0 +1,114 @@ +# DataItems + +A **DataItem** is the primitive observable point on a [Component](/concepts/components) or [Composition](/concepts/components#compositions). It does not carry a value — it declares the shape of values that the agent expects. An `AVAILABILITY` EVENT DataItem says "this point reports `AVAILABLE` or `UNAVAILABLE` over time"; a `POSITION` SAMPLE DataItem says "this point reports a numeric position over time with a configured unit". The runtime stream of values associated with a DataItem is described by [Observations](/concepts/observations). + +`MTConnect.NET` represents a DataItem with the [`MTConnect.Devices.DataItem`](/api/MTConnect.Devices/DataItem) class implementing `IDataItem`, and ships one concrete subclass per spec-defined DataItem type. The concrete classes live in `libraries/MTConnect.NET-Common/Devices/DataItems/` and are generated from the MTConnect SysML model: `AvailabilityDataItem`, `PositionDataItem`, `EmergencyStopDataItem`, `AssetCountDataItem`, etc. + +## Three categories + +Every DataItem belongs to exactly one of three categories, defined in [`MTConnect.Devices.DataItemCategory`](/api/MTConnect.Devices/DataItemCategory): + +- **`EVENT`** — a discrete-state observation. Values are strings (`READY`, `INTERRUPTED`, `AVAILABLE`) or numerics that do not interpolate. Examples: `AVAILABILITY`, `EMERGENCY_STOP`, `CONTROLLER_MODE`, `EXECUTION`. Source: MTConnect Standard `Part_2.0` Streams §3 ([docs.mtconnect.org](https://docs.mtconnect.org/)). +- **`SAMPLE`** — a continuous-time numeric observation. Values are scalars or vectors that have a unit and can be interpolated. Examples: `POSITION`, `TEMPERATURE`, `LOAD`, `SPINDLE_SPEED`. SAMPLE DataItems carry a `Units` attribute, an optional `NativeUnits` attribute, and an optional `SignificantDigits` attribute. +- **`CONDITION`** — an alarm-style observation that aggregates into a level: `NORMAL`, `WARNING`, `FAULT`, or `UNAVAILABLE`. Conditions carry an optional `nativeCode`, an optional `qualifier` (`HIGH` / `LOW`), and a human-readable message. Examples: `SYSTEM`, `LOGIC_PROGRAM`, `MOTION_PROGRAM`. Conditions deserve their own treatment — see [Observations: Conditions](/concepts/observations#conditions). + +The category drives serialization shape (a `` element wraps SAMPLE observations on the wire; a `` element wraps EVENT observations; a `` element wraps CONDITION observations) and it drives which Observation subclass the runtime constructs. + +## Identity attributes + +```csharp +public partial class DataItem : IDataItem +{ + public string Id { get; set; } + public string Name { get; set; } + public string Type { get; set; } + public string SubType { get; set; } + public DataItemCategory Category { get; set; } + + public string Units { get; set; } + public string NativeUnits { get; set; } + public int? SignificantDigits { get; set; } + + public DataItemRepresentation Representation { get; set; } + public DataItemStatistic Statistic { get; set; } + public DataItemCoordinateSystem CoordinateSystem { get; set; } + + public IContainer Container { get; set; } + public IDevice Device { get; set; } + + public virtual Version MinimumVersion { get; } + public virtual Version MaximumVersion { get; } +} +``` + +- **`Id`** — locally unique within the Device. Required by the spec on the wire. +- **`Name`** — optional. Where present, the adapter line `LATHE.AXIS.X|` resolves to a DataItem with `Name == "LATHE.AXIS.X"`. The SHDR adapter prefers `Name` lookup; the JSON consumer prefers `Id`. +- **`Type`** — the canonical type identifier in `UNDERSCORE_UPPER` form (`"AVAILABILITY"`, `"POSITION"`, `"EMERGENCY_STOP"`). The constant lives on the concrete class's `TypeId` field. +- **`SubType`** — refines the type. `POSITION` has subtypes `ACTUAL`, `COMMANDED`, `PROGRAMMED`, `TARGET`. `TEMPERATURE` has subtypes `ACTUAL`, `CALCULATED`. +- **`Category`** — EVENT / SAMPLE / CONDITION. +- **`Units`** — for SAMPLE DataItems. Canonical units are listed in the SysML model's `UnitsEnum` ([`mtconnect/mtconnect_sysml_model`](https://github.com/mtconnect/mtconnect_sysml_model)). +- **`Representation`** — `VALUE` (default), `DATA_SET`, `TABLE`, or `TIME_SERIES`. See [Representations](#representations) below. +- **`Container`** / **`Device`** — back-pointers to the Component / Device that owns the DataItem. + +## Representations + +`DataItemRepresentation` controls the shape of every observation that the DataItem produces: + +- **`VALUE`** (default) — one scalar per observation. The wire shape is `scalar-value`. +- **`DATA_SET`** — a set of key-value entries per observation. Keys are spec-defined for some types (`PART_COUNT` discriminates `accepted`, `rejected`, `bad`) or adapter-defined for others. Wire shape: `v1v2`. +- **`TABLE`** — entries-of-entries. Each top-level entry holds a sub-map. Used by `WORK_OFFSET_TABLE` and similar table-shaped DataItems. +- **`TIME_SERIES`** — a sample of values at a fixed cadence. Wire shape: `v1 v2 v3 ...`. + +Representations are version-gated: `DATA_SET` enters the spec at v1.5, `TABLE` at v1.6, and the wire-shape rules for each are codified in `MTConnectStreams_.xsd` ([schemas.mtconnect.org](https://schemas.mtconnect.org/)). The library's [Streams envelope](/wire-formats/) honours the gating when serializing a DataItem whose `Representation` is more recent than the requested response version. + +## Constructing DataItems + +Three idiomatic constructors: + +```csharp +using MTConnect.Devices; +using MTConnect.Devices.DataItems; + +// 1. Typed — the recommended path. The DataItem subclass carries the +// canonical Type / Category / default Units, so the call site is succinct. +var avail = new AvailabilityDataItem("ctrl"); + +// 2. Untyped via the base DataItem constructor. The constructor takes +// category + type + subType + id; suitable for adapter-side dynamic models. +var custom = new DataItem( + DataItemCategory.SAMPLE, + "POSITION", + "ACTUAL", + "x-pos-actual"); + +// 3. The container shortcut — attach a typed DataItem to a Component or +// Composition by generic. +component.AddDataItem(); +``` + +Construction through a typed class is preferable because the class also carries the `DescriptionText`, `MinimumVersion`, and any default `Units` value from the SysML model. The shortcut form leaves those nulls and pushes the burden of correctness onto the caller. + +## Filters, Constraints, Definitions + +A DataItem can carry side metadata that refines what the agent emits: + +- **`Filters`** — server-side filters that suppress observations. The two spec-defined filter types are `MINIMUM_DELTA` (only emit if `|new - last| > delta`) and `PERIOD` (emit at most once per period). Class: [`DataItemFilter`](/api/MTConnect.Devices/DataItemFilter); enum: [`DataItemFilterType`](/api/MTConnect.Devices/DataItemFilterType). +- **`Constraints`** — declared bounds and enumerated allowed values. `MAXIMUM`, `MINIMUM`, `VALUE` lists. Constraints are advisory in the spec — the agent emits values that violate the constraints, but consumers may flag them as alarms. +- **`Definition`** — for `DATA_SET` / `TABLE` representations, the structural definition of the entries and the cells. Class: [`DataItemDefinition`](/api/MTConnect.Devices/DataItemDefinition). +- **`ResetTrigger`** — for accumulators (`PART_COUNT`, `ACCUMULATED_TIME`), the lifecycle event that zeroes the accumulator: `SHIFT`, `DAY`, `MAINTENANCE`. Enum: [`DataItemResetTrigger`](/api/MTConnect.Devices/DataItemResetTrigger). +- **`Source`** — the SHDR / adapter key that maps incoming lines to this DataItem. Class: [`DataItemSource`](/api/MTConnect.Devices/DataItemSource). + +## DataItem hashing and change detection + +`DataItem.GenerateHash()` produces a SHA-1 hash over identity, category, type/subType, units, representation, statistic, coordinate-system, filter list, constraints, definition, and source. A change to any of those values changes the hash. The Device's hash includes every DataItem hash, so a single DataItem edit propagates up to the Device's `Hash` attribute on `/probe` — consumers detect that a model edit happened without re-parsing the full Devices document. + +## Version gating + +Like Components, every DataItem class carries `MinimumVersion` and `MaximumVersion`. `DataItem.Process(IDataItem, Version)` is the version-aware serializer; it strips properties added after the target version (for instance, `Statistic` is v1.2+; serializing for v1.1 elides it) and rejects DataItems whose `MinimumVersion` is above the target. Source: the SysML model's per-class introduction version, mirrored into the generated `.g.cs` files. Source-of-truth note: when the SysML model and the XSD disagree about a DataItem's introduction version, `MTConnect.NET` follows the SysML model — see [Compliance: Known divergences](/compliance/known-divergences) for the precedent. + +## Where to next + +- [Observations](/concepts/observations) — the runtime values flowing through DataItems. +- [Relationships](/concepts/relationships) — DataItem-to-DataItem references. +- [`IDataItem` API reference](/api/MTConnect.Devices/IDataItem). +- [Cookbook: Write an agent](/cookbook/write-an-agent). diff --git a/docs/concepts/devices.md b/docs/concepts/devices.md new file mode 100644 index 000000000..2836c1859 --- /dev/null +++ b/docs/concepts/devices.md @@ -0,0 +1,122 @@ +# Devices + +A **Device** is the top-level addressable entity that an MTConnect Agent emits observations for. Conceptually it is "one machine" — a CNC mill, a robot cell, a coordinate-measuring machine, a vibration sensor cluster — and in `MTConnect.NET` it maps directly to the [`MTConnect.Devices.Device`](/api/MTConnect.Devices/Device) class implementing `IDevice`. Every Device carries a UUID, a human-readable name, a type identifier, and a tree of [Components](/concepts/components), [Compositions](/concepts/components#compositions), and [DataItems](/concepts/data-items) underneath it. + +## Identity and structure + +A Device has three identity attributes, all required by the MTConnect Standard: + +- **`Uuid`** — globally unique, set once when the model is authored and never re-generated. Consumers correlate observations across agent restarts on this field. +- **`Id`** — locally unique within the model tree. Used to address the Device in the path-query syntax (`/probe/` resolves the same node as `/probe?path=...//Device[@id='']`). +- **`Name`** — display name. Free-form; not required to be unique across an installation. + +The class signature is straightforward: + +```csharp +public partial class Device : IDevice +{ + public const string TypeId = "Device"; + + public string Uuid { get; set; } + public string Id { get; set; } + public string Name { get; set; } + public string Type { get; set; } + + public IEnumerable Components { get; set; } + public IEnumerable Compositions { get; set; } + public IEnumerable DataItems { get; set; } +} +``` + +The `Type` string defaults to `"Device"` and matches the `TypeId` constant the class exposes. Subtypes (such as the Agent's self-describing Device, where `Type == "Agent"`) carry their own `TypeId` and resolve to a distinct concrete class. The spec defines `Device` and `Agent` as the two concrete Device types in `Part_3.0` of the MTConnect Standard ([docs.mtconnect.org](https://docs.mtconnect.org/)); `MTConnect.NET` adds no third Device subtype beyond those. + +## The Agent Device + +When the agent boots it auto-registers a self-describing Device of type `"Agent"` — a `MTConnect.Devices.Agent` instance — that emits agent-introspection observations (`AVAILABILITY` for the agent itself, `ASSET_CHANGED`, `ASSET_REMOVED`, `MTCONNECT_VERSION`, and adapter / module health DataItems). Disable this with `enableAgentDevice: false` in `agent.config.yaml` when a consumer is strict about device counts. The Agent Device first appears in v1.7 of the Standard — the library emits no Agent Device when serializing for a version below `MTConnectVersions.Version17`, mirroring the version-gating in `Device.Process(IDevice, Version)`. + +## Authoring a Device in code + +The minimal in-code constructor produces a Device with a random `Id`, a random `Uuid`, and an empty tree: + +```csharp +using MTConnect.Devices; +using MTConnect.Devices.Components; +using MTConnect.Devices.DataItems; + +var device = new Device +{ + Id = "mill-01", + Uuid = "1234-5678-9abc-def0", + Name = "Mill #1", + Type = Device.TypeId, +}; + +// Attach a Controller component and an AVAILABILITY data item. +var controller = new ControllerComponent { Id = "ctrl" }; +controller.AddDataItem(new AvailabilityDataItem(controller.Id)); +device.AddComponent(controller); +``` + +`AddComponent` is not just a list append. It walks the [Organizers](/api/MTConnect.Devices/Organizers) table to decide whether the child Component needs to nest under an Organizer Component (an `Axes` Organizer for an `Axis`, a `Controllers` Organizer for a `Controller`, etc.) and creates the Organizer on demand. The same logic runs for `AddDataItem`, which assigns the data item's `Container` to the Device and re-runs the `DataItemIdFormat` template (`Component._defaultDataItemIdFormat`) to derive a deterministic Id. + +## Authoring a Device in `Devices.xml` + +For deployments that ship a static model alongside the agent, the canonical authoring path is an XML file that the agent reads at startup. The schema is the `MTConnectDevices_.xsd` envelope from [schemas.mtconnect.org](https://schemas.mtconnect.org/). A minimal example: + +```xml + +
+ + + + + + + + + + + + + + + +``` + +The agent loads `Devices.xml` through the XML codec in `MTConnect.NET-XML` and validates it against the appropriate XSD. Validation failures are not silent — see [Troubleshooting: XSD validation failures](/troubleshooting/xsd-validation-failures) for the diagnostic flow. + +## Device-tree traversal + +`Device` exposes recursive traversal helpers so a consumer can ask "every Component under me, regardless of depth" or "every DataItem matching this Type" without writing the recursion itself: + +- `GetComponents()` — flat enumeration of every Component in the tree. +- `GetCompositions()` — flat enumeration of every Composition. +- `GetDataItems()` — flat enumeration of every DataItem across the Device, its Components, and its Compositions. +- `GetDataItemByKey(key)` — resolves a DataItem by `Id`, then `Name`, then `Source.DataItemId`, then `Source.Value` — the same precedence the SHDR adapter uses when matching an incoming line to a target DataItem. +- `GetDataItemByType(typeId, subType?)` — type-first lookup. + +The recursive traversal respects Component nesting (an `Axis` under an `Axes` Organizer under a `Path` under the root Device is still reachable in a single `GetDataItems()` call). + +## Device hashing + +`Device.GenerateHash()` produces an SHA-1 hash over the Device's identity properties plus the hashes of every DataItem, Composition, and Component beneath it. Two Devices with identical models hash to identical strings; that hash drives the `deviceModelChangeTime` value that the agent advertises on `/probe`, and the v2.2+ Header's `Hash` attribute. Consumers detect a model change by comparing the cached hash against the live one, without diffing the full XML. + +```csharp +var hashV1 = device.GenerateHash(); +device.AddDataItem(new EmergencyStopDataItem("ctrl")); +var hashV2 = device.GenerateHash(); +// hashV1 != hashV2 — the DataItem addition changed the device's identity. +``` + +## Where to next + +- [Components](/concepts/components) — the recursively-nested machine pieces. +- [DataItems](/concepts/data-items) — the primitive observable points. +- [Observations](/concepts/observations) — the time-stamped values flowing through DataItems. +- [`IDevice` API reference](/api/MTConnect.Devices/IDevice) — every property, every method. +- [Cookbook: Write an agent](/cookbook/write-an-agent) — a hands-on walk-through. diff --git a/docs/concepts/index.md b/docs/concepts/index.md new file mode 100644 index 000000000..7b1ea3fff --- /dev/null +++ b/docs/concepts/index.md @@ -0,0 +1,80 @@ +# Concepts + +This section maps the MTConnect Standard's core concepts to the public types in `MTConnect.NET`. Read it once and the rest of the site falls into place — the [API reference](/api/) names the types, [Configure & Use](/configure/) configures them, [Wire formats](/wire-formats/) serializes them, but everything ultimately reduces to the five concepts described here. + +## The five concepts + +- **Device** — the top-level addressable thing the agent emits observations for. A CNC mill, a robot, a 3D printer. Modeled by the `Device` class in `MTConnect.Devices`. +- **Component** — a recursively-nested machine piece under a Device (an axis, a path, a spindle, a controller). Modeled by `Component` and its many specializations (`Axes`, `Path`, `Spindle`, `Controller`, …) in `MTConnect.Devices.Components`. +- **DataItem** — a primitive observable point on a Component (a position, a temperature, an execution state, a tool offset). Modeled by `DataItem` and its specializations in `MTConnect.Devices.DataItems`. A DataItem declares its `type`, `subType`, `category` (`SAMPLE` / `EVENT` / `CONDITION`), `units`, and `nativeUnits`; observations get serialized using those declarations. +- **Observation** — a time-stamped value flowing through a DataItem. Modeled by `Observation` and its specializations (`SampleObservation`, `EventObservation`, `ConditionObservation`) in `MTConnect.Observations`. Carries a `sequence` number, a `timestamp`, and the value itself. +- **Asset** — a non-observation entity the device tracks (a cutting tool, a fixture, a file, a raw material, a pallet). Modeled by `Asset` and its specializations in `MTConnect.Assets`. Assets have an identity that outlives any single observation. + +## Class relationships + +```mermaid +classDiagram + class Device { + +string Id + +string Name + +string Uuid + +List~Component~ Components + +List~DataItem~ DataItems + } + class Component { + +string Id + +string Type + +List~Component~ Components + +List~DataItem~ DataItems + } + class DataItem { + +string Id + +string Type + +string SubType + +DataItemCategory Category + +string Units + } + class Observation { + +string DataItemId + +ulong Sequence + +DateTime Timestamp + } + class Asset { + +string AssetId + +string Type + +DateTime Timestamp + } + + Device "1" *-- "0..*" Component + Component "1" *-- "0..*" Component + Device "1" *-- "0..*" DataItem + Component "1" *-- "0..*" DataItem + DataItem "1" -- "0..*" Observation + Device "1" -- "0..*" Asset +``` + +## How a request flows through the agent + +```mermaid +sequenceDiagram + participant Adapter as SHDR / MQTT adapter + participant Agent as MTConnectAgent + participant Buffer as Sequence buffer + participant Broker as MTConnectAgentBroker + participant Client as HTTP / MQTT client + + Adapter->>Agent: Push observation (DataItemId, value, timestamp) + Agent->>Agent: Validate against DataItem declaration + Agent->>Buffer: Append with new sequence number + Client->>Broker: GET /current + Broker->>Buffer: Read latest observation per DataItem + Buffer-->>Broker: Observations + Broker-->>Client: Streams envelope (XML or JSON) +``` + +## Where to look next + +- **The data model in code**: see the API pages for `Device`, `Component`, `DataItem`, `Observation`, and `Asset`. Each page lists the spec versions in which the type appears and the wire codecs that serialize it. +- **The MTConnect Standard prose**: . +- **Validating that your configured devices match the spec**: see the [`Devices.xml` validation guide](/configure/agent) under Configure & Use. +- **Recipes that use these concepts**: [Cookbook](/cookbook/). diff --git a/docs/concepts/observations.md b/docs/concepts/observations.md new file mode 100644 index 000000000..f1ce8f749 --- /dev/null +++ b/docs/concepts/observations.md @@ -0,0 +1,169 @@ +# Observations + +An **Observation** is the time-stamped value flowing through a [DataItem](/concepts/data-items). DataItems declare the shape; Observations carry the data. Every Observation in `MTConnect.NET` inherits from [`MTConnect.Observations.Observation`](/api/MTConnect.Observations/Observation) and is one of three concrete subclasses chosen by the DataItem's `Category`: + +- [`SampleObservation`](/api/MTConnect.Observations/SampleObservation) for SAMPLE DataItems. +- [`EventObservation`](/api/MTConnect.Observations/EventObservation) for EVENT DataItems. +- [`ConditionObservation`](/api/MTConnect.Observations/ConditionObservation) for CONDITION DataItems. + +```mermaid +classDiagram + direction TB + IObservation <|-- Observation + Observation <|-- SampleObservation + Observation <|-- EventObservation + Observation <|-- ConditionObservation + SampleObservation <|-- SampleValueObservation + SampleObservation <|-- SampleDataSetObservation + SampleObservation <|-- SampleTableObservation + SampleObservation <|-- SampleTimeSeriesObservation + EventObservation <|-- EventValueObservation + EventObservation <|-- EventDataSetObservation + EventObservation <|-- EventTableObservation + class Observation { + +string DataItemId + +string DeviceUuid + +DateTime Timestamp + +ulong Sequence + +ulong InstanceId + +string Quality + +Observation~ValueKey~ Values + } + class ConditionObservation { + +ConditionLevel Level + +string NativeCode + +ConditionQualifier Qualifier + +string Message + } +``` + +## Core fields + +Every Observation carries: + +- **`DataItemId`** — must equal the `Id` of a DataItem present in the Device's model. The agent rejects observations whose `DataItemId` does not resolve. +- **`DeviceUuid`** — the owning Device's `Uuid`. +- **`Timestamp`** — when the value was observed. Encoded as UTC ISO 8601 on the wire, with optional fractional seconds (`2025-01-01T12:34:56.789Z`). +- **`Sequence`** — assigned by the agent as the observation enters the buffer. Monotonically increasing across the agent's lifetime; resets only on a buffer wipe. Consumers use Sequence to paginate `/sample` responses. +- **`InstanceId`** — the agent's instance identifier. A consumer that sees the instance change knows the agent restarted and the sequence numbers reset. +- **`Quality`** — optional. Carries data-quality annotation (`VALID`, `INVALID`, `QUESTIONABLE`, `OVERRANGE`). Enum source: SysML `QualityEnum`. Introduced in v2.3. +- **`Values`** — the dictionary of value entries the Observation carries. For VALUE-representation observations there is one entry keyed `"VALUE"`; for DATA_SET / TABLE / TIME_SERIES the entries map to the spec-defined keys. + +## The Unavailable sentinel + +The MTConnect Standard mandates that when an agent cannot determine a valid value for a DataItem, the result MUST be reported as the literal string `UNAVAILABLE`. The library makes this a first-class constant on [`Observation.Unavailable`](/api/MTConnect.Observations/Observation): + +```csharp +public const string Unavailable = "UNAVAILABLE"; +``` + +Every serializer, every codec, every Output transformer (under `MTConnect.NET-Common/Observations/Output/`) treats `Unavailable` as the canonical absent-value sentinel. Source: MTConnect Standard `Part_2.0` Streams §3 ([docs.mtconnect.org](https://docs.mtconnect.org/)). + +## Samples + +A SAMPLE observation carries a numeric value plus the SAMPLE-specific metadata that the DataItem declares. The four concrete sample subclasses map to the four DataItem `Representation` modes: + +- [`SampleValueObservation`](/api/MTConnect.Observations/SampleValueObservation) — one scalar. `CDATA = "1.5"` on the wire. +- [`SampleDataSetObservation`](/api/MTConnect.Observations/SampleDataSetObservation) — entries-of-scalars. +- [`SampleTableObservation`](/api/MTConnect.Observations/SampleTableObservation) — entries-of-entries-of-scalars. +- [`SampleTimeSeriesObservation`](/api/MTConnect.Observations/SampleTimeSeriesObservation) — a fixed-cadence vector. Carries `SampleCount` and `SampleRate` attributes. + +A typical Sample creation in code: + +```csharp +using MTConnect.Observations; + +var obs = new SampleValueObservation +{ + DeviceUuid = device.Uuid, + DataItemId = "x-pos-actual", + Timestamp = DateTime.UtcNow, + CDATA = "12.345", +}; +agent.AddObservation(device.Uuid, obs); +``` + +## Events + +An EVENT observation carries a discrete-state value. The shape mirrors Samples — `EventValueObservation`, `EventDataSetObservation`, `EventTableObservation` — but the wire envelope groups them under `` rather than ``. EVENT values are not numerically interpolated; consumers carry-forward the last known state until the next observation. + +A canonical Event: + +```csharp +var avail = new EventValueObservation +{ + DeviceUuid = device.Uuid, + DataItemId = "mill-01-avail", + Timestamp = DateTime.UtcNow, + CDATA = "AVAILABLE", +}; +agent.AddObservation(device.Uuid, avail); +``` + +## Conditions + +A CONDITION observation aggregates alarm-style state into a level: `NORMAL`, `WARNING`, `FAULT`, or `UNAVAILABLE`. Conditions deviate from Samples and Events in two ways: + +1. **Multiple actives**: a single CONDITION DataItem can hold many simultaneously-active condition observations, each keyed by `nativeCode`. Setting `NORMAL` with no `nativeCode` clears every active. +2. **Auxiliary attributes**: a Condition carries `nativeCode` (vendor's alarm code), `qualifier` (`HIGH` / `LOW`, from [`ConditionQualifier`](/api/MTConnect.Observations/ConditionQualifier)), `nativeSeverity`, and `message` (human-readable text). + +Class shape: + +```csharp +public class ConditionObservation : Observation, IConditionObservation +{ + public ConditionLevel Level { get; set; } // NORMAL, WARNING, FAULT, UNAVAILABLE + public string NativeCode { get; set; } + public ConditionQualifier Qualifier { get; set; } + public string NativeSeverity { get; set; } + public string Message { get; set; } +} +``` + +A typical Condition lifecycle in code: + +```csharp +using MTConnect.Observations; + +// Raise a fault. +agent.AddObservation(device.Uuid, new ConditionObservation +{ + DataItemId = "ctrl-system", + Timestamp = DateTime.UtcNow, + Level = ConditionLevel.FAULT, + NativeCode = "E1024", + Qualifier = ConditionQualifier.HIGH, + Message = "Spindle over-temperature", +}); + +// Clear all actives by sending NORMAL with no native code. +agent.AddObservation(device.Uuid, new ConditionObservation +{ + DataItemId = "ctrl-system", + Timestamp = DateTime.UtcNow, + Level = ConditionLevel.NORMAL, +}); +``` + +Source: MTConnect Standard `Part_2.0` Streams §10 ([docs.mtconnect.org](https://docs.mtconnect.org/)); SysML `ConditionLevelEnum` ([`mtconnect/mtconnect_sysml_model`](https://github.com/mtconnect/mtconnect_sysml_model)). + +## Reset triggers + +For accumulator-shaped DataItems (`PART_COUNT`, `ACCUMULATED_TIME`, `MATERIAL_FEED`), each observation carries an optional `ResetTriggered` field that marks the point at which the accumulator was zeroed. The values are spec-defined: `SHIFT`, `MANUAL`, `DAY`, `MAINTENANCE`, `MONTH`, `SHIFT_CHANGE`, `WEEK`, etc. Enum source: SysML `ResetTriggeredEnum`. Consumers detect a reset event by observing the field set on an incoming observation, not by inferring a value drop. + +## Sample vs Current vs Probe + +The agent exposes three retrieval endpoints with different semantics: + +- **`/probe`** — returns the Device model. No observations. +- **`/current`** — returns the most-recent observation per DataItem. +- **`/sample`** — returns every observation between `from` and `to` (or `count` after `from`), wrapping at the buffer's circular boundary if the range spans the wrap point. + +The `Sequence` field is the cursor for `/sample`. A consumer that paginates calls `/sample?from=&count=` and advances the `from` cursor with each batch. See [Wire formats](/wire-formats/) for the Streams envelope shape. + +## Where to next + +- [Assets](/concepts/assets) — non-observation entities the device tracks. +- [Relationships](/concepts/relationships) — how DataItem-to-DataItem references thread through observations. +- [`IObservation` API reference](/api/MTConnect.Observations/IObservation). +- [Wire formats: JSON v1](/wire-formats/json-v1) — Observation serialization shapes. diff --git a/docs/concepts/relationships.md b/docs/concepts/relationships.md new file mode 100644 index 000000000..0b5287d90 --- /dev/null +++ b/docs/concepts/relationships.md @@ -0,0 +1,130 @@ +# Relationships + +Beyond the strict containment tree (Device → Component → DataItem), the MTConnect Standard models cross-tree references through a set of explicit **Relationship** types. Relationships let a DataItem on one Component name another DataItem it depends on, an Asset describe its dependency on another Asset, and a Component point at a coordinate system or a sensor configuration. `MTConnect.NET` exposes the full Relationship hierarchy as concrete classes under [`MTConnect.Devices.DataItems`](/api/MTConnect.Devices.DataItems/) and [`MTConnect.Devices.Configurations`](/api/MTConnect.Devices.Configurations/), generated from the SysML model. + +## DataItem relationships + +A `DataItem` can declare relationships to other DataItems through `DataItemRelationship`: + +```csharp +public abstract class AbstractDataItemRelationship +{ + public string Id { get; set; } + public string Name { get; set; } + public string IdRef { get; set; } // the target DataItem's Id +} + +public class DataItemRelationship : AbstractDataItemRelationship +{ + public DataItemRelationshipType Type { get; set; } +} +``` + +The relationship type ([`DataItemRelationshipType`](/api/MTConnect.Devices/DataItemRelationshipType)) is one of: + +- **`LIMIT`** — the source DataItem's value is bounded by the target's value. +- **`OBSERVATION`** — the source is observationally dependent on the target. +- **`ATTACHMENT`** — the source DataItem is attached to the target (for fixture-style relationships). + +A typical usage: a `LOAD` SAMPLE DataItem declares a `LIMIT` relationship to the `LOAD_LIMIT` EVENT DataItem that holds its current upper bound. + +```xml + + + + + +``` + +Source: `Part_2.0` Streams §6 ([docs.mtconnect.org](https://docs.mtconnect.org/)); SysML `DataItemRelationship` class ([`mtconnect/mtconnect_sysml_model`](https://github.com/mtconnect/mtconnect_sysml_model)). + +## Specification relationships + +For DataItems whose semantics are governed by a published specification, `SpecificationRelationship` references a `Specification` element under a Component's `Configuration`: + +```csharp +public class SpecificationRelationship : AbstractDataItemRelationship +{ + public SpecificationRelationshipType Type { get; set; } // LIMIT +} +``` + +The `Specification` carries the spec-declared `Maximum`, `Minimum`, `Nominal`, `UpperLimit`, `LowerLimit`, `UpperWarning`, `LowerWarning` values. A `LOAD` SAMPLE DataItem points at the Specification through a `SpecificationRelationship`; the consumer renders bands and alarms from the spec rather than guessing thresholds. + +## Component relationships + +A Component can declare a `ComponentRelationship` to another Component — the spec models siblings that "belong together" but do not strictly nest, like a Path and the Controller that runs it. The relationship type ([`ComponentRelationshipType`](/api/MTConnect.Devices.Configurations/ComponentRelationshipType)) is one of `PARENT`, `CHILD`, `PEER`. Authored under the Component's `Configuration.Relationships`: + +```xml + + + + + + + +``` + +Source: `Part_3.0` Devices §7 ([docs.mtconnect.org](https://docs.mtconnect.org/)); SysML `ComponentRelationship` class. + +## Asset relationships + +An Asset can reference other Assets through `AssetRelationship` — a CuttingTool referencing its archetype, a Pallet referencing the Fixture mounted on it. The `IdRef` is the target Asset's `AssetId`, and the `Type` is spec-defined per Asset class (`CuttingToolArchetypeReference.ArchetypeIdRef` for CuttingTools, etc.). + +## CoordinateSystem references + +A Component can declare a `CoordinateSystem` element under its `Configuration` and refer to it from DataItems via `CoordinateSystemIdRef`: + +```csharp +public class DataItem : IDataItem +{ + public string CoordinateSystemIdRef { get; set; } + public DataItemCoordinateSystem CoordinateSystem { get; set; } + // ... +} +``` + +The legacy `CoordinateSystem` enum (`MACHINE`, `WORK`) was deprecated in v1.6 in favor of the `CoordinateSystem` element under `Configuration`; the library serializes the enum when targeting a version below v1.6 and the element when targeting v1.6+. The version-aware serialization is centralized in `DataItem.Process(IDataItem, Version)`. + +## Sensor configurations + +A Component can declare a `SensorConfiguration` element under its `Configuration` that describes the firmware version, calibration date, and per-channel measurement metadata of the sensors mounted on it. The channels reference DataItems through `Channel.Number` and back-reference the Component's DataItems. Source: SysML `SensorConfiguration` class. + +## Mermaid view of the cross-reference shape + +```mermaid +flowchart LR + subgraph Device + direction TB + DI1[DataItem: LOAD] + DI2[DataItem: LOAD_LIMIT] + DI3[DataItem: POSITION ACTUAL] + SPEC[Specification: LOAD bounds] + CS[CoordinateSystem: MACHINE] + end + + DI1 -- DataItemRelationship LIMIT idRef --> DI2 + DI1 -- SpecificationRelationship LIMIT idRef --> SPEC + DI3 -- CoordinateSystemIdRef --> CS + AssetA[Asset: CuttingTool TOOL-1] -- ArchetypeIdRef --> AssetB[Asset: CuttingToolArchetype TOOL-1-A] +``` + +Every Relationship resolves by `IdRef` — the textual ID of the referenced entity — not by a hard reference to an object. This is by design: agents pass models around as serialised XML / JSON, and IDs survive serialization where in-memory pointers do not. `MTConnect.NET` does not auto-resolve relationships when deserializing a model; callers resolve via [`Device.GetDataItemByKey(idRef)`](/api/MTConnect.Devices/Device#GetDataItemByKey) and friends when the relationship is needed. + +## Version gating across relationships + +Relationship types are version-gated like DataItem types: + +- `DataItemRelationship` enters at v1.5. +- `SpecificationRelationship` enters at v1.7. +- `ComponentRelationship` enters at v1.5; the `PEER` type at v1.7. +- The `Specification` element enters at v1.4. + +`DataItem.Process(IDataItem, Version)` and `Component.Process(IComponent, Version)` strip Relationships whose `MinimumVersion` exceeds the target. Source: SysML model's per-class `introducedAtVersion` field, mirrored into the generated `.g.cs` files. + +## Where to next + +- [Devices](/concepts/devices) — the containment tree Relationships layer over. +- [Components](/concepts/components) — the Components that author Configuration. +- [DataItems](/concepts/data-items) — the DataItems that emit Relationships. +- [`DataItemRelationship` API reference](/api/MTConnect.Devices/DataItemRelationship). diff --git a/docs/configure/adapter-config.md b/docs/configure/adapter-config.md new file mode 100644 index 000000000..d714a2163 --- /dev/null +++ b/docs/configure/adapter-config.md @@ -0,0 +1,184 @@ +# Configure an adapter + +An adapter ships data from a custom source (PLC, sensor, file, network feed) into one or more MTConnect agents. `MTConnect.NET` provides two adapter shapes: + +1. **The standalone adapter application** — a configurable executable that reads from a declared input and writes SHDR or MQTT to a declared output. +2. **The embeddable adapter library** — `MTConnect.NET-Applications-Adapter`, for building a custom adapter executable. + +This page documents the standalone adapter's YAML config plus the agent-side adapter modules that consume it. + +## Adapter vs agent — which side is which + +```mermaid +flowchart LR + subgraph Source + PLC[PLC / sensor / file] + end + + subgraph Adapter[Adapter executable] + READ[Input reader] + XFORM[Transform] + WRITE[SHDR / MQTT writer] + end + + subgraph Agent[MTConnect Agent] + MOD[shdr-adapter module / mqtt-adapter module] + BUF[Buffer] + HTTP[HTTP server] + end + + PLC -- vendor protocol --> READ + READ --> XFORM + XFORM --> WRITE + WRITE -- SHDR / MQTT --> MOD + MOD --> BUF + BUF --> HTTP +``` + +The **adapter** runs close to the data source, often on the same machine or LAN segment. It speaks the source's native protocol (vendor PLC API, OPC-UA, raw TCP) and translates to MTConnect-compatible SHDR or MQTT lines. The **agent** runs anywhere reachable from the adapter's output socket. + +## Standalone adapter config + +The adapter reads its configuration from `adapter.config.yaml`. The two top-level shapes are `input:` (where data comes from) and `output:` (where SHDR / MQTT lines go). + +```yaml +input: + type: tcp-csv + hostname: 192.168.1.100 + port: 9000 + fieldMap: + - field: 0 + dataItem: avail + - field: 1 + dataItem: x-pos-actual + - field: 2 + dataItem: spindle-load + +output: + type: shdr + port: 7878 + heartbeat: 1000 + +deviceKey: mill-01 +``` + +### `deviceKey` + +The adapter's device identifier. Every SHDR line emitted on the adapter's socket is associated with this `deviceKey`; the agent's `shdr-adapter` module uses the same `deviceKey` to route incoming lines to the correct Device in its model. The `deviceKey` matches the `name` attribute on the agent-side Device (or its `Id` if no Name is set). + +### `input:` + +The adapter ships built-in input shapes: + +| `type:` | Description | +|---|---| +| `tcp-csv` | TCP socket emitting CSV-per-line. `fieldMap` maps each CSV field to a DataItem. | +| `tcp-shdr` | TCP socket emitting SHDR-formatted lines from an upstream source. | +| `http-poll` | Periodic GET against an HTTP endpoint; expects an MTConnect-shaped response. | +| `file-tail` | Tail a log file; one line per observation. | +| `python` | Run a Python script for each observation; the script returns the value via Python.NET. | + +The shape of the input block depends on `type:`. The `tcp-csv` example above is the most common; `http-poll` looks like: + +```yaml +input: + type: http-poll + url: http://192.168.1.100/data + interval: 1000 +``` + +For a fully custom input, write a class implementing `IAdapterInput` and use the embeddable adapter library. + +### `output:` + +The adapter ships two output shapes: + +| `type:` | Description | +|---|---| +| `shdr` | TCP server that emits SHDR lines on the configured port. The agent's `shdr-adapter` module connects to this port. | +| `mqtt` | MQTT client that publishes to an external broker on a per-DataItem topic. | + +Example MQTT output: + +```yaml +output: + type: mqtt + server: broker.example.com + port: 1883 + topicPrefix: MTConnect/Adapter + username: adapter-01 + password: +``` + +When using MQTT output, the corresponding agent-side module is `mqtt-adapter` rather than `shdr-adapter`. + +### `heartbeat` + +For SHDR output, the interval (in milliseconds) at which the adapter sends a heartbeat (`* PING\n`) to its consumer. The agent expects a heartbeat at least every `heartbeat` interval; missed heartbeats trip the connection-loss state machine and force a reconnect. + +Default: `1000` ms (1 second). + +## Agent-side: `shdr-adapter` module + +For each running adapter, the agent's config declares a corresponding `shdr-adapter` module instance. The module connects to the adapter's SHDR output socket and routes incoming lines to the matching Device: + +```yaml +modules: +- shdr-adapter: + deviceKey: mill-01 + hostname: localhost + port: 7878 + heartbeat: 1000 + reconnectInterval: 1000 + connectionTimeout: 1000 +``` + +The full key reference is at [Configure modules: SHDR adapter](/configure/module-config#shdr-adapter). + +## Agent-side: `mqtt-adapter` module + +For MQTT-output adapters, the agent's config declares a corresponding `mqtt-adapter` module instance: + +```yaml +modules: +- mqtt-adapter: + deviceKey: mill-01 + server: broker.example.com + port: 1883 + topic: MTConnect/Adapter/mill-01 +``` + +The full key reference is at [Configure modules: MQTT adapter](/configure/module-config#mqtt-adapter). + +## SHDR line shape + +The SHDR protocol is described in MTConnect Standard `Part_5.0` ([docs.mtconnect.org](https://docs.mtconnect.org/)). A line is: + +```text +|| +``` + +with optional `|key|value` repeats for compound observations: + +```text +2025-01-01T12:34:56.789Z|avail|AVAILABLE +2025-01-01T12:34:56.789Z|x-pos-actual|12.345 +2025-01-01T12:34:56.789Z|spindle-load|45|spindle-load-cond|NORMAL|| +``` + +The `dataItemKey` resolves through the agent-side Device's `GetDataItemByKey(key)` lookup, which checks `Id`, then `Name`, then `Source.DataItemId`, then `Source.Value`. Authoring the adapter's `fieldMap` against the Device's `Name` attribute (rather than its auto-generated `Id`) is the most resilient pattern: a model edit that re-assigns IDs does not break the adapter. + +A heartbeat line is the literal `* PING\n`, to which the consumer responds with `* PONG \n` per the spec. + +## Buffering and reconnect + +The adapter buffers outbound lines while disconnected; on reconnect, the adapter does NOT replay the buffered lines. The agent-side `shdr-adapter` module emits an `UNAVAILABLE` observation for every DataItem associated with the adapter when the connection drops, and the agent re-establishes the connection through the `reconnectInterval` poll loop. + +For deployments that cannot tolerate data loss across a disconnect, route the adapter's output through MQTT with a persistent broker (set `cleanSession: false` on the MQTT client and use a durable topic queue) — the broker absorbs the in-flight messages while either end is offline. + +## Where to next + +- [Configure an agent](/configure/agent-config) — the agent side of the data flow. +- [Configure modules](/configure/module-config) — per-module configuration reference. +- [Cookbook: Write an adapter](/cookbook/write-an-adapter) — a programmatic walk-through. +- [Wire formats: SHDR](/wire-formats/shdr) — the on-the-wire shape. diff --git a/docs/configure/agent-config.md b/docs/configure/agent-config.md new file mode 100644 index 000000000..d428f6bf0 --- /dev/null +++ b/docs/configure/agent-config.md @@ -0,0 +1,199 @@ +# Configure an agent + +An agent's runtime behavior is shaped by two files: `agent.config.yaml` (the agent's YAML config) and `Devices.xml` (the static device model). This page documents every key in `agent.config.yaml`, the canonical YAML shape, the per-module configuration discriminators, and the validation pipeline that runs at agent startup. + +## File layout + +The standalone agent application reads its configuration from `agent.config.yaml` next to the executable (or, in the Docker image, from `/config/agent.config.yaml`). The file is YAML 1.2 with two top-level shapes: a `modules:` list (the agent's HTTP / MQTT / SHDR / adapter modules) and a flat block of agent-wide settings (buffer sizes, default version, durability, etc.). + +A minimal `agent.config.yaml` for a single-device HTTP agent: + +```yaml +# Path to the directory holding Devices.xml (or to a specific .xml file). +devices: devices + +# Agent-wide settings. +observationBufferSize: 150000 +assetBufferSize: 1000 +durable: false +defaultVersion: 2.5 +enableAgentDevice: true + +# Modules attached to the agent. +modules: + +- http-server: + port: 5000 + indentOutput: true + documentFormat: xml + accept: + text/xml: xml + application/json: json + responseCompression: + - gzip + - br +``` + +## Agent-wide settings + +Every key below is a top-level key in `agent.config.yaml`. + +### `devices` + +Path to the device-model source. Can be: + +- A directory — the agent loads every `*.xml` file in the directory. +- A single file path — the agent loads just that file. + +Default: `devices` (a directory in the agent's working directory). The on-disk path is resolved relative to the agent's working directory, not to the location of `agent.config.yaml`. + +### `observationBufferSize` + +The maximum number of observations the agent retains in its in-memory circular buffer. When full, the oldest observation is discarded; the next-sequence cursor wraps and consumers paginating across the wrap point see a gap. + +Default: `150000`. Suggested rule of thumb: at least ` * `. A 100 Hz adapter emitting on 10 DataItems wants `1000 * `. + +### `assetBufferSize` + +The maximum number of assets the agent retains. When full, the least-recently-updated asset is evicted. Removed-flag assets count toward the limit until they age out. + +Default: `1000`. + +### `durable` + +Whether the agent persists its buffers to disk and restores them on restart. When true, the agent writes buffer pages to `durableBufferPath` (default: a `buffer/` directory next to the executable). Restart picks up where the agent left off; the `instanceId` is preserved, so consumers do not see a sequence reset. + +Default: `false`. Set true in production for cases where a consumer must not lose data on agent restart. + +### `durableBufferPath` + +Directory path for the durable buffer. Used only when `durable: true`. Default: `buffer` (relative to the agent's working directory). + +### `defaultVersion` + +The MTConnect spec version the agent defaults to when a request omits the `?version=` query parameter. Format: `.` as a string (e.g. `"2.5"`). + +Default: the library's `MTConnectVersions.Max`. Set this explicitly in production so a consumer pinned to a specific spec version is not surprised by a library upgrade. + +### `enableAgentDevice` + +Whether to auto-register the self-describing Agent Device. The Agent Device emits its own `AVAILABILITY`, `ASSET_CHANGED`, `ASSET_REMOVED`, and `MTCONNECT_VERSION` observations, and gives consumers a single point to monitor the agent's health. + +Default: `true`. Set false when a consumer is strict about device counts (some legacy integrations break if the device list contains entries they did not author). + +### `processors` + +A list of input processors that run on every observation before it enters the buffer. The shipped processor types include the [Python processor](/modules/agent-processor-python) (`python:`), which runs a directory of [IronPython](https://ironpython.net/) scripts as per-observation transforms. + +```yaml +processors: +- python: + directory: processors +``` + +The `directory` key points at the directory holding the Python scripts. Each script is named after the DataItem it transforms. + +## Modules block + +The `modules:` block is a YAML sequence of single-key maps. The key names the module type; the value is the module-specific configuration. + +```yaml +modules: +- http-server: # one module instance + port: 5000 +- mqtt-relay: # another module instance + server: broker.example.com +- shdr-adapter: # a third + deviceKey: Okuma + port: 7878 +``` + +The shipped module types: + +- `http-server` — the HTTP endpoint surface. See [Configure modules: HTTP server](/configure/module-config#http-server). +- `mqtt-broker` — embedded MQTT broker emitting topics for each Device. See [Configure modules: MQTT broker](/configure/module-config#mqtt-broker). +- `mqtt-relay` — outbound publisher to an external MQTT broker. See [Configure modules: MQTT relay](/configure/module-config#mqtt-relay). +- `mqtt-adapter` — inbound consumer from an external MQTT broker. See [Configure modules: MQTT adapter](/configure/module-config#mqtt-adapter). +- `shdr-adapter` — inbound SHDR adapter (the agent connects to a TCP socket that emits SHDR). See [Configure modules: SHDR adapter](/configure/module-config#shdr-adapter). +- `http-adapter` — inbound HTTP adapter (the agent polls an HTTP endpoint that emits MTConnect-shaped responses). See [Configure modules: HTTP adapter](/configure/module-config#http-adapter). + +Multiple instances of the same module type are allowed and common — two `http-server` modules on different ports (one TLS, one plain), or two `shdr-adapter` modules for two devices. + +## Devices.xml + +The device model is authored in XML against the MTConnect Devices schema ([schemas.mtconnect.org](https://schemas.mtconnect.org/)). A single `Devices.xml` declares one or more Devices, each with its Component / Composition / DataItem tree. + +```xml + + + + + + + + + + + + + + + + + +``` + +The agent validates `Devices.xml` against the XSD declared by the document's namespace at startup. If validation fails, the agent logs the failure and exits with a non-zero code; see [Troubleshooting: XSD validation failures](/troubleshooting/xsd-validation-failures). + +The XML namespace selects the target MTConnect version: `urn:mtconnect.org:MTConnectDevices:2.5` validates against `MTConnectDevices_2.5.xsd`. Authoring against the lowest version your consumer base requires is the safest default; the agent serializes the model upward (and prunes properties added after the target) on every response. + +## Startup pipeline + +```mermaid +sequenceDiagram + autonumber + participant Exe as Agent executable + participant Cfg as agent.config.yaml + participant Mod as Modules + participant XML as Devices.xml + participant Buf as Buffers + + Exe->>Cfg: Parse YAML + Exe->>XML: Load Devices.xml (each file in devices/) + Exe->>XML: Validate against MTConnectDevices_.xsd + XML-->>Exe: IDevice tree (or exit on validation failure) + Exe->>Buf: Initialize observation + asset buffers (durable load if enabled) + Exe->>Mod: Instantiate each module, pass module-specific config + Mod-->>Exe: Module Start() returns + Exe->>Exe: Run forever +``` + +A successful startup logs: + +```text +[12:34:56 INF] Devices: 1 loaded +[12:34:56 INF] Modules: 3 started +[12:34:56 INF] Listening on http://0.0.0.0:5000 +[12:34:56 INF] Agent UUID: +[12:34:56 INF] Instance ID: 1737504000 +``` + +## Validation tooling + +To validate `agent.config.yaml` without starting the agent, the standalone agent ships a `--validate` flag that parses the YAML, applies it to the configuration object, and exits with a status code: + +```sh +MTConnect.NET-Agent --validate --config /path/to/agent.config.yaml +``` + +For `Devices.xml`, use the same `--validate` flag — the validation pipeline runs the XSD validator on every file in `devices/` and reports each file's status. + +## Where to next + +- [Configure an adapter](/configure/adapter-config) — the adapter side of the data flow. +- [Configure modules](/configure/module-config) — every module's full config-key reference. +- [Cookbook: Write an agent](/cookbook/write-an-agent) — a programmatic alternative to the YAML config. +- [Troubleshooting: Schema version mismatches](/troubleshooting/schema-version-mismatches) — when consumer and agent advertise different versions. diff --git a/docs/configure/index.md b/docs/configure/index.md new file mode 100644 index 000000000..fdb7802e1 --- /dev/null +++ b/docs/configure/index.md @@ -0,0 +1,72 @@ +# Configure & Use + +End-to-end guides for installing, configuring, running, and connecting consumers to `MTConnect.NET`. This is the operator-facing complement to the type-level [API reference](/api/) — read this section to stand up a real agent against real equipment. + +## What this section covers + +- **[Install](./install)** — NuGet package install for each shipped library, plus the prebuilt agent and prebuilt adapter, with per-target-framework notes. +- **[Configure an agent](./agent)** — `agent.config.yaml` (every key, every default, every permissible value), `Devices.xml` (schema, sample, common pitfalls, XSD validation), per-module configuration, logging. +- **[Configure an adapter](./adapter)** — SHDR / HTTP adapter config, ports, data-source bring-up, queue-vs-interval semantics. +- **[Run](./run)** — local development with `dotnet run`, Docker with `trakhound/mtconnect.net-agent`, Windows-service and systemd-unit deployment. +- **[Connect a consumer](./consumer)** — `curl` + browser examples for `/probe`, `/current`, `/sample`, `/asset`; MQTT subscriber examples for the relay topic tree; JSON v2 sample parser in .NET and Python. +- **[Operate](./operate)** — observability (logs, metrics, traces), common error modes and recovery, backup and restore of the agent's storage layer. + +## Topology + +```mermaid +flowchart LR + subgraph data[Data sources] + PLC[PLC / CNC] + SENSOR[Sensors] + end + + subgraph adapter[Adapter] + SHDRADAPT[SHDR adapter] + MQTTADAPT[MQTT adapter] + end + + subgraph agent[Agent] + AGENT[MTConnectAgent] + HTTPMOD[HTTP server module] + MQTTBROKER[MQTT broker module] + MQTTRELAY[MQTT relay module] + end + + subgraph consumers[Consumers] + DASHBOARD[Dashboard] + HISTORIAN[Historian] + BRIDGE[Cloud bridge] + end + + PLC --> SHDRADAPT + SENSOR --> MQTTADAPT + SHDRADAPT --> AGENT + MQTTADAPT --> AGENT + AGENT --> HTTPMOD + AGENT --> MQTTBROKER + AGENT --> MQTTRELAY + HTTPMOD --> DASHBOARD + MQTTBROKER --> HISTORIAN + MQTTRELAY --> BRIDGE +``` + +The agent's modular architecture means the same agent process can speak any combination of HTTP, MQTT broker (embedded), MQTT relay (to an external broker), SHDR adapter, MQTT adapter, and HTTP adapter — all configured through `agent.config.yaml`. + +## Integrations + +Step-by-step guides for the most-requested deployment shapes: + +- **[InfluxDB](./integrations/influxdb)** — pipe MTConnect observations into InfluxDB for time-series storage and Grafana dashboards. +- **[MQTT — Protocol overview](./integrations/mqtt-protocol)** — the MTConnect-over-MQTT topic tree, payload formats, and broker-side considerations. +- **[MQTT — AWS Greengrass (Moquette)](./integrations/mqtt-aws-greengrass-moquette)** — running the agent against the Moquette broker on Greengrass. +- **[MQTT — AWS Greengrass (Mqtt-Bridge)](./integrations/mqtt-aws-greengrass-mqtt-bridge)** — bridging local-broker traffic out through Greengrass. +- **[MQTT — AWS IoT](./integrations/mqtt-aws-iot)** — publishing directly to AWS IoT Core. +- **[MQTT — HiveMQ](./integrations/mqtt-hivemq)** — running against HiveMQ as the external broker. +- **[OpenSSL setup](./integrations/openssl)** — generating and configuring TLS certificates for HTTPS and MQTTS endpoints. + +## See also + +- [Getting started](/getting-started) — the three-step quickstart, if you haven't installed the agent yet. +- [Wire formats](/wire-formats/) — what the agent emits on the wire, by codec. +- [Cookbook](/cookbook/) — recipes for the common deployment patterns. +- [Troubleshooting](/troubleshooting/) — what to do when something goes wrong. diff --git a/docs/configure/install.md b/docs/configure/install.md new file mode 100644 index 000000000..79f551c6c --- /dev/null +++ b/docs/configure/install.md @@ -0,0 +1,127 @@ +# Install + +`MTConnect.NET` ships in three forms: a standalone agent application, a standalone adapter application, and a set of embeddable NuGet libraries. Pick the shape that matches what you are building. + +## Decision matrix + +| You want to … | Install | +|---|---| +| Run a preconfigured agent against `Devices.xml` and adapters | The standalone agent application | +| Ship data from a custom data source (PLC, sensor, file) over SHDR or MQTT | The standalone adapter application | +| Embed agent / adapter / client functionality inside your own .NET application | The NuGet libraries | +| Build a tool that parses MTConnect wire-format payloads | `MTConnect.NET-XML`, `MTConnect.NET-JSON`, or `MTConnect.NET-JSON-cppagent` NuGet packages | + +## The standalone agent application + +The agent ships as a self-contained executable in three deployment forms: + +- **Installer**: Windows MSI, macOS pkg, Linux deb / rpm. Linked from the [project releases page](https://github.com/TrakHound/MTConnect.NET/releases). +- **Docker image**: `trakhound/mtconnect.net-agent:` on Docker Hub. The image entry-point is `MTConnect.NET-Agent` with `agent.config.yaml` resolved from `/config/agent.config.yaml`. +- **Source build**: `dotnet build agent/MTConnect.NET-Agent/MTConnect.NET-Agent.csproj -c Release` from a clone of the repo. + +Quick start with Docker: + +```sh +docker run --rm -d --name mtc-agent \ + -p 5000:5000 \ + -v "$PWD/agent.config.yaml:/config/agent.config.yaml:ro" \ + -v "$PWD/Devices.xml:/config/devices/Devices.xml:ro" \ + trakhound/mtconnect.net-agent:latest + +curl -s http://localhost:5000/probe | head -50 +``` + +The default config exposes the HTTP server on port `5000`. The MTConnect endpoints (`/probe`, `/current`, `/sample`, `/asset`) are served under that port. + +## The standalone adapter application + +The adapter ships through the same release channel. The single executable reads from a custom data source (a CSV file tail, a TCP socket, a PLC's ladder API) and writes SHDR lines or MQTT messages to a configured downstream: + +```sh +MTConnect.NET-Adapter --config adapter.config.yaml +``` + +The adapter's config file declares the input source and the output protocol. The `MTConnect.NET-Applications-Adapter` NuGet package hosts the same logic for embedding inside a custom adapter executable. + +## The embeddable NuGet libraries + +Every published library is on [nuget.org](https://www.nuget.org/) under the `MTConnect.NET-*` prefix. The two-layer install pattern: + +- Start with the **meta package** `MTConnect.NET`, which transitively pulls every other shipped library. +- Or pin the **specific libraries** you need. + +### Meta package + +```sh +dotnet add package MTConnect.NET +``` + +This installs every library and is the right choice when you are building an embedded agent or adapter end-to-end. + +### Per-library install + +The library set: + +| Library | Purpose | +|---|---| +| `MTConnect.NET-Common` | Devices / Components / DataItems / Observations / Assets type system. | +| `MTConnect.NET-HTTP` | HTTP-server module: `/probe`, `/current`, `/sample`, `/asset`. | +| `MTConnect.NET-SHDR` | SHDR adapter protocol — both consumer and producer. | +| `MTConnect.NET-MQTT` | MQTT broker / relay / adapter modules. | +| `MTConnect.NET-XML` | XML envelope codec — every Streams / Devices / Assets / Error envelope. | +| `MTConnect.NET-JSON` | JSON v1 envelope codec. | +| `MTConnect.NET-JSON-cppagent` | JSON-CPPAGENT v2 envelope codec (cppagent-parity). | +| `MTConnect.NET-TLS` | TLS configuration for the HTTP / MQTT modules. | +| `MTConnect.NET-Services` | Windows service / systemd-unit hosting. | +| `MTConnect.NET-DeviceFinder` | Network discovery for MTConnect agents (mDNS). | +| `MTConnect.NET-SysML` | SysML-XMI-driven source generator (build-time only). | +| `MTConnect.NET-Applications-Agents` | Agent host package — used by the standalone agent application. | +| `MTConnect.NET-Applications-Adapter` | Adapter host package — used by the standalone adapter application. | + +Install one or more: + +```sh +dotnet add package MTConnect.NET-Common +dotnet add package MTConnect.NET-HTTP +dotnet add package MTConnect.NET-XML +``` + +## Target frameworks + +The libraries multi-target a wide matrix: .NET 9.0, .NET 8.0, .NET 7.0, .NET 6.0, .NET 5.0, .NET Core 3.1, .NET Standard 2.0, and .NET Framework 4.6.1 through 4.8. The matrix is declared in each `.csproj`'s `` property. + +The .NET Standard 2.0 target is the lowest common denominator and is the target of choice for libraries embedding `MTConnect.NET` from a class library. The .NET Framework 4.6.1 target is the lowest .NET Framework version supported; consumers on .NET Framework 4.8 receive the .NET Framework 4.8 target's binary, which has access to features the 4.6.1 binary cannot use. + +The standalone agent ships as a .NET 8.0 single-file executable by default; the Docker image is built from the same. + +## Version pinning + +Pin to a specific version in production: + +```xml + +``` + +The library follows semantic versioning across major versions but with the caveat that the public-surface contracts are not yet formally semver-stable — minor version bumps occasionally add a property or a class. Pin to the major.minor pair (`6.10.*`) for the safest auto-update window. + +## Verify the install + +A two-line smoke test: + +```csharp +using MTConnect; +using MTConnect.Devices; + +var d = new Device { Id = "smoke-test", Name = "Smoke" }; +Console.WriteLine($"Created Device {d.Uuid} with hash {d.GenerateHash()}"); +``` + +A successful run prints the Device's UUID (a random GUID, since none was specified) and an SHA-1 hash of the empty model. If you see "package not found" instead, double-check that `MTConnect.NET-Common` is in your project's `` list. + +## Where to next + +- [Configure an agent](/configure/agent-config) — the agent's YAML configuration. +- [Configure an adapter](/configure/adapter-config) — the adapter's YAML configuration. +- [Configure modules](/configure/module-config) — per-module configuration keys. +- [Cookbook: Write an agent](/cookbook/write-an-agent) — your first agent in code. +- [Cookbook: Write an adapter](/cookbook/write-an-adapter) — your first adapter. diff --git a/docs/InfluxDB.md b/docs/configure/integrations/influxdb.md similarity index 100% rename from docs/InfluxDB.md rename to docs/configure/integrations/influxdb.md diff --git a/docs/MQTT-AWS-Greengrass-Moquette.md b/docs/configure/integrations/mqtt-aws-greengrass-moquette.md similarity index 92% rename from docs/MQTT-AWS-Greengrass-Moquette.md rename to docs/configure/integrations/mqtt-aws-greengrass-moquette.md index cb165b2f0..261b8c637 100644 --- a/docs/MQTT-AWS-Greengrass-Moquette.md +++ b/docs/configure/integrations/mqtt-aws-greengrass-moquette.md @@ -42,7 +42,7 @@ modules: ## Screenshots ### AWS Thing -![Screenshot](../img/mqtt-aws-thing-certificates.png) +![Screenshot](/img/mqtt-aws-thing-certificates.png) ### AWS Core Device -![Screenshot](../img/mqtt-aws-greengrass-moquette-01.png) +![Screenshot](/img/mqtt-aws-greengrass-moquette-01.png) diff --git a/docs/MQTT-AWS-Greengrass-Mqtt-Bridge.md b/docs/configure/integrations/mqtt-aws-greengrass-mqtt-bridge.md similarity index 100% rename from docs/MQTT-AWS-Greengrass-Mqtt-Bridge.md rename to docs/configure/integrations/mqtt-aws-greengrass-mqtt-bridge.md diff --git a/docs/MQTT-AWS-IoT.md b/docs/configure/integrations/mqtt-aws-iot.md similarity index 100% rename from docs/MQTT-AWS-IoT.md rename to docs/configure/integrations/mqtt-aws-iot.md diff --git a/docs/MQTT-HiveMQ.md b/docs/configure/integrations/mqtt-hivemq.md similarity index 100% rename from docs/MQTT-HiveMQ.md rename to docs/configure/integrations/mqtt-hivemq.md diff --git a/docs/MQTT-Protocol.md b/docs/configure/integrations/mqtt-protocol.md similarity index 98% rename from docs/MQTT-Protocol.md rename to docs/configure/integrations/mqtt-protocol.md index 6e9eb3eca..8f371290c 100644 --- a/docs/MQTT-Protocol.md +++ b/docs/configure/integrations/mqtt-protocol.md @@ -5,11 +5,11 @@ This is a protocol for accessing MTConnect data using MQTT that mimics the funct The main difference between the HTTP and MQTT protocols is that the MQTT protocol deals with the individual MTConnect entities directly (ex. Device, Observation, Asset). #### All Devices -![All_Devices](../img/mtconnect-mqtt-protocol-all-01.png) +![All_Devices](/img/mtconnect-mqtt-protocol-all-01.png) #### By Device -![All_Devices](../img/mtconnect-mqtt-protocol-by-device-01.png) +![All_Devices](/img/mtconnect-mqtt-protocol-by-device-01.png) ### Multiple Configurable Observation Intervals diff --git a/docs/OpenSSL.md b/docs/configure/integrations/openssl.md similarity index 100% rename from docs/OpenSSL.md rename to docs/configure/integrations/openssl.md diff --git a/docs/configure/module-config.md b/docs/configure/module-config.md new file mode 100644 index 000000000..c91a67b3e --- /dev/null +++ b/docs/configure/module-config.md @@ -0,0 +1,232 @@ +# Configure modules + +Modules are the agent's pluggable extension points. Each module attaches a capability — HTTP serving, MQTT publishing, SHDR ingestion — and a single agent typically runs several modules at once. This page documents every shipped module's configuration keys. + +The module set: + +- [HTTP server](#http-server) — `/probe`, `/current`, `/sample`, `/asset` endpoints. +- [MQTT broker](#mqtt-broker) — embedded MQTT broker. +- [MQTT relay](#mqtt-relay) — outbound publisher to an external MQTT broker. +- [MQTT adapter](#mqtt-adapter) — inbound consumer from an external MQTT broker. +- [SHDR adapter](#shdr-adapter) — inbound TCP-SHDR adapter. +- [HTTP adapter](#http-adapter) — inbound HTTP-poll adapter. + +Every module is declared in `agent.config.yaml` under `modules:` as a single-key map. The key is the module's name; the value is the module's config object. + +## HTTP server + +Hosts the MTConnect endpoints: `/probe`, `/current`, `/sample`, `/asset`, plus optional file-serving for stylesheets and schemas. Module key: `http-server`. Implementation: `MTConnect.NET-AgentModule-HttpServer`. + +### Keys + +```yaml +- http-server: + hostname: 0.0.0.0 # interface to bind. Default: all interfaces. + port: 5000 # listen port. Default: 5000. + allowPut: false # whether /put is allowed for ingest. Default: false. + indentOutput: true # pretty-print responses. Default: false. + documentFormat: xml # default response format. xml | json | json-cppAgent + accept: # MIME-to-format dispatch. + text/xml: xml + application/json: json + application/mtconnect+json: json-cppAgent + responseCompression: # which compression encodings to advertise. + - gzip + - br + files: # static-file mounts under /styles, /schemas, etc. + - path: schemas + location: schemas + - path: styles + location: styles + tls: # optional TLS settings. + pem: + certificateAuthority: /path/to/rootCA.crt + certificatePath: /path/to/server.crt + privateKeyPath: /path/to/server.key + privateKeyPassword: +``` + +Multiple `http-server` instances are supported and common — one on port `5000` plain, another on port `5001` with TLS, and a third on `5002` with `allowPut: true` for an internal ingest endpoint. + +### `tls` + +The `tls:` block configures TLS termination. Two shapes are supported: + +- `pem:` — PEM-encoded certificate chain and private key. +- `pfx:` — PKCS#12 bundle. + +When TLS is enabled, the HTTP server accepts only HTTPS connections. The `tlsConfiguration` class is shared with the MQTT modules — see [`MTConnect.Tls.TlsConfiguration`](/api/MTConnect.Tls/TlsConfiguration). + +## MQTT broker + +Hosts an embedded MQTT broker that publishes one topic per Device / DataItem, formatted as JSON-CPPAGENT-MQTT. Consumers connect with any MQTT client. Module key: `mqtt-broker`. Implementation: `MTConnect.NET-AgentModule-MqttBroker`. + +```yaml +- mqtt-broker: + port: 1883 + currentInterval: 10000 + sampleInterval: 500 + documentFormat: JSON-CPPAGENT + topicPrefix: MTConnect/Document + topicStructure: Document # Document | Entity + tls: + pem: + certificateAuthority: /path/to/rootCA.crt + certificatePath: /path/to/server.crt + privateKeyPath: /path/to/server.key + privateKeyPassword: +``` + +### Topic structures + +- **`Document`** — one topic per response document. Topics are `/Probe/`, `/Current/`, `/Sample/`, `/Asset//`. The payload is the full envelope. +- **`Entity`** — one topic per Observation / Asset / Device. Topics are `/Devices/`, `/Observations//`, `/Assets//`. The payload is a single entity. + +The `Document` structure is the cppagent-MQTT parity shape; the `Entity` structure is the library's per-observation alternative for consumers that prefer one-topic-per-observation. + +### Intervals + +- **`currentInterval`** — milliseconds between successive `Current` publishes. Default: `10000` (10 s). +- **`sampleInterval`** — milliseconds between successive `Sample` publishes. Default: `500`. + +## MQTT relay + +Publishes outbound MQTT messages to an external broker. The agent acts as a client. Module key: `mqtt-relay`. Implementation: `MTConnect.NET-AgentModule-MqttRelay`. The configuration object is [`MqttRelayModuleConfiguration`](/api/MTConnect.Configurations/MqttRelayModuleConfiguration). + +```yaml +- mqtt-relay: + server: broker.example.com # MQTT broker hostname. + port: 1883 # broker port. + timeout: 5000 # connect / I/O timeout (ms). + reconnectInterval: 10000 # delay between reconnect attempts (ms). + + username: agent-01 # optional broker auth. + password: + clientId: agent-01 # MQTT client id. + cleanSession: true # MQTT clean-session flag. + qos: 1 # 0 | 1 | 2. + + useTls: false # whether to use TLS. + tls: + pem: + certificateAuthority: /path/to/rootCA.crt + certificatePath: /path/to/agent.crt + privateKeyPath: /path/to/agent.key + privateKeyPassword: + + topicPrefix: MTConnect # topic prefix. + topicStructure: Document # Document | Entity (see MQTT broker). + documentFormat: JSON-CPPAGENT-MQTT + indentOutput: false + + currentInterval: 5000 # millis between Current publishes. + sampleInterval: 500 # millis between Sample publishes. + durableRelay: true # buffer + replay on reconnect. +``` + +### `durableRelay` + +When true, the relay buffers outbound messages while disconnected and replays them on reconnect, preserving ordering. Set false to drop in-flight messages and resume only the live stream. + +### Default values + +The shipped defaults match what the constructor sets: + +| Key | Default | +|---|---| +| `server` | `localhost` | +| `port` | `1883` | +| `timeout` | `5000` | +| `reconnectInterval` | `10000` | +| `topicPrefix` | `MTConnect` | +| `topicStructure` | `Document` | +| `documentFormat` | `json-cppAgent` | +| `currentInterval` | `5000` | +| `sampleInterval` | `500` | +| `durableRelay` | `false` | + +## MQTT adapter + +Subscribes to an external MQTT broker and ingests Observations from incoming messages. Module key: `mqtt-adapter`. Implementation: `MTConnect.NET-AgentModule-MqttAdapter`. + +```yaml +- mqtt-adapter: + deviceKey: mill-01 # the Device this adapter feeds. + server: broker.example.com + port: 1883 + topic: MTConnect/Adapter/mill-01 # subscribe topic (supports + and # wildcards). + username: agent-01 + password: + useTls: false + tls: { ... } # same TlsConfiguration shape as above. +``` + +The adapter expects each MQTT message to carry a JSON-CPPAGENT or JSON-v1 Observation payload (or an SHDR-formatted text line). The `documentFormat` field auto-detects when omitted. + +## SHDR adapter + +Connects to an SHDR-output adapter over TCP and ingests SHDR lines. Module key: `shdr-adapter`. Implementation: `MTConnect.NET-AgentModule-ShdrAdapter`. + +```yaml +- shdr-adapter: + deviceKey: mill-01 # the Device this adapter feeds. + hostname: localhost # remote SHDR adapter host. + port: 7878 # remote SHDR adapter port. + heartbeat: 1000 # heartbeat interval (ms). + reconnectInterval: 1000 # delay between reconnect attempts (ms). + connectionTimeout: 1000 # connection timeout (ms). +``` + +Multiple instances are typical when more than one upstream adapter feeds the agent — one per Device, each on its own port. + +## HTTP adapter + +Polls an HTTP endpoint that returns MTConnect-shaped responses. Module key: `http-adapter`. Implementation: `MTConnect.NET-AgentModule-HttpAdapter`. + +```yaml +- http-adapter: + deviceKey: mill-01 + url: http://upstream-agent.example.com:5000/sample + interval: 1000 # poll interval (ms). + documentFormat: xml # expected response format. +``` + +The HTTP adapter is most often used to chain agents — a regional aggregator agent polling per-cell agents — but works against any HTTP endpoint that emits the right envelope. + +## Configuration objects + +Each module's YAML keys deserialize into a configuration class: + +| Module | Configuration class | +|---|---| +| `http-server` | [`MTConnect.Configurations.HttpServerModuleConfiguration`](/api/MTConnect.Configurations/HttpServerModuleConfiguration) | +| `mqtt-broker` | [`MTConnect.Configurations.MqttBrokerModuleConfiguration`](/api/MTConnect.Configurations/MqttBrokerModuleConfiguration) | +| `mqtt-relay` | [`MTConnect.Configurations.MqttRelayModuleConfiguration`](/api/MTConnect.Configurations/MqttRelayModuleConfiguration) | +| `mqtt-adapter` | [`MTConnect.Configurations.MqttAdapterModuleConfiguration`](/api/MTConnect.Configurations/MqttAdapterModuleConfiguration) | +| `shdr-adapter` | [`MTConnect.Configurations.ShdrAdapterModuleConfiguration`](/api/MTConnect.Configurations/ShdrAdapterModuleConfiguration) | +| `http-adapter` | [`MTConnect.Configurations.HttpAdapterModuleConfiguration`](/api/MTConnect.Configurations/HttpAdapterModuleConfiguration) | + +Programmatic configuration uses the class directly: + +```csharp +using MTConnect.Configurations; + +var relay = new MqttRelayModuleConfiguration +{ + Server = "broker.example.com", + Port = 8883, + UseTls = true, + DocumentFormat = "JSON-CPPAGENT-MQTT", + TopicPrefix = "MTConnect/Document", + CurrentInterval = 5000, + SampleInterval = 500, + DurableRelay = true, +}; +``` + +## Where to next + +- [Configure an agent](/configure/agent-config) — the agent-wide settings the modules live under. +- [Cookbook: Configure MQTT relay](/cookbook/configure-mqtt-relay) — a full MQTT-relay walk-through. +- [Cookbook: Write a JSON-MQTT consumer](/cookbook/write-a-json-mqtt-consumer) — the consumer side. +- [Troubleshooting: MQTT TLS handshake](/troubleshooting/mqtt-tls-handshake) — when TLS connections fail. diff --git a/docs/cookbook/configure-mqtt-relay.md b/docs/cookbook/configure-mqtt-relay.md new file mode 100644 index 000000000..9ba549b68 --- /dev/null +++ b/docs/cookbook/configure-mqtt-relay.md @@ -0,0 +1,197 @@ +# Configure the MQTT relay + +This recipe configures the `mqtt-relay` module — the agent's outbound publisher that pushes observations and assets to an external MQTT broker. By the end you have: + +- The agent publishing to a broker every 500 ms (Samples) and 5 s (Current). +- A subscriber receiving the published payloads in JSON-CPPAGENT-MQTT format. +- TLS enabled on the broker connection. +- A durable-relay configuration that buffers and replays on reconnect. + +## 1. The minimal config + +In `agent.config.yaml`: + +```yaml +modules: +- mqtt-relay: + server: broker.example.com + port: 1883 + topicPrefix: MTConnect/Document + topicStructure: Document + documentFormat: JSON-CPPAGENT-MQTT + currentInterval: 5000 + sampleInterval: 500 +``` + +That is the smallest config that works. The relay publishes to four topics per Device: + +- `MTConnect/Document/Probe/` — full `MTConnectDevices` envelope, on model change. +- `MTConnect/Document/Current/` — full `MTConnectStreams` `Current` envelope, every `currentInterval` ms. +- `MTConnect/Document/Sample/` — full `MTConnectStreams` `Sample` envelope (delta since last publish), every `sampleInterval` ms. +- `MTConnect/Document/Asset//` — full `MTConnectAssets` envelope, on asset change. + +## 2. The topology + +```mermaid +flowchart LR + Adapter[SHDR adapter] --> Agent + Agent[MTConnect Agent] -->|publish JSON-CPPAGENT-MQTT| Broker + Broker[MQTT broker] -->|subscribe| Consumer1[Dashboard] + Broker -->|subscribe| Consumer2[Historian] + Broker -->|subscribe| Consumer3[Bridge] +``` + +The relay decouples the agent from its consumers. Consumers come and go; the broker absorbs the publish-subscribe semantics. + +## 3. Document structure vs Entity structure + +Two `topicStructure:` values: + +- **`Document`** — full envelope per topic. Consumers parse `MTConnectStreams` / `MTConnectDevices` / `MTConnectAssets` envelopes. +- **`Entity`** — one entity per topic. Topics are `/Observations//`, `/Devices/`, `/Assets//`. The payload is a single entity. + +Document is the cppagent-MQTT parity shape; Entity is the library's per-observation shape that some downstream consumers (Kafka bridges, time-series databases) find easier to ingest. + +Switch to Entity by setting `topicStructure: Entity` and (optionally) `documentFormat: JSON` to use the library's JSON v1 codec instead of JSON-CPPAGENT. + +## 4. TLS-enabled relay + +For broker-side TLS, set `useTls: true` and configure the `tls:` block: + +```yaml +modules: +- mqtt-relay: + server: broker.example.com + port: 8883 + useTls: true + tls: + pem: + certificateAuthority: /etc/mtconnect/ca.crt + certificatePath: /etc/mtconnect/agent.crt + privateKeyPath: /etc/mtconnect/agent.key + privateKeyPassword: + topicPrefix: MTConnect/Document + topicStructure: Document + documentFormat: JSON-CPPAGENT-MQTT + currentInterval: 5000 + sampleInterval: 500 +``` + +The `pem:` block declares a PEM-encoded certificate chain. Two alternates: + +- `pfx:` — a PKCS#12 bundle path + password (Windows-friendly). +- Omit both — the agent picks up the platform certificate store's roots; useful for brokers using a public CA-signed certificate. + +See [Troubleshooting: MQTT TLS handshake](/troubleshooting/mqtt-tls-handshake) when the handshake fails. + +## 5. Authenticated relay + +Brokers commonly require username/password authentication: + +```yaml +modules: +- mqtt-relay: + server: broker.example.com + port: 1883 + username: agent-01 + password: + clientId: agent-01-relay + cleanSession: false # preserve session across reconnects. + qos: 1 # at-least-once delivery. + topicPrefix: MTConnect/Document + topicStructure: Document + documentFormat: JSON-CPPAGENT-MQTT +``` + +Production deployments typically: + +- Use a per-agent `clientId` so the broker can distinguish multiple agents. +- Set `cleanSession: false` so the broker preserves the agent's subscription state across reconnects. +- Use `qos: 1` (at-least-once) — `qos: 0` drops on reconnect; `qos: 2` (exactly-once) adds a four-way handshake the agent rarely needs. + +## 6. Durable relay + +The `durableRelay:` flag buffers outbound messages while the broker is unreachable and replays them on reconnect: + +```yaml +modules: +- mqtt-relay: + server: broker.example.com + port: 1883 + durableRelay: true + currentInterval: 5000 + sampleInterval: 500 +``` + +When `durableRelay: true`, every Observation that enters the agent's buffer also enters a per-relay outbound queue. On reconnect, the relay drains the queue in sequence order before resuming live publishes. This is the right setting for cases where a consumer must not miss data; the trade-off is bounded memory growth during long disconnects. + +## 7. The subscriber side + +A `mosquitto_sub` subscribing to the relay: + +```sh +mosquitto_sub -h broker.example.com -p 1883 -t 'MTConnect/Document/+/+' -v +``` + +The `-t` glob matches any depth-2 sub-topic under `MTConnect/Document/`. Sample output for one published Current envelope: + +```text +MTConnect/Document/Current/mill-01 {"MTConnectStreams":{"Header":{...},"Streams":{...}}} +``` + +A dotnet subscriber using MQTTnet: + +```csharp +using MQTTnet; +using MQTTnet.Client; +using System.Text; + +var factory = new MqttFactory(); +var client = factory.CreateMqttClient(); + +await client.ConnectAsync(new MqttClientOptionsBuilder() + .WithTcpServer("broker.example.com", 1883) + .Build()); + +await client.SubscribeAsync( + new MqttTopicFilterBuilder().WithTopic("MTConnect/Document/Current/+").Build()); + +client.ApplicationMessageReceivedAsync += async e => +{ + var json = Encoding.UTF8.GetString(e.ApplicationMessage.PayloadSegment); + Console.WriteLine($"{e.ApplicationMessage.Topic} : {json[..Math.Min(json.Length, 80)]}..."); + await Task.CompletedTask; +}; + +await Task.Delay(Timeout.Infinite); +``` + +The payload parses as a standard `MTConnectStreams` JSON envelope; pass it to your in-process parser of choice. See [Cookbook: Write a JSON-MQTT consumer](/cookbook/write-a-json-mqtt-consumer) for a complete consumer. + +## 8. Tuning the intervals + +`currentInterval` and `sampleInterval` are the two knobs that govern bandwidth: + +| Knob | Default | Effect | +|---|---|---| +| `currentInterval` | `5000` (5 s) | Frequency of full Current envelopes. | +| `sampleInterval` | `500` (500 ms) | Frequency of delta Sample envelopes. | + +A high-frequency CNC monitoring deployment runs `sampleInterval: 100` for sub-second tool-position updates. A low-bandwidth deployment over cellular runs `sampleInterval: 5000` and `currentInterval: 60000` to minimize transmits. The Current envelope is large (the full per-DataItem snapshot); the Sample envelope is small (only observations since the last publish). + +## 9. Availability topic + +The agent publishes a retained `Availability` message on connect / disconnect, so subscribers know whether the relay is live: + +- Topic: `/Probe/Availability` +- Payload on connect: `AVAILABLE` +- Payload on disconnect (LWT): `UNAVAILABLE` + +The retained-message + LWT pattern lets a subscriber that connects after the agent went offline still see the `UNAVAILABLE` state instead of waiting for the next publish. + +## Where to next + +- [Cookbook: Write a JSON-MQTT consumer](/cookbook/write-a-json-mqtt-consumer) — the consumer side, with parsing code. +- [Configure modules: MQTT relay](/configure/module-config#mqtt-relay) — the full key reference. +- [Wire formats: JSON-CPPAGENT-MQTT](/wire-formats/json-cppagent-mqtt) — the on-the-wire payload shape. +- [Troubleshooting: MQTT TLS handshake](/troubleshooting/mqtt-tls-handshake) — TLS connection diagnostics. diff --git a/docs/cookbook/index.md b/docs/cookbook/index.md new file mode 100644 index 000000000..bc857f347 --- /dev/null +++ b/docs/cookbook/index.md @@ -0,0 +1,27 @@ +# Cookbook + +Recipes for the deployment patterns that come up most often. Each recipe is task-driven — pick the goal, follow the steps, end with a working configuration. + +## Available recipes + +- **Write your first agent** — install the NuGet package, scaffold a `Program.cs` with `MTConnectAgentApplication`, point a consumer at `/probe` and `/current`. See [Getting started](/getting-started) for the full walkthrough. +- **Write your first adapter** — install `MTConnect.NET-Applications-Adapter`, pick the right `ShdrAdapter` variant for your data-flow pattern (`ShdrAdapter`, `ShdrIntervalAdapter`, `ShdrQueueAdapter`, `ShdrIntervalQueueAdapter`), feed values from your PLC reader into it. See [Configure an adapter](/configure/adapter). +- **Write a custom agent module** — subclass `MTConnectAgentModule` or `MTConnectInputAgentModule`, wire a config block into `agent.config.yaml`, load the module by ID. The standalone agent application picks it up automatically through the module-loader. +- **Configure the MQTT relay module** — enable `mqtt-relay` in `agent.config.yaml`, point it at an external broker, define the topic template, set the availability topic. See the [MQTT protocol overview](/configure/integrations/mqtt-protocol) for the topic tree. +- **Write a JSON-MQTT consumer** — subscribe to the relay's topic tree, parse each message with the `MTConnect.NET-JSON-cppagent` codec, dispatch by topic prefix. .NET sample uses `MTConnectMqttClient`; Python sample uses `paho-mqtt` with a hand-rolled parser following the JSON-CPPAGENT v2 envelope shape. +- **Migrate from JSON v1 to JSON-CPPAGENT v2** — the v2 codec is the cppagent-parity target; the v1 codec ships for compatibility with consumers that pre-date the spec's JSON formalization. See [Wire formats](/wire-formats/) for the envelope-level comparison. +- **Add a custom DataItem type** — define the type, the controlled-vocabulary subType (if any), and the units in your `Devices.xml`. The agent validates the declaration against the spec's controlled vocabularies and registers the DataItem at startup. +- **Persist Assets to disk** — assets outlive observations and need a storage layer. Configure the agent's asset buffer to back to the file system; the buffer survives restarts. +- **Bridge an MTConnect agent to InfluxDB or Grafana** — see the [InfluxDB integration](/configure/integrations/influxdb) page. +- **Run the agent under a Windows service or systemd unit** — see [Run](/configure/run). + +## Recipe shape + +Every cookbook page follows the same structure: **goal**, **prerequisites**, **steps** (numbered, with code blocks), **verification** (the curl / log / file-system check that proves it worked), **what to read next**. + +## See also + +- [Configure & Use](/configure/) — the reference behind the recipes. +- [API reference](/api/) — every type the recipes mention. +- [Examples](/examples/) — runnable sample applications that mirror the patterns in these recipes. +- [Troubleshooting](/troubleshooting/) — what to do when a recipe doesn't yield the expected result. diff --git a/docs/cookbook/migrate-versions.md b/docs/cookbook/migrate-versions.md new file mode 100644 index 000000000..48baa73e4 --- /dev/null +++ b/docs/cookbook/migrate-versions.md @@ -0,0 +1,147 @@ +# Migrate between MTConnect versions + +`MTConnect.NET` supports every published MTConnect spec version from v1.0 through v2.7. A consumer or agent moving between versions encounters changes in the wire shape, the type system, and the available DataItems / Assets. This recipe is the migration playbook — what to expect at each version step, what code-level changes follow, and how to keep two ends in sync during the transition. + +## When to migrate + +Three triggers for a version bump: + +1. **A spec-version-introduced type is needed** — the consumer wants `ComponentConfigurationParameters` Assets (v2.2+), rich Pallet measurements (v2.4+), or the `Quality` Observation field (v2.3+). +2. **A consumer requires a specific version** — a downstream historian validates against v2.5 XSDs and rejects v2.0 envelopes. +3. **A regulatory or organizational mandate** — the customer's compliance posture pins them to v2.x. + +The wire format does not change in a way that forces a version bump on its own; consumers reading XML against the schema's namespace already pick up the right schema URL. + +## Migration matrix + +The high-frequency-of-impact version transitions: + +| From | To | Code-level impact | Wire-level impact | +|---|---|---|---| +| v1.6 → v1.7 | low | `Agent` Device introduced (auto-registered); `MTConnectVersion` attribute on Device | new top-level `Agent` element in `` | +| v1.8 → v2.0 | low | `coordinateSystem` enum deprecated in favor of `coordinateSystemIdRef` | namespace change to `urn:mtconnect.org:MTConnect:2.0` | +| v2.1 → v2.2 | medium | `Hash` attribute on `Header` and `Device`; `ComponentConfigurationParameters` Asset | new `hash` attribute on every Device | +| v2.2 → v2.3 | low | `Quality` first-class on Observations | new `quality` attribute on Observations | +| v2.3 → v2.4 | medium | rich-template Pallet measurements (typed classes replace free-form `Measurement`) | new Measurement element names in `MTConnectAssets` | +| v2.4 → v2.5 | low | spec-internal cleanup; no new wire-format-visible types | no new attributes | +| v2.5 → v2.6 | low | v2.6 XMI is byte-identical to v2.7 in the published spec | no wire-format change | +| v2.6 → v2.7 | low | spec cleanup; minor attribute additions | no breaking wire-format changes | + +The "impact" column is the typical code-side surface area for a consumer / agent author. None of the transitions above are forced-rewrite; the library handles each through version-aware serialization. + +## Step 1: pin the target + +Set the agent's `defaultVersion` to the target: + +```yaml +defaultVersion: 2.5 +``` + +Or pin in code: + +```csharp +using MTConnect; + +var version = MTConnectVersions.Version25; +var device = Device.Process(myDevice, version); +``` + +`Device.Process(IDevice, Version)` is the version-aware serializer. It prunes properties that did not exist at `version`, strips Components and DataItems whose `MinimumVersion` is above `version`, and emits the rest. The same call shapes JSON-cppagent serialization through `JsonCppAgentFormatter`. + +## Step 2: validate `Devices.xml` against the new XSD + +Update the XML namespace and `schemaLocation`: + +```xml + + ... + +``` + +Validate locally: + +```sh +xmllint --noout --schema https://schemas.mtconnect.org/schemas/MTConnectDevices_2.5.xsd Devices.xml +``` + +The agent validates on startup; running the validator separately is faster when iterating on the model. + +## Step 3: update consumer expectations + +Consumers reading the agent's output need to handle the new attributes / elements without breaking. Specifically: + +- **v2.2 `Hash` attribute** — consumers that ignored unknown attributes already handle this; consumers that did strict-schema validation pick up the new value automatically through the schema bump. +- **v2.3 `Quality` field** — consumers reading observations should default `Quality` to `VALID` when absent. +- **v2.4 Pallet measurements** — consumers parsing Asset measurements should accept the new typed element names (`HeightMeasurement`, `WidthMeasurement`, `LoadedHeightMeasurement`, etc.) in addition to the free-form `Measurement` element. The library handles both. + +## Step 4: code-side updates + +Where the consumer is using `MTConnect.NET` directly, the migration is a constant change: + +```diff +- var version = MTConnectVersions.Version23; ++ var version = MTConnectVersions.Version25; +``` + +That single change re-shapes every serialization on the next request. No other code change is required for a non-breaking bump. + +For breaking transitions (v1.8 → v2.0 around `coordinateSystem`, v2.3 → v2.4 around Pallet measurements), the library accepts the old shape on input and serializes the new shape on output — so reading a v1.8 `Devices.xml` and serving it as v2.0 works without rewriting the input file. To migrate the input file's authoring style: + +```diff +- ++ +``` + +with a `CoordinateSystem` element declared under the Component's `Configuration`. + +## Step 5: dual-version operation during the transition + +A frequent migration pattern: run two agents at once, one on the old version and one on the new, with both fed by the same adapter. Consumers pinned to the old spec read from agent A; consumers pinned to the new spec read from agent B. The same SHDR adapter feeds both via separate `shdr-adapter` module instances on each agent. + +Simplification once the consumer base is fully migrated: shut down agent A and keep agent B. + +A single-agent dual-version pattern works too, since the agent serializes to the requested version per request: + +```sh +# Old consumer hits the agent with ?version=1.8 +curl 'http://agent:5000/current?version=1.8' + +# New consumer hits the agent with ?version=2.5 +curl 'http://agent:5000/current?version=2.5' +``` + +The agent prunes properties and elements per request; no agent-side switching is required. + +## Step 6: validate after migration + +A regression checklist: + +- [ ] `curl 'http://agent:5000/probe?version='` returns a `Devices` envelope whose namespace matches ``. +- [ ] `xmllint --noout --schema ` against a captured `/probe` response succeeds. +- [ ] `Header.schemaVersion` matches the new version on every endpoint. +- [ ] Consumer logs show no parse errors for new-version-introduced attributes. +- [ ] If using MQTT relay, subscribers receive payloads that parse cleanly. + +## Common migration pitfalls + +### A v2.0+ Devices.xml served to a v1.x-pinned consumer + +The agent prunes v2.0-introduced properties when serving v1.x, so this works. Where it fails: when the v2.0-only DataItems are referenced by ID elsewhere in the model (e.g. a `LIMIT` `DataItemRelationship` pointing at a v2.0-only DataItem), the v1.x output ends up with a dangling `idRef`. The fix: author Relationships only against DataItems present at the lowest version your consumers query. + +### Pallet measurements still showing as free-form on v2.4 + +If your `Devices.xml` was authored at v2.3 with ``, the library accepts it but does not auto-promote it to the v2.4 typed `HeightMeasurement` class. To migrate the authoring style, rewrite the `Devices.xml` to use the typed element names. The library serializes both shapes; choose the v2.4 typed shape for new models. + +### Schema version mismatch at startup + +The agent rejects a `Devices.xml` whose namespace declares a version higher than the agent's `MTConnectVersions.Max`. Bump the library before bumping the `Devices.xml` namespace; do not bump the `Devices.xml` to v3.0 if the library shipped only through v2.7. See [Troubleshooting: Schema version mismatches](/troubleshooting/schema-version-mismatches). + +## Where to next + +- [Compliance: Per-version matrix](/compliance/per-version-matrix) — the full feature inventory per version. +- [Configure an agent](/configure/agent-config) — where `defaultVersion` lives. +- [Troubleshooting: Schema version mismatches](/troubleshooting/schema-version-mismatches) — the diagnostic flow when the agent and consumer disagree. +- [Troubleshooting: XSD validation failures](/troubleshooting/xsd-validation-failures) — when the new `Devices.xml` fails validation. diff --git a/docs/cookbook/write-a-json-mqtt-consumer.md b/docs/cookbook/write-a-json-mqtt-consumer.md new file mode 100644 index 000000000..89dd26ed7 --- /dev/null +++ b/docs/cookbook/write-a-json-mqtt-consumer.md @@ -0,0 +1,232 @@ +# Write a JSON-MQTT consumer + +This recipe builds a consumer that subscribes to an MTConnect agent's MQTT relay output, parses the JSON-CPPAGENT-MQTT payloads, and surfaces the observations. By the end you have: + +- A dotnet console application connecting to an MQTT broker. +- Subscription to the relay's per-Device topics. +- Parsing of the JSON envelope into typed `IObservation` instances. +- A Python alternative for non-dotnet consumers. + +## 1. Set up the dotnet consumer + +```sh +dotnet new console -o MyConsumer +cd MyConsumer +dotnet add package MQTTnet +dotnet add package MTConnect.NET-JSON-cppagent +``` + +The `MQTTnet` package is the MQTT client; `MTConnect.NET-JSON-cppagent` is the codec that parses JSON-CPPAGENT envelopes into the library's type system. + +## 2. Connect and subscribe + +```csharp +using MQTTnet; +using MQTTnet.Client; +using System.Text; + +var factory = new MqttFactory(); +var client = factory.CreateMqttClient(); + +var options = new MqttClientOptionsBuilder() + .WithTcpServer("broker.example.com", 1883) + .WithCredentials("consumer-01", "") + .WithClientId("consumer-01") + .WithCleanSession(false) + .Build(); + +await client.ConnectAsync(options); + +// Subscribe to every Sample envelope from every Device. +await client.SubscribeAsync( + new MqttTopicFilterBuilder() + .WithTopic("MTConnect/Document/Sample/+") + .WithAtLeastOnceQoS() + .Build()); + +// Also subscribe to Current envelopes for the bootstrap snapshot. +await client.SubscribeAsync( + new MqttTopicFilterBuilder() + .WithTopic("MTConnect/Document/Current/+") + .WithAtLeastOnceQoS() + .Build()); + +Console.WriteLine("Connected; awaiting payloads. Ctrl-C to exit."); +``` + +## 3. Parse the payload + +The relay publishes JSON-CPPAGENT-MQTT (a JSON-CPPAGENT envelope wrapped for MQTT delivery). The library's [`JsonCppAgentFormatter`](/api/MTConnect.Formatters.JsonCppAgent/JsonCppAgentFormatter) parses it into typed `IStreamsResponseDocument`, `IDevicesResponseDocument`, and `IAssetsResponseDocument` instances: + +```csharp +using MTConnect.Formatters.JsonCppAgent; + +client.ApplicationMessageReceivedAsync += async e => +{ + var payload = e.ApplicationMessage.PayloadSegment.ToArray(); + var topic = e.ApplicationMessage.Topic; + + if (topic.StartsWith("MTConnect/Document/Sample/") || + topic.StartsWith("MTConnect/Document/Current/")) + { + var streams = new JsonCppAgentFormatter().DeserializeStreamsResponse(payload); + if (streams is null) return; + + foreach (var deviceStream in streams.Streams.DeviceStreams) + { + foreach (var componentStream in deviceStream.ComponentStreams) + { + foreach (var obs in componentStream.Observations) + { + Console.WriteLine( + $"{deviceStream.Uuid} {obs.DataItemId} = {obs.GetValue(ValueKeys.Result)} @ {obs.Timestamp:O}"); + } + } + } + } + + await Task.CompletedTask; +}; +``` + +A `Sample` payload contains the delta since the last publish — observations that happened in the last `sampleInterval` ms. A `Current` payload contains the most-recent observation per DataItem at publish time. + +## 4. Watch for asset changes + +Assets arrive on a separate topic. Subscribe and parse: + +```csharp +await client.SubscribeAsync( + new MqttTopicFilterBuilder() + .WithTopic("MTConnect/Document/Asset/+/+") + .Build()); + +// In the message handler: +if (topic.StartsWith("MTConnect/Document/Asset/")) +{ + var assets = new JsonCppAgentFormatter().DeserializeAssetsResponse(payload); + foreach (var asset in assets.Assets) + { + Console.WriteLine($"Asset {asset.AssetId} type={asset.Type} removed={asset.Removed}"); + } +} +``` + +## 5. Filter by Device or DataItem + +The single-plus wildcards in the topic patterns scope subscription. For one specific Device: + +```text +MTConnect/Document/Sample/mill-01 +``` + +For one specific DataItem in Entity-structured mode: + +```text +MTConnect/Entity/Observations/mill-01/x-pos-actual +``` + +A consumer that wants only spindle observations from any mill subscribes: + +```text +MTConnect/Entity/Observations/mill-+/spindle-+ +``` + +The broker handles the wildcard expansion; the consumer sees only matching topics. + +## 6. Reconnect handling + +MQTT clients drop connections on network blips. MQTTnet handles reconnect with a managed client wrapper: + +```csharp +var managed = factory.CreateManagedMqttClient(); + +await managed.StartAsync(new ManagedMqttClientOptionsBuilder() + .WithClientOptions(options) + .WithAutoReconnectDelay(TimeSpan.FromSeconds(5)) + .Build()); + +await managed.SubscribeAsync(/* topics ... */); +``` + +The managed client reconnects automatically and re-establishes subscriptions. Pair it with `cleanSession: false` on the relay so the broker delivers messages that were published while the consumer was disconnected. + +## 7. Python consumer + +For non-dotnet integrations, the same payloads parse cleanly in Python: + +```python +import paho.mqtt.client as mqtt +import json + +def on_connect(client, userdata, flags, rc): + print(f"Connected; rc={rc}") + client.subscribe("MTConnect/Document/Sample/+") + client.subscribe("MTConnect/Document/Current/+") + +def on_message(client, userdata, msg): + payload = json.loads(msg.payload) + streams = payload.get("MTConnectStreams", {}) + for device_stream in streams.get("Streams", {}).get("DeviceStream", []): + for component_stream in device_stream.get("ComponentStream", []): + for category in ("Samples", "Events", "Condition"): + items = component_stream.get(category, []) + for obs in items: + # obs is a single-key wrapper: {"AvailabilityType": {...}} + for type_name, body in obs.items(): + data_item_id = body.get("dataItemId") + value = body.get("Value") or body.get("value") + ts = body.get("timestamp") + print(f"{device_stream['uuid']} {data_item_id} = {value} @ {ts}") + +client = mqtt.Client(client_id="consumer-py") +client.username_pw_set("consumer-01", "") +client.on_connect = on_connect +client.on_message = on_message +client.connect("broker.example.com", 1883, 60) +client.loop_forever() +``` + +The JSON-CPPAGENT shape — each observation wrapped in `{"": {...}}` — is unambiguous to parse; the outer key names the spec type, the inner body carries `dataItemId`, `timestamp`, `value` / `Value`, and any DATA_SET / TABLE entries. + +## 8. Bridging into a database + +A consumer that bridges observations into a time-series database queues them and bulk-inserts: + +```csharp +using System.Threading.Channels; + +var queue = Channel.CreateBounded(10_000); + +client.ApplicationMessageReceivedAsync += async e => +{ + var streams = new JsonCppAgentFormatter().DeserializeStreamsResponse(e.ApplicationMessage.PayloadSegment.ToArray()); + foreach (var ds in streams.Streams.DeviceStreams) + foreach (var cs in ds.ComponentStreams) + foreach (var obs in cs.Observations) + await queue.Writer.WriteAsync(obs); +}; + +_ = Task.Run(async () => +{ + var batch = new List(500); + await foreach (var obs in queue.Reader.ReadAllAsync()) + { + batch.Add(obs); + if (batch.Count >= 500) + { + await InsertBatch(batch); + batch.Clear(); + } + } +}); +``` + +For InfluxDB specifically, see the [InfluxDB integration page](/configure/integrations/influxdb) for the line-protocol mapping. + +## Where to next + +- [Cookbook: Configure MQTT relay](/cookbook/configure-mqtt-relay) — the agent side that publishes the messages this consumer reads. +- [Wire formats: JSON-CPPAGENT-MQTT](/wire-formats/json-cppagent-mqtt) — payload shape reference. +- [`JsonCppAgentFormatter` API reference](/api/MTConnect.Formatters.JsonCppAgent/JsonCppAgentFormatter). +- [Configure & Use: integrations: InfluxDB](/configure/integrations/influxdb) — turn this consumer into a bridge. diff --git a/docs/cookbook/write-a-module.md b/docs/cookbook/write-a-module.md new file mode 100644 index 000000000..5b83c9753 --- /dev/null +++ b/docs/cookbook/write-a-module.md @@ -0,0 +1,234 @@ +# Write a custom agent module + +A **module** is the agent's pluggable extension point. The shipped modules — HTTP server, MQTT broker, MQTT relay, MQTT adapter, SHDR adapter, HTTP adapter — all implement the same [`IMTConnectAgentModule`](/api/MTConnect.Agents/IMTConnectAgentModule) interface. This recipe shows how to write a custom module so an agent can publish to a destination the shipped modules do not cover (an InfluxDB bucket, a Kafka topic, a Postgres table, a webhook). + +By the end you have: + +- A class implementing `IMTConnectAgentModule`. +- The module wired into the agent and receiving observations as the agent buffers them. +- A pattern for declaring the module's config in `agent.config.yaml`. + +## 1. Set up the project + +A custom module is a separate class library. Reference `MTConnect.NET-Common`: + +```sh +dotnet new classlib -o MyCustomModule +cd MyCustomModule +dotnet add package MTConnect.NET-Common +``` + +## 2. Implement IMTConnectAgentModule + +The interface is small. The full surface: + +```csharp +namespace MTConnect.Agents; + +public interface IMTConnectAgentModule +{ + string Id { get; } + void StartBeforeLoad(IMTConnectAgentBroker agent, object configuration); + void StartAfterLoad(IMTConnectAgentBroker agent, object configuration); + void Stop(); +} +``` + +Two lifecycle hooks: `StartBeforeLoad` runs before the agent has loaded the device model; `StartAfterLoad` runs after. Most modules use `StartAfterLoad` because they need to subscribe to observation events that fire once the device model is in place. + +A minimal module that prints every observation to the console: + +```csharp +using System; +using MTConnect.Agents; +using MTConnect.Observations; + +namespace MyCustomModule; + +public class ConsoleSinkModule : IMTConnectAgentModule +{ + public string Id => "console-sink"; + + private IMTConnectAgentBroker _agent; + private ConsoleSinkConfiguration _config; + + public void StartBeforeLoad(IMTConnectAgentBroker agent, object configuration) + { + // no-op for this module. + } + + public void StartAfterLoad(IMTConnectAgentBroker agent, object configuration) + { + _agent = agent; + _config = configuration as ConsoleSinkConfiguration ?? new ConsoleSinkConfiguration(); + + _agent.ObservationAdded += OnObservationAdded; + Console.WriteLine($"[{Id}] Started. Prefix='{_config.Prefix}'"); + } + + public void Stop() + { + if (_agent != null) + { + _agent.ObservationAdded -= OnObservationAdded; + Console.WriteLine($"[{Id}] Stopped."); + } + } + + private void OnObservationAdded(object sender, IObservation obs) + { + var valueText = obs.GetValue(ValueKeys.Result) ?? Observation.Unavailable; + Console.WriteLine($"[{Id}] {_config.Prefix} {obs.DataItemId}={valueText} @ {obs.Timestamp:O}"); + } +} + +public class ConsoleSinkConfiguration +{ + public string Prefix { get; set; } = ">>"; +} +``` + +The `ObservationAdded` event on `IMTConnectAgentBroker` fires once per observation as it enters the buffer. Other events on the broker: + +- `AssetAdded` — fires when an Asset enters the asset buffer. +- `AssetRemoved` — fires when an Asset is removed. +- `DeviceAdded` — fires when a Device is added to the agent's device list. + +## 3. Plug the module into the agent + +Three integration shapes: + +### a. Programmatic (in-process) + +When the agent is hosted in a custom executable, instantiate the module after the agent: + +```csharp +var agent = new MTConnectAgentBroker(...); +agent.AddDevice(device); + +var module = new ConsoleSinkModule(); +module.StartAfterLoad(agent, new ConsoleSinkConfiguration { Prefix = "OBS" }); +``` + +### b. Via the standalone agent's YAML config + +The standalone agent loads modules through reflection. Register the assembly with the agent's module loader (drop the assembly into the agent's `modules/` directory) and reference the module by Id in `agent.config.yaml`: + +```yaml +modules: +- console-sink: + prefix: ">>" +``` + +The agent loader matches the YAML key (`console-sink`) against each module assembly's `Id` property and constructs a configuration object from the YAML value. The config-binding uses YamlDotNet's case-insensitive convention; `Prefix` in C# maps from `prefix` in YAML. + +### c. As a NuGet package + +Publish the module assembly to a NuGet feed (private or `nuget.org`). Consumers add it with `dotnet add package MyCustomModule` and reference the module's `Id` in their `agent.config.yaml`. + +## 4. Lifecycle in detail + +```mermaid +sequenceDiagram + autonumber + participant Cfg as agent.config.yaml + participant Agent as MTConnectAgentBroker + participant Loader as Module loader + participant Mod as Custom module + + Cfg ->> Loader: declares "console-sink" + Loader ->> Mod: instantiate ConsoleSinkModule + Loader ->> Mod: StartBeforeLoad(agent, cfg) + Agent ->> Agent: load Devices.xml + Loader ->> Mod: StartAfterLoad(agent, cfg) + Mod ->> Agent: subscribe to ObservationAdded + Agent ->> Mod: ObservationAdded (per observation) + Agent ->> Mod: Stop() [on shutdown] +``` + +The agent stops every module in reverse-registration order on shutdown. A module's `Stop()` MUST unsubscribe from events and release any held resources; otherwise the agent leaks resources on every restart of a long-lived process. + +## 5. Production patterns + +Custom modules in production deployments typically: + +- **Implement `IDisposable`** (in addition to `IMTConnectAgentModule`) so they release I/O resources cleanly on shutdown. +- **Buffer outgoing writes** so a slow downstream does not back-pressure the agent's observation pipeline. A typical pattern: queue observations in an in-memory channel and flush from a background task. +- **Implement structured logging** — wire the module up to the agent's [`ILogger`](https://learn.microsoft.com/dotnet/api/microsoft.extensions.logging.ilogger) so errors are visible in the standard log stream. +- **Honor the `cancellationToken`** that the agent passes for graceful shutdown. + +A buffered pattern: + +```csharp +private readonly System.Threading.Channels.Channel _queue = + System.Threading.Channels.Channel.CreateBounded(1000); + +public void StartAfterLoad(IMTConnectAgentBroker agent, object configuration) +{ + _agent = agent; + _agent.ObservationAdded += (_, obs) => + { + // Drop if the queue is full; do not block the agent thread. + _queue.Writer.TryWrite(obs); + }; + _ = Task.Run(FlushLoopAsync); +} + +private async Task FlushLoopAsync() +{ + await foreach (var obs in _queue.Reader.ReadAllAsync()) + { + try { await WriteToDownstream(obs); } + catch (Exception ex) { /* log + retry */ } + } +} +``` + +## 6. Test the module + +A minimal NUnit test: + +```csharp +using NUnit.Framework; +using MTConnect.Agents; +using MTConnect.Devices; +using MTConnect.Observations; +using MyCustomModule; + +[TestFixture] +public class ConsoleSinkModuleTests +{ + [Test] + public void Module_subscribes_and_emits_on_observation() + { + var agent = new MTConnectAgentBroker(); + var device = new Device { Id = "test", Uuid = "test", Name = "Test" }; + device.AddDataItem(new MTConnect.Devices.DataItems.AvailabilityDataItem(device.Id)); + agent.AddDevice(device); + + var module = new ConsoleSinkModule(); + module.StartAfterLoad(agent, new ConsoleSinkConfiguration { Prefix = "TEST" }); + + // Capture stdout to assert on the module's output. + using var sw = new System.IO.StringWriter(); + Console.SetOut(sw); + + agent.AddObservation(device.Uuid, new EventValueObservation + { + DataItemId = "test-avail", + Timestamp = DateTime.UtcNow, + CDATA = "AVAILABLE", + }); + + Assert.That(sw.ToString(), Does.Contain("TEST")); + Assert.That(sw.ToString(), Does.Contain("AVAILABLE")); + } +} +``` + +## Where to next + +- [Cookbook: Write an agent](/cookbook/write-an-agent) — the agent host the module plugs into. +- [Configure modules](/configure/module-config) — the configuration shape every shipped module follows. +- [`IMTConnectAgentModule` API reference](/api/MTConnect.Agents/IMTConnectAgentModule). +- [Cookbook: Configure MQTT relay](/cookbook/configure-mqtt-relay) — a shipped-module example to study. diff --git a/docs/cookbook/write-an-adapter.md b/docs/cookbook/write-an-adapter.md new file mode 100644 index 000000000..05da362b8 --- /dev/null +++ b/docs/cookbook/write-an-adapter.md @@ -0,0 +1,171 @@ +# Write an adapter + +This recipe walks through building an MTConnect adapter in code — the upstream half of the data flow that ships values from a custom source (a CSV log, a TCP feed, a PLC) into an MTConnect agent over SHDR. + +By the end you have: + +- A class implementing `IAdapter` that emits SHDR lines on TCP port 7878. +- A test client that connects to the adapter and prints the lines. +- A pattern for wiring the adapter into the agent's `shdr-adapter` module. + +## 1. Set up the project + +```sh +dotnet new console -o MyAdapter +cd MyAdapter +dotnet add package MTConnect.NET-SHDR +``` + +The `MTConnect.NET-SHDR` package contains the SHDR codec — parser, writer, heartbeat state machine. + +## 2. Build a minimal adapter + +The library's [`ShdrAdapter`](/api/MTConnect.Shdr/ShdrAdapter) class implements an SHDR TCP server. Instantiate it with a device key and a port: + +```csharp +using MTConnect.Shdr; + +var adapter = new ShdrAdapter(deviceKey: "mill-01", port: 7878); +adapter.Start(); + +Console.WriteLine("SHDR adapter listening on port 7878 for device mill-01"); +``` + +The adapter is now accepting connections. Any consumer that opens a TCP socket to `localhost:7878` joins the broadcast list. + +## 3. Push observations + +Each observation is fed into the adapter through the `Add` family of methods: + +```csharp +using MTConnect.Shdr; +using MTConnect.Devices; + +// EVENT — discrete state. +adapter.AddDataItem(new ShdrDataItem("avail", "AVAILABLE")); +adapter.AddDataItem(new ShdrDataItem("ctrl-mode", "AUTOMATIC")); + +// SAMPLE — numeric value. +adapter.AddDataItem(new ShdrDataItem("x-pos-actual", 12.345m)); + +// CONDITION — a fault. +adapter.AddCondition(new ShdrCondition("ctrl-system", + ConditionLevel.FAULT, + nativeCode: "E1024", + qualifier: "HIGH", + message: "Spindle over-temperature")); +``` + +The `AddDataItem` call adds the observation to the adapter's outgoing buffer and broadcasts an SHDR line to every connected consumer. The line shape is `||`, formatted per `Part_5.0` of the MTConnect Standard ([docs.mtconnect.org](https://docs.mtconnect.org/)). + +## 4. Drive a real data source + +A typical adapter polls a vendor data source and emits observations on each poll. The pattern: + +```csharp +using System.Net.Http; +using MTConnect.Shdr; + +var adapter = new ShdrAdapter("mill-01", 7878); +adapter.Start(); + +var http = new HttpClient(); + +while (true) +{ + // Pretend this is the PLC's HTTP API. + var json = await http.GetStringAsync("http://192.168.1.100/status"); + var status = ParseStatus(json); + + adapter.AddDataItem(new ShdrDataItem("avail", status.Available ? "AVAILABLE" : "UNAVAILABLE")); + adapter.AddDataItem(new ShdrDataItem("ctrl-mode", status.Mode)); + adapter.AddDataItem(new ShdrDataItem("x-pos-actual", status.AxisX)); + + await Task.Delay(500); +} +``` + +The 500 ms poll interval is the adapter's own pace; the SHDR consumer sees the lines as they emit. Adjust by data source. + +## 5. Test the adapter standalone + +In another terminal: + +```sh +nc localhost 7878 +``` + +You should see: + +```text +2025-01-01T12:34:56.789Z|avail|AVAILABLE +2025-01-01T12:34:56.890Z|ctrl-mode|AUTOMATIC +2025-01-01T12:34:56.890Z|x-pos-actual|12.345 +* PING +``` + +The `* PING` line is the adapter's heartbeat, sent every `Heartbeat` ms (default 10 000). A connected consumer responds with `* PONG ` to confirm liveness. + +## 6. Wire the adapter into an agent + +On the agent side, configure a `shdr-adapter` module that points at the adapter's TCP socket: + +```yaml +modules: +- shdr-adapter: + deviceKey: mill-01 + hostname: localhost + port: 7878 + heartbeat: 1000 + reconnectInterval: 1000 + connectionTimeout: 1000 +``` + +The agent's `shdr-adapter` module connects to `localhost:7878`, consumes the SHDR lines, looks up each `dataItemKey` against the Device's model ([`Device.GetDataItemByKey`](/api/MTConnect.Devices/Device#GetDataItemByKey) checks `Id`, then `Name`, then `Source.DataItemId`, then `Source.Value`), and writes the resulting Observation into the agent's buffer. + +A flow diagram: + +```mermaid +sequenceDiagram + participant PLC + participant Adapter as ShdrAdapter (port 7878) + participant AgentMod as shdr-adapter module + participant Buffer as Agent buffer + participant HTTP as HTTP server + participant Consumer + + PLC ->> Adapter: vendor API response + Adapter ->> AgentMod: SHDR line + AgentMod ->> AgentMod: resolve dataItemKey via Device model + AgentMod ->> Buffer: AddObservation + Consumer ->> HTTP: GET /current + HTTP ->> Buffer: latest per DataItem + Buffer -->> HTTP: observations + HTTP -->> Consumer: MTConnectStreams envelope +``` + +## 7. Handle disconnect / reconnect + +The `ShdrAdapter` class manages reconnect / heartbeat / buffer state internally: + +- When the consumer disconnects, the adapter drops the connection and listens for a new one. +- When the consumer fails to send a `* PONG` within the heartbeat window, the adapter closes the connection. +- On reconnect, the adapter does NOT replay lines emitted while disconnected — the consumer asks the agent for `/sample?from=` to fill the gap, and the agent answers from its buffer. + +The adapter side does not buffer for replay because the data source (a PLC, a sensor) is the source of truth: the agent re-asks the data source on reconnect, not the adapter. This matches the SHDR spec's lifecycle in `Part_5.0` Network. + +## 8. Production patterns + +For production deployments: + +- **Run the adapter as a service**: use `MTConnect.NET-Services` to host it as a Windows service or systemd unit. +- **Persist the source-side queue**: if the data source is reliable but the adapter-to-agent link is flaky, queue at the data-source side (PLC's log, message queue) and play forward. +- **Use MQTT instead of SHDR**: for cross-network deployments, swap the SHDR output for an MQTT publish to a persistent broker. See [Cookbook: Configure MQTT relay](/cookbook/configure-mqtt-relay). +- **Validate the data source's encoding**: SHDR is plain text; ensure the source's character encoding is UTF-8 to avoid byte-mangling on the wire. + +## Where to next + +- [Configure an adapter](/configure/adapter-config) — the standalone adapter executable's YAML config, for cases where you do not need a custom C# adapter. +- [Cookbook: Write an agent](/cookbook/write-an-agent) — the agent side. +- [Wire formats: SHDR](/wire-formats/shdr) — the protocol details. +- [Troubleshooting: Common error modes](/troubleshooting/common-error-modes) — adapter disconnect scenarios. diff --git a/docs/cookbook/write-an-agent.md b/docs/cookbook/write-an-agent.md new file mode 100644 index 000000000..14196da14 --- /dev/null +++ b/docs/cookbook/write-an-agent.md @@ -0,0 +1,193 @@ +# Write an agent + +This recipe walks through building an MTConnect agent in code, end to end. By the end you have a running process that: + +- Holds a Device with a Controller component and a few DataItems. +- Accepts observations. +- Serves `/probe`, `/current`, and `/sample` over HTTP on port 5000. + +The complete code is small: about 60 lines of C# plus a `*.csproj` reference. + +## 1. Set up the project + +Create a new console project and add the meta package: + +```sh +dotnet new console -o MyAgent +cd MyAgent +dotnet add package MTConnect.NET +``` + +The `MTConnect.NET` meta package transitively pulls every shipped library, including `MTConnect.NET-Common`, `MTConnect.NET-HTTP`, and `MTConnect.NET-XML`. + +## 2. Build the Device + +In `Program.cs`: + +```csharp +using MTConnect.Devices; +using MTConnect.Devices.Components; +using MTConnect.Devices.DataItems; + +// Create a Device with a Controller and an Availability data item on each. +var device = new Device +{ + Id = "mill-01", + Uuid = "1234-5678-9abc-def0", + Name = "Mill #1", + Type = Device.TypeId, +}; + +// Attach an AVAILABILITY data item on the Device itself. +device.AddDataItem(new AvailabilityDataItem(device.Id)); + +// Attach a Controller with CONTROLLER_MODE and EXECUTION data items. +var controller = new ControllerComponent { Id = "ctrl" }; +controller.AddDataItem(new ControllerModeDataItem(controller.Id)); +controller.AddDataItem(new ExecutionDataItem(controller.Id)); +device.AddComponent(controller); +``` + +`AddComponent` and `AddDataItem` set the parent-pointers and the ID-format templates automatically — you do not need to populate `Container` or `Parent` by hand. + +## 3. Create the agent + +The agent is a [`MTConnectAgentBroker`](/api/MTConnect.Agents/MTConnectAgentBroker) instance — the broker subclass of [`MTConnectAgent`](/api/MTConnect.Agents/MTConnectAgent) that adds an observation buffer and an asset buffer: + +```csharp +using MTConnect.Agents; + +var agent = new MTConnectAgentBroker( + uuid: "agent-uuid-01", + instanceId: (ulong)DateTimeOffset.UtcNow.ToUnixTimeSeconds(), + deviceModelChangeTime: DateTimeOffset.UtcNow.ToUnixTimeMilliseconds(), + initializeAgentDevice: true); + +agent.AddDevice(device); +``` + +The `initializeAgentDevice: true` argument auto-registers the self-describing Agent Device that emits agent-introspection observations. + +## 4. Push observations + +A single observation lifecycle: + +```csharp +using MTConnect.Observations; + +agent.AddObservation(device.Uuid, new EventValueObservation +{ + DataItemId = "mill-01-avail", + Timestamp = DateTime.UtcNow, + CDATA = "AVAILABLE", +}); + +agent.AddObservation(device.Uuid, new EventValueObservation +{ + DataItemId = "ctrl-mode", + Timestamp = DateTime.UtcNow, + CDATA = "AUTOMATIC", +}); + +agent.AddObservation(device.Uuid, new EventValueObservation +{ + DataItemId = "ctrl-exec", + Timestamp = DateTime.UtcNow, + CDATA = "ACTIVE", +}); +``` + +The agent assigns a monotonically increasing `Sequence` to each observation as it enters the buffer. + +## 5. Start the HTTP server + +The HTTP server module hosts the MTConnect endpoints. Add a reference to `MTConnect.NET-AgentModule-HttpServer` (already transitive through `MTConnect.NET`) and start it: + +```csharp +using MTConnect.Configurations; +using MTConnect.Agents.Modules; + +var httpConfig = new HttpServerModuleConfiguration +{ + Hostname = "0.0.0.0", + Port = 5000, + IndentOutput = true, + DocumentFormat = "xml", +}; + +var httpModule = new HttpServerModule(agent, httpConfig); +await httpModule.StartAsync(); + +Console.WriteLine("Agent running at http://localhost:5000/probe"); +Console.WriteLine("Press Ctrl-C to exit."); +await Task.Delay(Timeout.Infinite); +``` + +## 6. Hit the endpoints + +In another terminal: + +```sh +curl -s http://localhost:5000/probe | head -30 +curl -s http://localhost:5000/current | head -30 +curl -s http://localhost:5000/sample?count=10 | head -30 +``` + +`/probe` returns the Device model — Components, Compositions, DataItems — wrapped in a `MTConnectDevices` envelope. `/current` returns the most-recent observation per DataItem. `/sample` returns the observation history. + +A `/probe` response looks like: + +```xml + +
+ + + + + + + + + + + + + + + + + + +``` + +Note that the `Controllers` Organizer wrapped the Controller automatically — `Device.AddComponent` walks [`MTConnect.Devices.Organizers`](/api/MTConnect.Devices/Organizers) on insert and creates the Organizer where one is required. + +## 7. Test it + +A minimal smoke test using `dotnet`'s built-in HTTP client: + +```csharp +using System.Net.Http; + +var http = new HttpClient { BaseAddress = new Uri("http://localhost:5000") }; +var probe = await http.GetStringAsync("/probe"); +Console.WriteLine(probe); +``` + +The HTTP client returns the same XML envelope the agent serves to curl. + +## What you have now + +- A running agent with one Device, one Controller, and three EVENT DataItems. +- Observations entering the buffer with monotonic sequence numbers. +- The four MTConnect endpoints (`/probe`, `/current`, `/sample`, `/asset`) served over HTTP. + +## Where to next + +- **Add an adapter**: see [Cookbook: Write an adapter](/cookbook/write-an-adapter) for the ingestion side. +- **Switch to JSON output**: set `documentFormat: "json-cppAgent"` in the HTTP config and `Accept: application/mtconnect+json` on the request. See [Wire formats: JSON-CPPAGENT](/wire-formats/json-cppagent). +- **Persist the buffer**: pass an [`IAgentConfiguration`](/api/MTConnect.Configurations/IAgentConfiguration) with `Durable = true` to enable on-disk durability. +- **Run it via YAML**: see [Configure an agent](/configure/agent-config) for the configuration-driven path that skips writing C# entirely. +- **Add an MQTT relay**: see [Cookbook: Configure MQTT relay](/cookbook/configure-mqtt-relay). diff --git a/docs/development/builder.md b/docs/development/builder.md new file mode 100644 index 000000000..553e784ae --- /dev/null +++ b/docs/development/builder.md @@ -0,0 +1,63 @@ +# Release builder (`MTConnect.NET.Builder`) + +- **Source path** — `build/MTConnect.NET.Builder/` +- **Project type** — .NET console application (TFM: `net8.0`) +- **Audience** — repository maintainers and release engineers; not consumed by library users. + +## Purpose + +`MTConnect.NET.Builder` is the in-tree tool that assembles release artefacts from the repository: NuGet packages, Windows installers (Inno Setup), Docker images, and the GitHub release entries that point at them. It exists because the release set spans seven layers (libraries, agent applications, adapter applications, agent modules, adapter modules, container images, installers) and each layer has its own framework matrix and packaging quirks; a single script captures the cross-cutting metadata (publisher, version, repository URL, package tags, icon URLs) in one place rather than scattered across thirty-odd `.csproj` files. + +The tool is not part of the public library surface — it does not ship as a NuGet package, the docs site does not link it from the user-facing nav, and it is excluded from the auto-generated API reference. It is documented here so contributors who need to cut a release can find it. + +## When to run it + +Run the builder when cutting a release. Day-to-day contributors do not invoke it; `dotnet build` against `MTConnect.NET.sln` is enough for normal development. + +## Configuration + +The tool reads two YAML files at start-up: + +- `config.default.yaml` — checked in; the canonical template with the layered manifest (libraries, agent, adapter, packages, installers, docker images). +- `config.production.yaml` — local override (not checked in); points the `input` / `output` / `versionInfoPath` / `innoSetupPath` keys at the build machine's paths. + +The top-level keys are: + +| Key | Type | Purpose | +| --- | --- | --- | +| `publisher` | string | The publisher string baked into NuGet metadata and installer descriptors. | +| `input` | path | The repository root to read source from. | +| `output` | path | The directory the build artefacts land in. | +| `versionInfoPath` | path | The file the tool reads the release version from (`Directory.Build.props`). | +| `innoSetupPath` | path | The Inno Setup compiler executable (`iscc.exe`). | +| `agent` | map | Per-installer + per-image manifest for the agent. | +| `adapter` | map | Per-installer + per-image manifest for the adapter. | +| `libraries` | list of maps | NuGet package families to pack and publish. | + +Each `installer` block carries an application name, output filename, target runtimes (e.g. `win-x86`, `win-x64`), and the .NET framework matrix to compile for. Each `docker` block carries the base image, runtime, and framework per architecture. + +## Build and run + +``` +dotnet run --project build/MTConnect.NET.Builder +``` + +In a `DEBUG` build the tool drops into an interactive prompt that accepts the same commands as the command-line interface; in a release build it reads its arguments and runs to completion. The command parser is in `CommandParser/`; the per-task parts are in `Parts/` (one folder per build phase — `agent`, `adapter`, `libraries`, `installer`, `docker`). + +## Output + +The tool produces: + +- NuGet packages, one per library project listed under `libraries[].packages[]`, written to `output/nuget/`. +- Inno Setup installers, one per `runtime` × `framework` combination listed under `agent.installer` and `adapter.installer`, written to `output/installers/`. +- Docker images, one per `images[]` entry under `agent.docker` and `adapter.docker`, pushed to the registry referenced by `imageName`. +- GitHub release metadata via Octokit, posted against the configured repository. + +## Updating the manifest + +When a new library project lands in the repository, add a corresponding entry under `libraries[].packages[]` in `config.default.yaml`. When a new runtime or framework lands in the support matrix, extend the relevant `runtimes` / `frameworks` lists. The tool reads the manifest dynamically; there is no code change to make alongside. + +## See also + +- [tools/dotnet.sh](/cli/dotnet-sh) and [tools/test.sh](/cli/test-sh) — the day-to-day contributor CLIs (these do not invoke the builder). +- [SysML importer](/cli/sysml-import) — the other in-tree code-generation tool; runs at codebase-edit time, not at release time. diff --git a/docs/examples/agent-embedded.md b/docs/examples/agent-embedded.md new file mode 100644 index 000000000..3cf9f362f --- /dev/null +++ b/docs/examples/agent-embedded.md @@ -0,0 +1,131 @@ +# Embedded agent + +- **Source path** — `examples/MTConnect.NET-Agent-Embedded/` +- **Project type** — .NET console application +- **NuGet package** — [`MTConnect.NET-Applications-Agents`](https://www.nuget.org/packages/MTConnect.NET-Applications-Agents) +- **Configuration** — `examples/MTConnect.NET-Agent-Embedded/agent.config.yaml` + +## Purpose + +Hosts an MTConnect agent inside the same .NET process as the data source, so the data source writes observations into the agent directly. This is the integration shape to pick when: + +- the data source is .NET code you control (a PLC poller, a database tail, another MTConnect agent), and +- a separate SHDR adapter and a TCP hop between adapter and agent would add latency or operational surface without a corresponding benefit. + +The example builds a synthetic CNC device model in code (a controller, a path, three linear axes) and emits a fresh observation set on each read tick. + +## Build and run + +``` +dotnet run --project examples/MTConnect.NET-Agent-Embedded +``` + +The agent loads `agent.config.yaml` from the working directory, starts the HTTP server on port `5000`, and begins emitting observations on the `readInterval` cadence configured for the `datasource` module. Probe the running agent with: + +``` +curl http://localhost:5000/probe +curl http://localhost:5000/current +``` + +## How the example is structured + +`Program.cs` is a single file with three pieces: the entry point, a custom configuration class, and the module that hosts the device model and the read loop. + +### Entry point + +```csharp +var app = new MTConnectAgentApplication(); +app.Run(args, true); +``` + +`MTConnectAgentApplication` is the same host the standalone `mtconnect-agent` CLI uses. Calling `Run(args, true)` starts the agent, reads `agent.config.yaml`, loads any modules registered in that file, and blocks until shutdown. + +### Custom module configuration + +```csharp +public class ModuleConfiguration +{ + public string DeviceUuid { get; set; } + public string DeviceName { get; set; } + public string SerialNumber { get; set; } +} +``` + +Each module can declare its own configuration shape. The agent picks the matching YAML section out of `agent.config.yaml` based on `ConfigurationTypeId` and deserializes it into the class. + +### Agent module + +```csharp +public class Module : MTConnectInputAgentModule +{ + public const string ConfigurationTypeId = "datasource"; + + public Module(IMTConnectAgentBroker agent, object configuration) : base(agent) + { + _configuration = AgentApplicationConfiguration.GetConfiguration(configuration); + } +} +``` + +`MTConnectInputAgentModule` is the base class for modules that produce observations. The agent calls two virtual hooks at start-up and on every read tick: + +- `OnAddDevice()` — return an `IDevice` once at start-up; the agent registers it with the probe response. +- `OnRead()` — called every `readInterval` milliseconds; emit observations with `AddValueObservation` and `AddConditionObservation`. + +### Building the device model in code + +```csharp +protected override IDevice OnAddDevice() +{ + var device = new Device(); + device.Uuid = _configuration.DeviceUuid; + device.Name = _configuration.DeviceName; + device.AddDataItem(); + + AddController(device); + AddAxes(device); + + return device; +} +``` + +Constructing the model from code (rather than loading a static `devices.xml`) is the right path when the shape of the device depends on what the data source reports — variable axis counts, optional sensors, asset serial numbers that change at boot. + +### Emitting observations + +```csharp +protected override void OnRead() +{ + AddValueObservation(Availability.AVAILABLE); + AddValueObservation(EmergencyStop.ARMED); + AddValueObservation(0.0002, "X", PositionDataItem.SubTypes.ACTUAL); + AddConditionObservation( + MTConnect.Observations.ConditionLevel.WARNING, "404", "This is an Alarm"); +} +``` + +`AddValueObservation` accepts the DataItem type and an optional component name, so the same code can target multiple instances of the same component (the three linear axes here share the call shape and differ only in the axis name). + +## Configuring the read cadence and device identity + +```yaml +modules: + +- datasource: + deviceUuid: 7E647B2D-C6A3-40BF-9CE9-FB09834850C9 + deviceName: dev-001 + serialNumber: 123456 + readInterval: 1000 + +- http-server: + port: 5000 +``` + +The `datasource` key matches `ConfigurationTypeId = "datasource"`; the fields below it map onto `ModuleConfiguration` and onto the inherited `readInterval` property. + +## See also + +- [Cookbook: write an agent](/cookbook/write-an-agent) — the same pattern, recast as a step-by-step recipe. +- [Cookbook: write a module](/cookbook/write-a-module) — how to build a reusable module that ships as a NuGet package. +- [HTTP server module](/modules/http-server) — the agent module that serves `/probe`, `/current`, and `/sample`. +- [Agent configuration](/configure/agent-config) — every key the agent reads from `agent.config.yaml`. diff --git a/docs/examples/client-http.md b/docs/examples/client-http.md new file mode 100644 index 000000000..bfd1ebb21 --- /dev/null +++ b/docs/examples/client-http.md @@ -0,0 +1,80 @@ +# HTTP client + +- **Source path** — `examples/MTConnect.NET-Client-HTTP/` +- **Project type** — .NET console application +- **NuGet package** — [`MTConnect.NET-HTTP`](https://www.nuget.org/packages/MTConnect.NET-HTTP) + +## Purpose + +Demonstrates the consumer side of the MTConnect HTTP protocol: connect to a running agent, fetch the device model from `/probe`, then subscribe to a long-polling sample stream and surface each observation to application code via events. + +## Build and run + +Start an agent (the [embedded-agent example](/examples/agent-embedded) is the shortest path), then in a second shell: + +``` +dotnet run --project examples/MTConnect.NET-Client-HTTP +``` + +The example prompts for the hostname and port of the agent on standard input. With the embedded example running: + +``` +Enter Hostname: +localhost +Enter Port: +5000 +Connecting to (localhost:5000).. +Client Started +Device Received : 7E647B2D-C6A3-40BF-9CE9-FB09834850C9 : dev-001 : 2.7 +Observation Received : availability : AVAILABLE @ 2026-05-15T11:08:43.0000000Z +... +``` + +## How the example is structured + +`Program.cs` exposes two client shapes: a document-level client (default) and an entity-level client (commented out). The document client mirrors what most consumers want — read full `Devices`, `Streams`, and `Assets` envelopes; subscribe to event streams. + +### Document client + +```csharp +var client = new MTConnectHttpClient(hostname, port); +client.Interval = 100; + +client.ClientStarted += (s, args) => Console.WriteLine("Client Started"); +client.ClientStopped += (s, args) => Console.WriteLine("Client Stopped"); +client.FormatError += (s, args) => Console.WriteLine($"Format Error : {args.ContentType.Name} : {args.Messages?.FirstOrDefault()}"); + +client.ProbeReceived += (s, response) => { /* iterate response.Devices */ }; +client.CurrentReceived += (s, response) => { /* iterate response.Streams */ }; + +client.Start(); +``` + +`MTConnectHttpClient` wraps the agent's HTTP endpoints (`/probe`, `/current`, `/sample`, `/asset`) and exposes them as a long-polling subscription with event hooks. The `Interval` property is the consumer-side sample interval — the client requests `/sample?interval=100` and receives each sequence batch through `CurrentReceived` (or `SampleReceived` if you wire that hook up instead). + +### Per-observation validation + +The example shows how to validate each observation against its DataItem constraints: + +```csharp +var validationResult = observation.Validate(); +Console.WriteLine($"Observation Validation : {observation.DataItemId} : {validationResult.IsValid} : {validationResult.Message}"); +``` + +`Observation.Validate()` checks the value against the DataItem's controlled vocabulary (for events with enumerated subtypes), the representation (`VALUE`, `DATA_SET`, `TABLE`, `TIME_SERIES`), and the per-version constraints carried in the SysML model. + +## When to pick this client + +Choose `MTConnectHttpClient` when you want: + +- the full envelope structure (devices, components, observations grouped by component-stream), not just flattened observations, +- automatic long-polling so the consumer reacts to new data without burning a poll loop, +- a single event-driven API surface that mirrors the REST shape one-to-one. + +Choose `MTConnectMqttClient` (see the [MQTT client example](/examples/client-mqtt)) instead when the agent publishes through `mqtt-relay` or `mqtt-broker` and you want push delivery without the long-polling overhead. + +## See also + +- [HTTP server module](/modules/http-server) — the server side of this conversation. +- [Wire formats — XML](/wire-formats/xml) and [JSON v1](/wire-formats/json-v1) / [JSON-CPPAGENT v2](/wire-formats/json-v2-cppagent) — what the envelopes look like on the wire. +- [API reference: `MTConnectHttpClient`](/api/) — every event and property the client exposes. diff --git a/docs/examples/client-mqtt.md b/docs/examples/client-mqtt.md new file mode 100644 index 000000000..7b1be9941 --- /dev/null +++ b/docs/examples/client-mqtt.md @@ -0,0 +1,83 @@ +# MQTT client + +- **Source path** — `examples/MTConnect.NET-Client-MQTT/` +- **Project type** — .NET console application +- **NuGet package** — [`MTConnect.NET-MQTT`](https://www.nuget.org/packages/MTConnect.NET-MQTT) + +## Purpose + +Demonstrates the consumer side of an MTConnect-over-MQTT topic tree. The example subscribes to a broker that an agent publishes to (typically through the `mqtt-relay` or `mqtt-broker` agent modules) and prints each device and observation it receives. + +## Build and run + +Stand up an agent that publishes to MQTT — the shortest path is enabling the `mqtt-relay` module in `agent.config.yaml` and pointing it at a local Mosquitto or HiveMQ broker. Then: + +``` +dotnet run --project examples/MTConnect.NET-Client-MQTT +``` + +The example is hard-coded to `localhost:1883` with `MTConnect` as the topic prefix. Adjust those in `Program.cs` for any other broker. + +## How the example is structured + +`Program.cs` exposes two client shapes: a document client (default) and an entity client (commented out). Pick one depending on whether the publisher is a relay (Document mode, default) or a broker emitting per-entity messages (Entity mode). + +### Document client + +```csharp +var config = new MTConnectMqttClientConfiguration(); +config.Server = "localhost"; +config.Port = 1883; +config.TopicPrefix = "MTConnect"; + +var client = new MTConnectMqttClient(config); +client.ClientStarted += (s, args) => Console.WriteLine("Client Started"); +client.DeviceReceived += (topic, device) => + Console.WriteLine($"Device Received : {device.Uuid} : {device.Name}"); +client.ObservationReceived += (topic, observation) => + Console.WriteLine($"Observation Received : {observation.DataItemId} : {string.Join(';', observation.Values.Select(o => o.Value))}"); + +client.Start(); +``` + +`MTConnectMqttClient` subscribes to the broker, walks the topic tree under `TopicPrefix`, parses each payload with the JSON-CPPAGENT-MQTT decoder, and dispatches the result through typed event hooks (`DeviceReceived`, `ObservationReceived`, `AssetReceived`). + +### Document topic tree + +A relay publishes whole envelopes under topics like: + +``` +MTConnect/Probe/ +MTConnect/Current/ +MTConnect/Sample// +MTConnect/Asset/ +``` + +A broker publishes per-observation messages instead — the topic tree is finer-grained, one topic per DataItem. + +### Entity client + +Commented out in the example, but useful when the publisher is `mqtt-broker` and emits one MQTT message per observation: + +```csharp +var client = new MTConnectMqttClient("localhost", 1883); +client.ObservationReceived += (s, observation) => Console.WriteLine(observation.Uuid); +client.AssetReceived += (s, asset) => Console.WriteLine(asset.Uuid); +client.Start(); +``` + +## When to pick this client + +Choose `MTConnectMqttClient` when: + +- the agent already publishes to an MQTT broker (cheaper for many-consumer fan-out than each consumer pulling `/sample`), +- the deployment topology has the consumer behind a firewall that allows outbound MQTT but not inbound HTTP, or +- the consumer wants push delivery without long-polling overhead. + +## See also + +- [MQTT relay module](/modules/mqtt-relay) — publishes whole envelopes (document mode). +- [MQTT broker module](/modules/mqtt-broker) — publishes per-observation messages (entity mode). +- [MQTT protocol overview](/configure/integrations/mqtt-protocol) — the canonical topic tree and message-shape catalogue. +- [JSON-CPPAGENT-MQTT wire format](/wire-formats/json-v2-cppagent-mqtt) — the on-the-wire payload shape. +- [Cookbook: write a JSON-MQTT consumer](/cookbook/write-a-json-mqtt-consumer) — the same flow as a recipe with multi-language samples. diff --git a/docs/examples/client-shdr.md b/docs/examples/client-shdr.md new file mode 100644 index 000000000..0c625c3be --- /dev/null +++ b/docs/examples/client-shdr.md @@ -0,0 +1,62 @@ +# SHDR client + +- **Source path** — `examples/MTConnect.NET-Client-SHDR/` +- **Project type** — .NET console application +- **NuGet package** — [`MTConnect.NET-SHDR`](https://www.nuget.org/packages/MTConnect.NET-SHDR) + +## Purpose + +Demonstrates a minimal SHDR consumer: connect to a TCP endpoint that speaks the SHDR protocol, print every protocol line as it arrives, and exit cleanly on shutdown. Useful when debugging an SHDR adapter, building a custom downstream consumer, or replaying a captured stream against a parser. + +## Build and run + +Point the example at a running SHDR endpoint — typically an `shdr-output`-enabled agent module, the `mtconnect-adapter` CLI, or a custom adapter. Then: + +``` +dotnet run --project examples/MTConnect.NET-Client-SHDR +``` + +The example prompts for hostname and port on standard input. Once connected, each SHDR line prints verbatim: + +``` +Connecting to (localhost:7878).. +Connection Established +2026-05-15T11:08:43.0000000Z|availability|AVAILABLE +2026-05-15T11:08:43.0000000Z|emergencystop|ARMED +2026-05-15T11:08:43.0000000Z|x_position_actual|0.0002 +``` + +## How the example is structured + +`Program.cs` is the smallest of the four examples — it wires three events on `ShdrClient` and starts the connection: + +```csharp +var client = new ShdrClient(hostname, port); + +client.Connected += (s, e) => Console.WriteLine("Connection Established"); +client.ProtocolReceived += (s, line) => Console.WriteLine(line); +client.Disconnected += (s, e) => Console.WriteLine("Disconnected"); + +client.Start(); +Console.ReadLine(); +client.Stop(); +``` + +`ShdrClient` handles the underlying TCP loop, reconnect-on-disconnect behaviour, and per-line buffering. `ProtocolReceived` fires once per `\n`-terminated line; the consumer is responsible for parsing the pipe-delimited fields itself if it needs structured data. + +## When to pick this client + +Choose `ShdrClient` when you want: + +- the raw on-the-wire SHDR text, not parsed observations (debugging, replay, custom routing), +- a smaller dependency footprint than the HTTP or MQTT client (no XML/JSON parser, no envelope reconstruction), +- a pluggable building block for a custom adapter that needs to consume one SHDR stream and emit another. + +If you want parsed observations rather than raw lines, point an agent at the same SHDR endpoint with the `shdr-adapter` module and consume `/current` or `/sample` from the agent instead. + +## See also + +- [SHDR wire format](/wire-formats/shdr) — the line-level grammar and the canonical examples. +- [SHDR adapter module](/modules/shdr-adapter) — the agent-side consumer that turns SHDR lines into observations. +- [SHDR output module](/modules/shdr-output) — the agent-side emitter that produces these lines on the wire. +- [Cookbook: write an adapter](/cookbook/write-an-adapter) — building a producer instead of a consumer. diff --git a/docs/examples/index.md b/docs/examples/index.md new file mode 100644 index 000000000..2f8739b12 --- /dev/null +++ b/docs/examples/index.md @@ -0,0 +1,29 @@ +# Examples + +Runnable, self-contained sample applications in the `examples/` directory of the repository. Each example is a small .NET console project that demonstrates one integration shape — embedding an agent inside an application, or consuming an agent from a client. + +## Available examples + +- **[Embedded agent](/examples/agent-embedded)** — a console application that hosts an MTConnect agent inside its own process and writes observations into it directly, without an external SHDR adapter or TCP hop. +- **[HTTP client](/examples/client-http)** — a console application that connects to a running MTConnect agent over HTTP, polls `/probe` and `/current`, and prints each observation as it arrives. +- **[MQTT client](/examples/client-mqtt)** — a console application that subscribes to an MQTT broker carrying MTConnect-formatted messages (typically published by the `mqtt-relay` or `mqtt-broker` agent modules) and prints each device and observation it receives. +- **[SHDR client](/examples/client-shdr)** — a console application that connects to a raw SHDR endpoint and prints each protocol line as it arrives. Useful when debugging an adapter or building a custom consumer of the SHDR stream. + +## How to run an example + +Each example is a standalone .NET project. From the repository root: + +``` +dotnet run --project examples/MTConnect.NET-Agent-Embedded +dotnet run --project examples/MTConnect.NET-Client-HTTP +dotnet run --project examples/MTConnect.NET-Client-MQTT +dotnet run --project examples/MTConnect.NET-Client-SHDR +``` + +The client examples prompt for connection details on standard input (hostname, port). The embedded-agent example reads its module configuration from `examples/MTConnect.NET-Agent-Embedded/agent.config.yaml`. + +## See also + +- [Getting started](/getting-started) — the shortest path from a fresh checkout to a running agent. +- [Cookbook](/cookbook/) — task-driven recipes that mirror the patterns these examples illustrate. +- [Modules](/modules/) — the agent modules the examples interact with on the wire (HTTP server, MQTT relay/broker, SHDR adapter). diff --git a/docs/getting-started.md b/docs/getting-started.md new file mode 100644 index 000000000..126fca739 --- /dev/null +++ b/docs/getting-started.md @@ -0,0 +1,123 @@ +# Getting started + +This walkthrough takes you from a blank machine to a running `MTConnect.NET` agent serving the `/probe` and `/current` endpoints to a local consumer, in three steps: + +1. Install the agent (NuGet template, prebuilt binary, or Docker). +2. Run it locally. +3. Point a consumer at it. + +For a deeper tour — every config knob, every module, every wire format — head to [Configure & Use](/configure/) once you have the agent running. + +## 1. Install + +Choose the path that matches how you want to deploy. + +### Option A: scaffold a custom agent from the dotnet template + +The fastest way to embed an agent inside your own application. Requires the [.NET SDK](https://dotnet.microsoft.com/download) (9.0 recommended). + +```bash +dotnet new install MTConnect.NET-Agent-Template +mkdir my-agent && cd my-agent +dotnet new mtconnect.net-agent +dotnet run +``` + +The template produces a `Program.cs` with an `MTConnectAgentApplication` host plus a sample data-source module wired up to it. Open `agent.config.yaml` to point the data-source at your PLC, or remove the sample module and add your own. + +### Option B: add the agent NuGet package to an existing project + +```bash +dotnet add package MTConnect.NET-Applications-Agents +``` + +Then in `Program.cs`: + +```csharp +using MTConnect.Applications; + +namespace MyAgent +{ + public class Program + { + public static void Main(string[] args) + { + var app = new MTConnectAgentApplication(); + app.Run(args, true); + } + } +} +``` + +`MTConnectAgentApplication` handles the HTTP server, SHDR adapters, command-line arguments, device management, buffer management, logging, and Windows-service hosting. Add or remove modules through `agent.config.yaml`. + +### Option C: download the prebuilt agent + +Grab the latest installer (Windows) or zip (Linux / macOS) from the [releases page](https://github.com/TrakHound/MTConnect.NET/releases/latest). The installer drops the agent into `Program Files\MTConnect.NET\Agent\` (Windows) or wherever you extract the archive (Linux / macOS) and ships with a default `agent.config.yaml` and a sample `devices/` directory. + +### Option D: Docker + +```bash +docker pull trakhound/mtconnect.net-agent +docker run --rm -p 5000:5000 trakhound/mtconnect.net-agent +``` + +Mount your own `agent.config.yaml` and `devices/` directory with `-v`. See [Run](/configure/run) for the production-grade invocation. + +## 2. Run it + +If you used the template or installed the prebuilt binary, the default config opens an HTTP server on port `5000`: + +```bash +dotnet run # template / source build +./MTConnect.NET-Agent # prebuilt binary on Linux / macOS +MTConnect.NET-Agent.exe # prebuilt binary on Windows +``` + +The console prints the agent header, the loaded modules, and the discovered devices. The HTTP server is now listening on `http://localhost:5000/`. + +The shipped `agent.config.yaml` enables the HTTP server module by default. To add or remove modules — MQTT broker, MQTT relay, SHDR adapter, MQTT adapter, HTTP adapter — uncomment the relevant block in the config file or add a new one. The agent picks up config changes automatically. + +## 3. Point a consumer at it + +The HTTP server speaks the MTConnect REST API. Three endpoints cover most use cases: + +```bash +# What devices and data items does this agent expose? +curl http://localhost:5000/probe + +# What is the most recent value for every data item? +curl http://localhost:5000/current + +# Stream historic samples from sequence 100 onwards. +curl 'http://localhost:5000/sample?from=100&count=100' +``` + +Append `Accept: application/json` (or `?documentFormat=json`) to receive the JSON-CPPAGENT v2 codec output instead of XML: + +```bash +curl -H 'Accept: application/json' http://localhost:5000/current +``` + +For an MQTT-based consumer, enable the `mqtt-relay` module in `agent.config.yaml` and point a subscriber at the relay's topic tree. See [Wire formats](/wire-formats/) for the topic shape and codec details. + +For a programmatic .NET consumer, use the `MTConnectHttpClient` or `MTConnectMqttClient` classes from `MTConnect.NET-HTTP` / `MTConnect.NET-MQTT`: + +```csharp +using MTConnect.Clients; + +var client = new MTConnectHttpClient("http://localhost:5000"); +var probe = await client.GetProbeAsync(); + +foreach (var device in probe.Devices) +{ + Console.WriteLine($"{device.Name}: {device.DataItems.Count} data items"); +} +``` + +## Next steps + +- Add real data: connect an [adapter](/configure/adapter) over SHDR or MQTT. +- Deploy for production: run the agent [as a service](/configure/run) on Windows or Linux. +- Build a custom module: read the [Cookbook](/cookbook/) recipe for writing a module. +- Understand the data model: read [Concepts](/concepts/) for Devices, Components, DataItems, Observations, and Assets. diff --git a/img/Embedded-Architecture-Diagram.png b/docs/img/Embedded-Architecture-Diagram.png similarity index 100% rename from img/Embedded-Architecture-Diagram.png rename to docs/img/Embedded-Architecture-Diagram.png diff --git a/img/MTConnect-Agent/Browser/current-request-web-browser.png b/docs/img/MTConnect-Agent/Browser/current-request-web-browser.png similarity index 100% rename from img/MTConnect-Agent/Browser/current-request-web-browser.png rename to docs/img/MTConnect-Agent/Browser/current-request-web-browser.png diff --git a/img/MTConnect-Agent/Browser/probe-request-web-browser.png b/docs/img/MTConnect-Agent/Browser/probe-request-web-browser.png similarity index 100% rename from img/MTConnect-Agent/Browser/probe-request-web-browser.png rename to docs/img/MTConnect-Agent/Browser/probe-request-web-browser.png diff --git a/img/MTConnect-Agent/Installation/installer-components.png b/docs/img/MTConnect-Agent/Installation/installer-components.png similarity index 100% rename from img/MTConnect-Agent/Installation/installer-components.png rename to docs/img/MTConnect-Agent/Installation/installer-components.png diff --git a/img/MTConnect-Agent/Installation/installer-directory.png b/docs/img/MTConnect-Agent/Installation/installer-directory.png similarity index 100% rename from img/MTConnect-Agent/Installation/installer-directory.png rename to docs/img/MTConnect-Agent/Installation/installer-directory.png diff --git a/img/MTConnect-Agent/Installation/installer-finish.png b/docs/img/MTConnect-Agent/Installation/installer-finish.png similarity index 100% rename from img/MTConnect-Agent/Installation/installer-finish.png rename to docs/img/MTConnect-Agent/Installation/installer-finish.png diff --git a/img/MTConnect-Agent/Installation/installer-license.png b/docs/img/MTConnect-Agent/Installation/installer-license.png similarity index 100% rename from img/MTConnect-Agent/Installation/installer-license.png rename to docs/img/MTConnect-Agent/Installation/installer-license.png diff --git a/img/MTConnect-Agent/Installation/installer-progress.png b/docs/img/MTConnect-Agent/Installation/installer-progress.png similarity index 100% rename from img/MTConnect-Agent/Installation/installer-progress.png rename to docs/img/MTConnect-Agent/Installation/installer-progress.png diff --git a/img/MTConnect-Agent/Installation/installer-review.png b/docs/img/MTConnect-Agent/Installation/installer-review.png similarity index 100% rename from img/MTConnect-Agent/Installation/installer-review.png rename to docs/img/MTConnect-Agent/Installation/installer-review.png diff --git a/img/Traditional-Architecture-Diagram.png b/docs/img/Traditional-Architecture-Diagram.png similarity index 100% rename from img/Traditional-Architecture-Diagram.png rename to docs/img/Traditional-Architecture-Diagram.png diff --git a/img/agent-diagram.png b/docs/img/agent-diagram.png similarity index 100% rename from img/agent-diagram.png rename to docs/img/agent-diagram.png diff --git a/img/mqtt-aws-greengrass-moquette-01.png b/docs/img/mqtt-aws-greengrass-moquette-01.png similarity index 100% rename from img/mqtt-aws-greengrass-moquette-01.png rename to docs/img/mqtt-aws-greengrass-moquette-01.png diff --git a/img/mqtt-aws-thing-certificates.png b/docs/img/mqtt-aws-thing-certificates.png similarity index 100% rename from img/mqtt-aws-thing-certificates.png rename to docs/img/mqtt-aws-thing-certificates.png diff --git a/img/mtconnect-agent-http-communication-dark.png b/docs/img/mtconnect-agent-http-communication-dark.png similarity index 100% rename from img/mtconnect-agent-http-communication-dark.png rename to docs/img/mtconnect-agent-http-communication-dark.png diff --git a/img/mtconnect-agent-http-communication-white.png b/docs/img/mtconnect-agent-http-communication-white.png similarity index 100% rename from img/mtconnect-agent-http-communication-white.png rename to docs/img/mtconnect-agent-http-communication-white.png diff --git a/img/mtconnect-agent-http-communication.png b/docs/img/mtconnect-agent-http-communication.png similarity index 100% rename from img/mtconnect-agent-http-communication.png rename to docs/img/mtconnect-agent-http-communication.png diff --git a/img/mtconnect-agent-http-http-communication-dark.png b/docs/img/mtconnect-agent-http-http-communication-dark.png similarity index 100% rename from img/mtconnect-agent-http-http-communication-dark.png rename to docs/img/mtconnect-agent-http-http-communication-dark.png diff --git a/img/mtconnect-agent-http-http-communication-white.png b/docs/img/mtconnect-agent-http-http-communication-white.png similarity index 100% rename from img/mtconnect-agent-http-http-communication-white.png rename to docs/img/mtconnect-agent-http-http-communication-white.png diff --git a/img/mtconnect-agent-http-http-communication.png b/docs/img/mtconnect-agent-http-http-communication.png similarity index 100% rename from img/mtconnect-agent-http-http-communication.png rename to docs/img/mtconnect-agent-http-http-communication.png diff --git a/img/mtconnect-agent-http-mqtt-communication-white.png b/docs/img/mtconnect-agent-http-mqtt-communication-white.png similarity index 100% rename from img/mtconnect-agent-http-mqtt-communication-white.png rename to docs/img/mtconnect-agent-http-mqtt-communication-white.png diff --git a/img/mtconnect-agent-http-shdr-communication-dark.png b/docs/img/mtconnect-agent-http-shdr-communication-dark.png similarity index 100% rename from img/mtconnect-agent-http-shdr-communication-dark.png rename to docs/img/mtconnect-agent-http-shdr-communication-dark.png diff --git a/img/mtconnect-agent-http-shdr-communication-white.png b/docs/img/mtconnect-agent-http-shdr-communication-white.png similarity index 100% rename from img/mtconnect-agent-http-shdr-communication-white.png rename to docs/img/mtconnect-agent-http-shdr-communication-white.png diff --git a/img/mtconnect-agent-http-shdr-communication.png b/docs/img/mtconnect-agent-http-shdr-communication.png similarity index 100% rename from img/mtconnect-agent-http-shdr-communication.png rename to docs/img/mtconnect-agent-http-shdr-communication.png diff --git a/img/mtconnect-agent-mqtt-shdr-communication-dark.png b/docs/img/mtconnect-agent-mqtt-shdr-communication-dark.png similarity index 100% rename from img/mtconnect-agent-mqtt-shdr-communication-dark.png rename to docs/img/mtconnect-agent-mqtt-shdr-communication-dark.png diff --git a/img/mtconnect-agent-mqtt-shdr-communication.png b/docs/img/mtconnect-agent-mqtt-shdr-communication.png similarity index 100% rename from img/mtconnect-agent-mqtt-shdr-communication.png rename to docs/img/mtconnect-agent-mqtt-shdr-communication.png diff --git a/img/mtconnect-agent-shdr-mqtt-communication-white.png b/docs/img/mtconnect-agent-shdr-mqtt-communication-white.png similarity index 100% rename from img/mtconnect-agent-shdr-mqtt-communication-white.png rename to docs/img/mtconnect-agent-shdr-mqtt-communication-white.png diff --git a/img/mtconnect-mqtt-protocol-all-01.png b/docs/img/mtconnect-mqtt-protocol-all-01.png similarity index 100% rename from img/mtconnect-mqtt-protocol-all-01.png rename to docs/img/mtconnect-mqtt-protocol-all-01.png diff --git a/img/mtconnect-mqtt-protocol-by-device-01.png b/docs/img/mtconnect-mqtt-protocol-by-device-01.png similarity index 100% rename from img/mtconnect-mqtt-protocol-by-device-01.png rename to docs/img/mtconnect-mqtt-protocol-by-device-01.png diff --git a/img/mtconnect-net-02-md.png b/docs/img/mtconnect-net-02-md.png similarity index 100% rename from img/mtconnect-net-02-md.png rename to docs/img/mtconnect-net-02-md.png diff --git a/img/mtconnect-net-03-md.png b/docs/img/mtconnect-net-03-md.png similarity index 100% rename from img/mtconnect-net-03-md.png rename to docs/img/mtconnect-net-03-md.png diff --git a/img/mtconnect-net-03-nuget.png b/docs/img/mtconnect-net-03-nuget.png similarity index 100% rename from img/mtconnect-net-03-nuget.png rename to docs/img/mtconnect-net-03-nuget.png diff --git a/img/vs-create-console-project.png b/docs/img/vs-create-console-project.png similarity index 100% rename from img/vs-create-console-project.png rename to docs/img/vs-create-console-project.png diff --git a/docs/index.html b/docs/index.html deleted file mode 100644 index 4e3dffe83..000000000 --- a/docs/index.html +++ /dev/null @@ -1 +0,0 @@ -HELLO WORLD diff --git a/docs/index.md b/docs/index.md new file mode 100644 index 000000000..8bb5f9b7d --- /dev/null +++ b/docs/index.md @@ -0,0 +1,117 @@ +--- +layout: home + +hero: + name: MTConnect.NET + text: The .NET implementation of the MTConnect Standard + tagline: 100% public-surface API coverage. 100% MTConnect Standard compliance. + actions: + - theme: brand + text: Get started + link: /getting-started + - theme: alt + text: View on GitHub + link: https://github.com/TrakHound/MTConnect.NET + +features: + - title: MTConnect Standard compliance + details: | + Every shipped envelope (Streams, Devices, Assets, Error) validates against the corresponding XSD across MTConnect v1.0 through v2.7. Wire output is byte-for-byte cppagent-parity for the JSON-CPPAGENT v2 array-of-wrappers codec. + link: /compliance/ + linkText: Compliance posture + - title: Public-surface API coverage + details: | + Every public class, interface, method, property, event, and enum has a documentation page generated from the library's XML doc comments — with a real usage example. + link: /api/ + linkText: API reference + - title: Configure-and-use guides + details: | + End-to-end guides for installing the NuGet packages, configuring an agent, configuring an adapter, running locally / in Docker / as a service, and connecting a consumer over HTTP or MQTT. + link: /configure/ + linkText: Configure & Use + - title: Wire-format reference + details: | + XML, JSON v1, JSON-CPPAGENT (v2 codec), JSON-CPPAGENT-MQTT, SHDR — sample envelopes, codec class names, round-trip pseudocode, and Mermaid diagrams for the wire-flow handshakes. + link: /wire-formats/ + linkText: Wire formats + - title: Cookbook + details: | + Recipes for common problems — write an agent, write an adapter, write a module, configure the MQTT relay, write a JSON-MQTT consumer. + link: /cookbook/ + linkText: Cookbook + - title: Runnable examples + details: | + Four self-contained console applications in `examples/` — an embedded agent, an HTTP client, an MQTT client, and an SHDR client. Each is `dotnet run`-able directly from the repository. + link: /examples/ + linkText: Examples + - title: Troubleshooting + details: | + XSD validation failures, schema-version mismatches, MQTT TLS handshake failures — common errors and the fixes that work. + link: /troubleshooting/ + linkText: Troubleshooting +--- + +## What is MTConnect.NET? + +`MTConnect.NET` is a fully open-source .NET library set, agent application, and adapter application that implements the [MTConnect Standard](https://www.mtconnect.org/) end to end. It ships: + +- **A standalone agent application** — a preconfigured executable that hosts an MTConnect agent with a modular architecture (HTTP server, MQTT broker, MQTT relay, SHDR adapter, MQTT adapter, HTTP adapter). Runs on Windows, Linux, and macOS, with installers, a Docker image, and Windows-service / systemd-unit deployment paths. +- **A standalone adapter application** — for shipping data from a PLC or other source into an MTConnect agent over SHDR or MQTT. +- **Embeddable libraries** — fourteen NuGet packages (`MTConnect.NET`, `MTConnect.NET-Common`, `MTConnect.NET-HTTP`, `MTConnect.NET-SHDR`, `MTConnect.NET-MQTT`, `MTConnect.NET-XML`, `MTConnect.NET-JSON`, `MTConnect.NET-JSON-cppagent`, `MTConnect.NET-TLS`, `MTConnect.NET-Services`, `MTConnect.NET-DeviceFinder`, `MTConnect.NET-SysML`, plus the `MTConnect.NET-Applications-Agents` and `MTConnect.NET-Applications-Adapter` host packages) for embedding agent / adapter / client functionality inside a custom application. +- **Spec coverage through v2.7** — the SysML model drives source generation, so every spec-version-introduced type is present, every deprecation is recorded, and every type carries its `MinimumVersion` / `MaximumVersion` metadata. + +## Target frameworks + +The libraries multi-target .NET 9.0, .NET 8.0, .NET 7.0, .NET 6.0, .NET 5.0, .NET Core 3.1, .NET Standard 2.0, and .NET Framework 4.6.1 through 4.8. + +## Architecture at a glance + +```mermaid +flowchart LR + subgraph adapters[Adapters] + SHDR[SHDR adapter] + HTTPADAPT[HTTP adapter] + end + + subgraph agent[MTConnect.NET Agent] + direction TB + INPUT[Input pipeline] + BUFFER[Sequence buffer] + PROBE[Probe / Current / Sample / Asset] + MODULES[Modules] + end + + subgraph wire[Wire formats] + XMLENV[XML envelope] + JSONV2[JSON-CPPAGENT v2] + MQTT[MQTT relay topics] + end + + subgraph consumers[Consumers] + DASHBOARD[Dashboards] + BRIDGE[Bridges] + HISTORIAN[Historians] + end + + SHDR --> INPUT + HTTPADAPT --> INPUT + INPUT --> BUFFER + BUFFER --> PROBE + PROBE --> MODULES + MODULES --> XMLENV + MODULES --> JSONV2 + MODULES --> MQTT + XMLENV --> DASHBOARD + JSONV2 --> BRIDGE + MQTT --> HISTORIAN +``` + +The diagram above is rendered by the Mermaid plugin. Every architecture / sequence / state-machine / wire-flow diagram in this site is authored in Mermaid — no ASCII art, no external image renders for schematic content. + +## Where to next + +- New to MTConnect.NET? Start with [Getting started](/getting-started). +- Deciding whether the library covers your spec target? Read the [Compliance](/compliance/) posture. +- Standing up an agent against real equipment? Walk through [Configure & Use](/configure/). +- Looking up a specific class or method? Open the [API reference](/api/). +- Want to see a working program first? Browse the [Examples](/examples/) — four `dotnet run`-able console apps for the common integration shapes. diff --git a/docs/modules/agent-processor-python.md b/docs/modules/agent-processor-python.md new file mode 100644 index 000000000..85272de24 --- /dev/null +++ b/docs/modules/agent-processor-python.md @@ -0,0 +1,143 @@ +# Python agent processor + +- **Module name** — MTConnect Python Agent Processor +- **Identifier** — `python` +- **NuGet package** — `MTConnect.NET-AgentProcessor-Python` +- **Source path** — `agent/Processors/MTConnect.NET-AgentProcessor-Python/` + +## Purpose + +Runs a directory of Python scripts as a per-observation transform between the adapter intake and the agent's observation buffer. Each script exports a `process(observation)` function; the processor invokes every loaded function in turn and passes the resulting `ProcessObservation` on to the next hop in the pipeline. Use the processor to rewrite a single observation's value (units conversion, threshold mapping), to derive new observations from one observation, or to filter observations out (return `None` to suppress a write). + +This is the only processor in the module catalogue that hosts a non-.NET scripting language. It loads scripts in the standalone agent application (`MTConnect.NET-Agent` / `MTConnect.NET-Agent-Application`) and is also available as a standalone NuGet package for embedding in a custom agent host. + +## Configuration schema + +The module's configuration class is `ProcessorConfiguration`. The keys below describe the YAML map under `python:`. + +| Key | Type | Default | Permissible values | Notes | +| --- | --- | --- | --- | --- | +| `directory` | string | `processors` | absolute path or path relative to the agent's base directory | The directory the processor monitors for `.py` script files. Created on startup if absent. | + +The processor watches the directory with a `FileSystemWatcher` and reloads any changed, created, or deleted `.py` file on a 2-second debounce — edits land without restarting the agent. + +## Wire interaction + +```mermaid +sequenceDiagram + participant Adapter as Adapter intake + participant Agent as Agent core + participant Processor as Python processor + participant Script as process(observation) + participant Buffer as Observation buffer + + Adapter->>Agent: ObservationInput + Agent->>Processor: OnProcess(observation) + loop one invocation per loaded .py file + Processor->>Script: process(observation) + Script-->>Processor: ProcessObservation (or None) + end + Processor-->>Agent: ObservationInput + Agent->>Buffer: write +``` + +Scripts run in declaration order under a single `IronPython.Hosting.Python` engine. A script that throws is logged at `Error` level and skipped — the next script in the directory still runs against the original or partially-transformed observation, so a bad script does not stall the pipeline. + +## Example configuration + +A typical agent configuration that loads the Python processor alongside a `shdr-adapter` and an `http-server`: + +```yaml +processors: + - python: + directory: processors + +modules: + - shdr-adapter: + address: 127.0.0.1 + port: 7878 + deviceKey: M12346 + + - http-server: + port: 5000 +``` + +The example scripts below sit under `./processors/` next to the agent executable. + +### Map an `EMERGENCY_STOP` event to `ARMED` / `TRIGGERED` + +```python +def process(observation): + + if observation.DataItem.Type == 'EMERGENCY_STOP': + + result = observation.GetValue('Result') + + if result.lower() == 'TRUE'.lower(): + observation.AddValue('Result', 'ARMED') + else: + observation.AddValue('Result', 'TRIGGERED') + + return observation +``` + +### Scale `PATH_FEEDRATE_OVERRIDE` from a fraction to a percentage + +```python +def process(observation): + + if observation.DataItem.Type == 'PATH_FEEDRATE_OVERRIDE': + + result = float(observation.GetValue('Result')) + observation.AddValue('Result', result * 100) + + return observation +``` + +### Derive a `TIME_SERIES` observation from a discrete sample + +```python +import clr +clr.AddReference("MTConnect.NET-Common") +import MTConnect.Input + +def process(observation): + + if observation.DataItem.Id == "L2p1Fact": + + timeseries = MTConnect.Input.TimeSeriesObservationInput() + timeseries.DataItemKey = 'L2p1Sensor' + timeseries.SampleRate = 100 + + n = 15 + samples = [0] * n + + for x in range(n): + samples[x] = float(x) + + timeseries.Samples = samples + + observation.Agent.AddObservation(observation.DataItem.Device.Uuid, timeseries) + + return observation +``` + +## Scripting environment + +- The scripting engine is **IronPython**, the .NET implementation of Python 3. Standard library coverage is broad but not complete; CPython-only extensions (NumPy, SciPy, pandas, anything with native C extensions) are not available. +- `clr.AddReference` exposes any assembly the agent has loaded. The `MTConnect.NET-Common` reference shown above brings `MTConnect.Input.*` into scope so a script can construct new observations directly. +- The `observation` argument is a `ProcessObservation` (see [API reference](/api/MTConnect.Processors.html)). Its `Agent` property is the running `IMTConnectAgent`, so a script can call `AddObservation(deviceUuid, observationInput)` to inject a new observation without returning it from `process`. +- Returning `None` suppresses the write entirely — useful for filtering noise out of the buffer. + +## Troubleshooting pointers + +- **A script loads but does not run** — the `process` symbol must be a module-level function with one parameter. Check the agent log for `Python Script Loaded : ` at `Debug` level; a script that loads but does not log that line is missing the `process` symbol. +- **`Error Loading Python Script` on startup** — the agent log line includes the script path and the exception message. Most commonly: a `SyntaxError`, or an `ImportError` for a CPython-only module. +- **Edits are not picked up** — the watcher only fires on files matching `*.py` in the configured `directory` (no recursion). Subdirectories are ignored; symlinks follow the platform default. + +See the [Troubleshooting](/troubleshooting/) section for general observation-pipeline failures. + +## API reference + +- [`MTConnect.Processors`](/api/MTConnect.Processors.html) — the processor base class and the `ProcessObservation` model the scripts receive. +- [`MTConnect.Input`](/api/MTConnect.Input.html) — the `ObservationInput` / `TimeSeriesObservationInput` types a script can construct and feed back into the agent via `AddObservation`. diff --git a/docs/modules/http-adapter.md b/docs/modules/http-adapter.md new file mode 100644 index 000000000..c07e12eb7 --- /dev/null +++ b/docs/modules/http-adapter.md @@ -0,0 +1,114 @@ +# HTTP adapter + +- **Module name** — MTConnect HTTP Adapter agent module +- **Identifier** — `http-adapter` +- **NuGet package** — `MTConnect.NET-AgentModule-HttpAdapter` +- **Source path** — `agent/Modules/MTConnect.NET-AgentModule-HttpAdapter/` + +## Purpose + +Reads from another MTConnect agent's REST endpoints (`/probe`, `/current`, `/sample`) and forwards the observations into the local agent. Use this module to aggregate observations from several upstream agents into one consolidated agent, or to bridge agents that sit on different networks. The module supports both streaming (chunked-transfer `/sample`) and polling (repeated `/current`) modes. + +## Configuration schema + +The module's configuration class is `HttpAdapterModuleConfiguration` (it derives from `HttpClientConfiguration`). The keys below describe the YAML map under `http-adapter:`. + +| Key | Type | Default | Permissible values | Notes | +| --- | --- | --- | --- | --- | +| `address` | string | `null` | hostname or IP address | The remote agent's address. | +| `port` | int | `5000` | 1-65535 | The remote agent's HTTP / HTTPS port. | +| `deviceKey` | string | `null` | device name or UUID | The remote-agent device to read. | +| `interval` | int | `500` | milliseconds | The polling / streaming interval requested from the remote agent. | +| `heartbeat` | int | `1000` | milliseconds | The heartbeat interval used to keep the streaming connection alive. | +| `useSSL` | bool | `false` | `true`, `false` | Switches the client to HTTPS. | +| `outputConnectionInformation` | bool | `true` | `true`, `false` | Emits host / port of the upstream agent as an observation alongside the forwarded data. | +| `currentOnly` | bool | `false` | `true`, `false` | When `true`, the module polls `/current` only and does not request `/sample` pages. | +| `useStreaming` | bool | `true` | `true`, `false` | When `true`, uses HTTP chunked-transfer streaming on `/sample`; when `false`, polls `/sample` at the configured interval. | +| `devices` | map[string,`DeviceMappingConfiguration`] | `null` | see below | Maps remote device identifiers to local device identifiers. | + +### `devices` schema + +Each entry maps a remote device to a local device. The map key is the remote-agent device identifier (`Device@name` or `Device@uuid`); the value's fields choose the corresponding local device: + +| Key | Type | Notes | +| --- | --- | --- | +| `name` | string | The local device's `name`. | +| `uuid` | string | The local device's `uuid`. | +| `id` | string | The local device's `id`. | + +Set at least one of `name` / `uuid` / `id`; the resolver picks the first non-null in that order. + +## Wire interaction + +```mermaid +sequenceDiagram + autonumber + participant Upstream as Upstream MTConnect agent + participant Adapter as http-adapter module + participant Local as Local MTConnect agent + participant Buffer as Sequence buffer + + Adapter->>Upstream: GET /probe?device= + Upstream-->>Adapter: 200 OK + Devices envelope + Adapter->>Local: register device (mapped per devices: map) + Adapter->>Upstream: GET /current?device= + Upstream-->>Adapter: 200 OK + Streams envelope + Adapter->>Local: AddObservations(mapped deviceKey, ...) + Local->>Buffer: append to sequence buffer + alt useStreaming = true + Adapter->>Upstream: GET /sample?device=&interval=&heartbeat= (chunked) + loop chunks + Upstream-->>Adapter: streamed Streams envelope chunk + Adapter->>Local: AddObservations(mapped deviceKey, ...) + end + else useStreaming = false (polling) + loop every ms + Adapter->>Upstream: GET /current?device= + Upstream-->>Adapter: 200 OK + Streams envelope + Adapter->>Local: AddObservations(mapped deviceKey, ...) + end + end +``` + +## Example configuration + +```yaml +modules: + - http-adapter: + address: upstream-agent.example.com + port: 5000 + deviceKey: M12346 + interval: 100 + heartbeat: 10000 + useSSL: false + currentOnly: false + useStreaming: true + devices: + M12346: + uuid: 00000000-0000-0000-0000-00000000abcd +``` + +For HTTPS: + +```yaml +modules: + - http-adapter: + address: upstream-agent.example.com + port: 5001 + useSSL: true + deviceKey: M12346 + useStreaming: true +``` + +## Troubleshooting + +- **Schema-version mismatches** — see [Schema-version mismatches](/troubleshooting/#schema-version-mismatches). If the upstream agent serves a different MTConnect version than the local agent expects, observations may fail to deserialize. +- **Heartbeat / interval tuning** — the upstream agent enforces an MTConnect-spec minimum on the `heartbeat` and `interval` query parameters. The module passes the configured values through verbatim; out-of-range values produce a `MTConnect.Errors.OUT_OF_RANGE` response from the upstream and the module retries. +- **Device-key mismatch** — `deviceKey` must match a device on the upstream agent. Use a browser to hit the upstream's `/probe` and confirm the device exists before configuring this module. +- **TLS / certificate errors** under `useSSL: true` are surfaced as connection-level failures and retried at the module's reconnect interval. + +## API reference + +- [`HttpAdapterModuleConfiguration`](/api/) — the module's configuration class. +- [`HttpClientConfiguration`](/api/) — the base HTTP client configuration shape. +- [`DeviceMappingConfiguration`](/api/) — the per-device mapping entry. diff --git a/docs/modules/http-server.md b/docs/modules/http-server.md new file mode 100644 index 000000000..98343010b --- /dev/null +++ b/docs/modules/http-server.md @@ -0,0 +1,132 @@ +# HTTP server + +- **Module name** — MTConnect HTTP Server agent module +- **Identifier** — `http-server` +- **NuGet package** — `MTConnect.NET-AgentModule-HttpServer` +- **Source path** — `agent/Modules/MTConnect.NET-AgentModule-HttpServer/` + +## Purpose + +Serves the MTConnect REST protocol — `/probe`, `/current`, `/sample`, `/asset` — over HTTP or HTTPS. This is the most common way to expose an agent to dashboards, bridges, and other consumers. The module wraps `MTConnectHttpServer` (under `MTConnect.Servers.Http`), accepts content-negotiated XML and JSON output, optionally accepts HTTP `PUT` of observations and assets, and serves a configurable set of static files (schemas, stylesheets, favicons). + +## Configuration schema + +The module's configuration class is `HttpServerModuleConfiguration` (it derives from `HttpServerConfiguration`). The keys below describe the YAML map under `http-server:`. Booleans use lowercase `true` / `false`; integer ports are unquoted decimals. + +| Key | Type | Default | Permissible values | Notes | +| --- | --- | --- | --- | --- | +| `hostname` | string | `null` (binds to all interfaces) | hostname, IP address, or `localhost` | The IP address or hostname the server binds to. | +| `port` | int | `5000` | 1-65535 | The TCP port to listen on. | +| `tls` | map | `null` (HTTP only) | see below | TLS configuration; presence switches the listener to HTTPS. | +| `accept` | map[string,string] | `{ "text/xml": "XML", "application/xml": "XML", "application/json": "JSON" }` | HTTP-accept-header to document-format-id pairs | Negotiates the response document format from the `Accept` header. | +| `responseCompression` | string[] | `null` | `gzip`, `br`, `deflate` | Compression encodings advertised to the client. | +| `allowPut` | bool | `false` | `true`, `false` | Allow HTTP `PUT` or `POST` of observation values and assets. | +| `allowPutFrom` | string[] | `null` | hostname or IP list | Restricts `PUT` / `POST` access to listed hosts when `allowPut` is `true`. | +| `defaultVersion` | string | unset (latest) | MTConnect version (e.g. `1.7`, `2.0`, `2.7`) | The MTConnect version the agent emits when the request does not specify one. | +| `documentFormat` | string | `XML` | `XML`, `JSON`, `JSON-cppAgent` | Default response document format. | +| `indentOutput` | bool | `true` | `true`, `false` | Indents the response document for readability. | +| `outputComments` | bool | `false` | `true`, `false` | Embeds MTConnect-standard descriptions as comments in the response. | +| `outputValidationLevel` | int | `0` | `0` (Ignore), `1` (Warning), `2` (Strict) | Server-side validation level applied before emitting the response. | +| `files` | list of `FileConfiguration` | `null` | see below | Static files served alongside the protocol endpoints (schemas, stylesheets, favicon). | +| `devicesNamespaces` | list of `NamespaceConfiguration` | `null` | see below | Extra XML namespaces injected into Devices envelopes. | +| `streamsNamespaces` | list of `NamespaceConfiguration` | `null` | as above | Extra XML namespaces injected into Streams envelopes. | +| `assetsNamespaces` | list of `NamespaceConfiguration` | `null` | as above | Extra XML namespaces injected into Assets envelopes. | +| `errorNamespaces` | list of `NamespaceConfiguration` | `null` | as above | Extra XML namespaces injected into Error envelopes. | +| `devicesStyle` | `StyleConfiguration` | `null` | XSLT stylesheet reference | Server-side XSLT applied to Devices responses. | +| `streamsStyle` | `StyleConfiguration` | `null` | as above | Server-side XSLT applied to Streams responses. | +| `assetsStyle` | `StyleConfiguration` | `null` | as above | Server-side XSLT applied to Assets responses. | +| `errorStyle` | `StyleConfiguration` | `null` | as above | Server-side XSLT applied to Error responses. | + +### `files[]` schema + +Each entry describes a static-file mount: + +| Key | Type | Permissible values | Notes | +| --- | --- | --- | --- | +| `path` | string | filesystem path | The location on the server (relative to the agent's working directory or absolute). | +| `location` | string | URL path segment | The path component to match in the inbound URL. | + +### `tls` schema + +The map accepts either a PFX bundle or a PEM triple: + +| Key | Sub-key | Type | Notes | +| --- | --- | --- | --- | +| `pfx` | `certificatePath` | string | Path to the `.pfx` file. | +| `pfx` | `certificatePassword` | string | PFX password. | +| `pem` | `certificatePath` | string | Path to the `.pem` certificate file. | +| `pem` | `privateKeyPath` | string | Path to the key file. | +| `pem` | `privateKeyPassword` | string | Key password (if encrypted). | +| `pem` | `certificateAuthority` | string | Path to the CA certificate. | +| `verifyClientCertificate` | — | bool | Toggles mutual-TLS verification of client certificate chains. | + +## Wire interaction + +```mermaid +sequenceDiagram + autonumber + participant Consumer + participant HTTP as http-server module + participant Agent as MTConnect agent core + participant Buffer as Sequence buffer + + Consumer->>HTTP: GET /probe + HTTP->>Agent: GetDevicesResponseDocument(...) + Agent-->>HTTP: Devices envelope + HTTP-->>Consumer: 200 OK + Devices document + Consumer->>HTTP: GET /current + HTTP->>Buffer: GetObservations(at: latest) + Buffer-->>HTTP: observation set + HTTP-->>Consumer: 200 OK + Streams document + Consumer->>HTTP: GET /sample?from=N&heartbeat=10000 + HTTP->>Buffer: GetObservations(from: N, ...) + Buffer-->>HTTP: observation page + HTTP-->>Consumer: 200 OK + Streams document (or chunked stream) +``` + +For long-running `sample` requests the module emits an HTTP chunked-transfer stream and pushes new observation pages as the agent receives them, holding the connection open up to the configured heartbeat interval. + +## Example configuration + +```yaml +modules: + - http-server: + hostname: 0.0.0.0 + port: 5000 + allowPut: true + indentOutput: true + documentFormat: XML + accept: + text/xml: XML + application/xml: XML + application/json: JSON-cppAgent + responseCompression: + - gzip + - br + files: + - path: schemas + location: schemas + - path: styles + location: styles + - path: styles/favicon.ico + location: favicon.ico + tls: + pfx: + certificatePath: /etc/mtconnect/certs/agent.pfx + certificatePassword: changeme + verifyClientCertificate: false +``` + +## Troubleshooting + +- **XSD validation failures** — see [XSD validation failures](/troubleshooting/#xsd-validation-failures). The .NET BCL ships XSD 1.0 features only; the v2.x MTConnect schemas use XSD 1.1 constructs. +- **MQTT TLS handshake failures** apply to the broker / relay modules; for HTTPS handshake failures the certificate must be readable by the agent's user account and the `tls.pfx.certificatePassword` must decrypt the PFX bundle. +- **Schema-version mismatches** — set `defaultVersion` to the MTConnect version the consumer expects when the consumer does not send a version parameter. + +## API reference + +- [`HttpServerModuleConfiguration`](/api/) — the module's configuration class. +- [`HttpServerConfiguration`](/api/) — the base configuration shape this module extends. +- [`MTConnectHttpServer`](/api/) — the runtime HTTP server the module wraps. +- [`MTConnectShdrHttpAgentServer`](/api/) — the concrete server with SHDR-protocol `PUT` handling enabled. +- [`TlsConfiguration`](/api/) — the TLS configuration schema. diff --git a/docs/modules/index.md b/docs/modules/index.md new file mode 100644 index 000000000..999fde725 --- /dev/null +++ b/docs/modules/index.md @@ -0,0 +1,83 @@ +# Modules + +`MTConnect.NET` ships an extensible agent and an extensible adapter. The runtime behavior each one exposes is composed from **modules** — small, independently configured units loaded on startup from the host's `agent.config.yaml` (for agent modules) or `adapter.config.yaml` (for adapter modules). A module's identifier is the YAML key under `modules:`; a module's configuration is the YAML map under that key. + +This section catalogs every shipped module — its purpose, its configuration knobs, the wire interaction it owns, an example configuration block, and where to look when it misbehaves. + +## How modules plug in + +```mermaid +flowchart LR + subgraph adapterhost[Adapter host] + direction TB + AHOST[ModuleHost] + AMOD[Adapter modules] + AHOST -- loads --> AMOD + end + + subgraph agenthost[Agent host] + direction TB + GHOST[AgentApplication] + GMOD[Agent modules] + GHOST -- loads --> GMOD + end + + subgraph external[External systems] + PLC[PLC / CNC / sensors] + BROKER[MQTT broker] + CONSUMER[HTTP / MQTT consumers] + end + + PLC -->|SHDR / MQTT| AMOD + AMOD -->|SHDR / MQTT| GMOD + GMOD -->|MTConnect REST / MQTT| CONSUMER + GMOD <-->|publish / subscribe| BROKER +``` + +Every agent module derives from `MTConnectAgentModule` (under `MTConnect.Modules`) and is registered via a `ConfigurationTypeId` const that matches the YAML key. Every adapter module derives from `MTConnectAdapterModule` and is registered the same way. The host application instantiates one module per YAML entry, passing the deserialized configuration map; the module owns its own startup, shutdown, and reconnection lifecycle. + +## Agent modules — shipped + +These six modules ship under `agent/Modules/MTConnect.NET-AgentModule-*` and load into the standalone agent application (`MTConnect.NET-Agent` / `MTConnect.NET-Agent-Application`). Each one is also available as a standalone NuGet package for embedding in a custom agent host. + +| Module | YAML key | Purpose | +| --- | --- | --- | +| [HTTP server](./http-server) | `http-server` | Serves the MTConnect REST protocol (Probe / Current / Sample / Asset) over HTTP / HTTPS. | +| [MQTT broker](./mqtt-broker) | `mqtt-broker` | Hosts an embedded MQTT broker that publishes the agent's documents and entities. | +| [MQTT relay](./mqtt-relay) | `mqtt-relay` | Publishes the agent's documents and entities to an external MQTT broker. | +| [MQTT adapter](./mqtt-adapter) | `mqtt-adapter` | Subscribes to an external MQTT broker and feeds observations into the agent. | +| [HTTP adapter](./http-adapter) | `http-adapter` | Polls or streams from another MTConnect agent's HTTP endpoints and feeds the observations into the local agent. | +| [SHDR adapter](./shdr-adapter) | `shdr-adapter` | Reads SHDR-protocol input from one or more SHDR adapters and feeds observations into the agent. | + +## Agent processors — shipped + +Agent processors sit one hop earlier than modules: they run as a per-observation transform between the adapter intake and the buffer write, while modules surface the buffered observations to the outside world. The catalogue contains one shipped processor, loaded the same way as a module — by YAML key under `processors:` in the host's `agent.config.yaml`. + +| Processor | YAML key | Purpose | +| --- | --- | --- | +| [Python agent processor](./agent-processor-python) | `python` | Runs a directory of Python (IronPython) scripts as per-observation transforms; supports rewriting, deriving, and filtering observations. | + +## Adapter modules — shipped + +These two modules ship under `adapter/Modules/MTConnect.NET-AdapterModule-*` and load into the standalone adapter application (`MTConnect.NET-Adapter` / `MTConnect.NET-Adapter-Application`). + +| Module | YAML key | Purpose | +| --- | --- | --- | +| [SHDR output](./shdr-output) | `shdr` | Hosts an SHDR-protocol server that an MTConnect agent's `shdr-adapter` module connects to. | +| [MQTT output](./mqtt-output) | `mqtt` | Publishes adapter input data to an MQTT broker that an MTConnect agent's `mqtt-adapter` module subscribes to. | + +## Reading a module page + +Each page has the same structure: + +- **Identifier** — the YAML key the host application matches against (set on the module's `ConfigurationTypeId` constant). +- **Purpose** — one paragraph stating what the module does and where it sits in the data path. +- **Configuration schema** — every property the module's configuration class exposes, with type, default, and permissible values. +- **Wire interaction** — a Mermaid sequence diagram showing how the module connects to the agent core and the external world. +- **Example configuration** — a complete YAML block you can drop into the host's config file. +- **Troubleshooting pointers** — links to the [Troubleshooting](/troubleshooting/) section for the failure modes specific to that module. +- **API reference** — links to the [API reference](/api/) for the module's configuration and runtime classes. + +## Combining modules + +Modules are independent — load none, load one, load several. A common deployment loads `http-server` plus `mqtt-relay` plus `shdr-adapter` so the agent serves REST, publishes to an external broker, and ingests from an SHDR-protocol source in the same process. The host invokes each module's start hook in declaration order and stops them in reverse order on shutdown. diff --git a/docs/modules/mqtt-adapter.md b/docs/modules/mqtt-adapter.md new file mode 100644 index 000000000..49fcfd692 --- /dev/null +++ b/docs/modules/mqtt-adapter.md @@ -0,0 +1,113 @@ +# MQTT adapter + +- **Module name** — MTConnect MQTT Adapter agent module +- **Identifier** — `mqtt-adapter` +- **NuGet package** — `MTConnect.NET-AgentModule-MqttAdapter` +- **Source path** — `agent/Modules/MTConnect.NET-AgentModule-MqttAdapter/` + +## Purpose + +Subscribes to an external MQTT broker and feeds the received observations, assets, and device payloads into the agent. This is the agent-side counterpart to the [MQTT output adapter module](./mqtt-output) — together they form an MQTT-mediated bridge between a remote adapter and the agent. + +::: warning Module status +This module is under development and may be deprecated in a future release. Please file feedback or issues on the public GitHub tracker. +::: + +## Configuration schema + +The module's configuration class is `MqttAdapterModuleConfiguration`. The keys below describe the YAML map under `mqtt-adapter:`. + +| Key | Type | Default | Permissible values | Notes | +| --- | --- | --- | --- | --- | +| `server` | string | `localhost` | hostname, IP, or fully qualified domain name | The hostname of the MQTT broker to subscribe to. | +| `port` | int | `1883` | 1-65535 | The broker's MQTT port. | +| `timeout` | int | `5000` | milliseconds | Connection and read / write timeout. | +| `reconnectInterval` | int | `10000` | milliseconds | Delay between reconnect attempts after a disconnect. | +| `username` | string | `null` | any | Username for username + password authentication. | +| `password` | string | `null` | any | Password for username + password authentication. | +| `clientId` | string | `null` (auto-generated) | any MQTT client-id string | Client identifier presented to the broker. | +| `cleanSession` | bool | `true` | `true`, `false` | Sets the MQTT clean-session flag. | +| `qos` | int | `1` | `0` (at-most-once), `1` (at-least-once), `2` (exactly-once) | The QoS level requested on subscriptions. | +| `useTls` | bool | `false` | `true`, `false` | Switches the connection to TLS (mqtts). | +| `certificateAuthority` | string | `null` | filesystem path | Path to the CA certificate file. | +| `pemCertificate` | string | `null` | filesystem path | Path to the PEM client-certificate file. | +| `pemPrivateKey` | string | `null` | filesystem path | Path to the PEM private-key file. | +| `allowUntrustedCertificates` | bool | `false` | `true`, `false` | Disables certificate-chain verification (development only). | +| `topicPrefix` | string | `null` | any MQTT-valid topic prefix | The topic prefix the module subscribes to. | +| `deviceKey` | string | `null` | device name or UUID | Identifies which Device in `Devices.xml` the incoming payloads target. | +| `documentFormat` | string | `json` | `XML`, `JSON`, `JSON-cppAgent` | The document format the broker payloads are encoded in. | + +### Subscribed topics + +With `topicPrefix: input`, the module subscribes to: + +- `input/observations` — observation payloads. +- `input/assets` — asset payloads. +- `input/device` — device-model payloads. + +## Wire interaction + +```mermaid +sequenceDiagram + autonumber + participant Remote as Remote producer + participant Broker as External MQTT broker + participant Adapter as mqtt-adapter module + participant Agent as MTConnect agent core + participant Buffer as Sequence buffer + + Adapter->>Broker: CONNECT (client-id, optional TLS handshake) + Broker-->>Adapter: CONNACK + Adapter->>Broker: SUBSCRIBE /observations + Adapter->>Broker: SUBSCRIBE /assets + Adapter->>Broker: SUBSCRIBE /device + Broker-->>Adapter: SUBACK + Remote->>Broker: PUBLISH /observations + Broker-->>Adapter: PUBLISH /observations + Adapter->>Agent: AddObservations(deviceKey, ...) + Agent->>Buffer: append to sequence buffer + Remote->>Broker: PUBLISH /assets + Broker-->>Adapter: PUBLISH /assets + Adapter->>Agent: AddAsset(deviceKey, ...) +``` + +## Example configuration + +```yaml +modules: + - mqtt-adapter: + server: broker.example.com + port: 1883 + topicPrefix: input + deviceKey: M12346 + qos: 1 + cleanSession: true + reconnectInterval: 10000 + documentFormat: json +``` + +For a TLS-secured broker with mutual TLS: + +```yaml +modules: + - mqtt-adapter: + server: broker.example.com + port: 8883 + useTls: true + certificateAuthority: /etc/mtconnect/certs/rootCA.pem + pemCertificate: /etc/mtconnect/certs/agent.pem + pemPrivateKey: /etc/mtconnect/certs/agent.key + topicPrefix: input + deviceKey: M12346 +``` + +## Troubleshooting + +- **MQTT TLS handshake failures** — see [MQTT TLS handshake failures](/troubleshooting/#mqtt-tls-handshake-failures). +- **`deviceKey` mismatch** — the value must match a `Device@name` or `Device@uuid` in the agent's `Devices.xml`. A mismatch causes the agent to drop the inbound observations silently; verify with the `/probe` endpoint that the device is present. +- **Payload-format mismatch** — `documentFormat` must match the encoding the remote producer publishes. The remote can be the [MQTT output adapter module](./mqtt-output), which publishes JSON. + +## API reference + +- [`MqttAdapterModuleConfiguration`](/api/) — the module's configuration class. +- [`MqttClientConfiguration`](/api/) — the base MQTT client configuration shape. diff --git a/docs/modules/mqtt-broker.md b/docs/modules/mqtt-broker.md new file mode 100644 index 000000000..f1c935315 --- /dev/null +++ b/docs/modules/mqtt-broker.md @@ -0,0 +1,116 @@ +# MQTT broker + +- **Module name** — MTConnect MQTT Broker agent module +- **Identifier** — `mqtt-broker` +- **NuGet package** — `MTConnect.NET-AgentModule-MqttBroker` +- **Source path** — `agent/Modules/MTConnect.NET-AgentModule-MqttBroker/` + +## Purpose + +Hosts an **embedded** MQTT broker inside the agent process. The broker accepts subscriptions from consumers and publishes the agent's documents (Probe / Current / Sample / Asset) and entities (per-DataItem observations) on the topic tree rooted at `topicPrefix`. Use this module when consumers should connect directly to the agent over MQTT without a separate broker deployment; use the [MQTT relay](./mqtt-relay) module when the agent should publish to an external broker instead. + +## Configuration schema + +The module's configuration class is `MqttBrokerModuleConfiguration`. The keys below describe the YAML map under `mqtt-broker:`. + +| Key | Type | Default | Permissible values | Notes | +| --- | --- | --- | --- | --- | +| `server` | string | `null` (binds to all interfaces) | hostname or IP address | The hostname or IP address the embedded broker binds to. | +| `port` | int | `1883` | 1-65535 | The TCP port the embedded broker listens on. `8883` is conventional for TLS. | +| `tls` | map | `null` | see the [HTTP server's `tls` schema](./http-server#tls-schema) | TLS configuration; presence switches the listener to mqtts. | +| `timeout` | int | `5000` | milliseconds | The timeout applied to client connection and read / write operations. | +| `initialDelay` | int | `500` | milliseconds | Delay between module start and broker bind, giving the OS time to release the TCP port from a previous run. | +| `restartInterval` | int | `5000` | milliseconds | Delay between broker-start retries after a bind failure. | +| `qos` | int | `0` | `0` (at-most-once), `1` (at-least-once), `2` (exactly-once) | The QoS level the broker publishes at. | +| `topicPrefix` | string | `MTConnect` | any MQTT-valid topic prefix | Root of the topic tree the broker publishes on. | +| `topicStructure` | enum | `Document` | `Document`, `Entity` | Selects per-document publication (`Document`) or per-DataItem publication (`Entity`). | +| `documentFormat` | string | `json-cppagent` | `XML`, `JSON`, `JSON-cppAgent` | The document format used for the published payloads. | +| `indentOutput` | bool | `false` | `true`, `false` | Indents the payload for readability (raises bytes-on-wire). | +| `currentInterval` | int | `5000` | milliseconds | The interval at which Current envelopes are republished. | +| `sampleInterval` | int | `500` | milliseconds | The interval at which Sample envelopes are republished. | + +### Topic tree + +With `topicPrefix: MTConnect` and `topicStructure: Document`, the broker publishes on: + +- `MTConnect/Probe/` — the Probe envelope. +- `MTConnect/Current/` — the Current envelope, republished every `currentInterval` ms. +- `MTConnect/Sample/` — the Sample envelope, republished every `sampleInterval` ms. +- `MTConnect/Asset//` — per-asset payloads. + +With `topicStructure: Entity` the broker publishes per-DataItem on `MTConnect/Observations///` instead. + +## Wire interaction + +```mermaid +sequenceDiagram + autonumber + participant Consumer as MQTT consumer + participant Broker as mqtt-broker module + participant Agent as MTConnect agent core + participant Buffer as Sequence buffer + + Consumer->>Broker: CONNECT (client-id, optional TLS handshake) + Broker-->>Consumer: CONNACK + Consumer->>Broker: SUBSCRIBE MTConnect/Current/+ + Broker-->>Consumer: SUBACK + loop every currentInterval ms + Agent->>Buffer: GetObservations(at: latest) + Buffer-->>Agent: observation set + Agent->>Broker: publish Current envelope + Broker-->>Consumer: PUBLISH MTConnect/Current/ + end + loop every sampleInterval ms + Agent->>Buffer: GetObservations(from: lastSequence) + Buffer-->>Agent: observation page + Agent->>Broker: publish Sample envelope + Broker-->>Consumer: PUBLISH MTConnect/Sample/ + end +``` + +## Example configuration + +```yaml +modules: + - mqtt-broker: + server: 0.0.0.0 + port: 1883 + topicPrefix: MTConnect + topicStructure: Document + documentFormat: json-cppagent + indentOutput: false + qos: 1 + currentInterval: 5000 + sampleInterval: 500 + timeout: 5000 + initialDelay: 500 + restartInterval: 5000 +``` + +For TLS-secured broker access: + +```yaml +modules: + - mqtt-broker: + port: 8883 + topicPrefix: MTConnect + tls: + pem: + certificatePath: /etc/mtconnect/certs/broker.pem + privateKeyPath: /etc/mtconnect/certs/broker.key + certificateAuthority: /etc/mtconnect/certs/rootCA.pem + verifyClientCertificate: true +``` + +## Troubleshooting + +- **Bind failures** — the embedded broker shares the TCP port with no other process. If the port is already in use the module retries every `restartInterval` ms; raise `initialDelay` if a previous run's socket is in `TIME_WAIT`. +- **MQTT TLS handshake failures** — see [MQTT TLS handshake failures](/troubleshooting/#mqtt-tls-handshake-failures). +- **Document format selection** — `json-cppagent` is byte-for-byte cppagent-parity for v2 envelopes; `XML` is the wire format defined by the MTConnect REST protocol; `JSON` is the legacy v1 JSON shape. + +## API reference + +- [`MqttBrokerModuleConfiguration`](/api/) — the module's configuration class. +- [`MqttTopicStructure`](/api/) — the `Document` / `Entity` enum. +- [`IMTConnectMqttDocumentServerConfiguration`](/api/) — the configuration interface this module implements. +- [`TlsConfiguration`](/api/) — the TLS configuration schema. diff --git a/docs/modules/mqtt-output.md b/docs/modules/mqtt-output.md new file mode 100644 index 000000000..d7917ef00 --- /dev/null +++ b/docs/modules/mqtt-output.md @@ -0,0 +1,169 @@ +# MQTT output (adapter module) + +- **Module name** — MTConnect MQTT adapter module (adapter-side) +- **Identifier** — `mqtt` +- **NuGet package** — `MTConnect.NET-AdapterModule-MQTT` +- **Source path** — `adapter/Modules/MTConnect.NET-AdapterModule-MQTT/` + +## Purpose + +Publishes the adapter's observation values to an MQTT broker. An MTConnect agent's [`mqtt-adapter`](./mqtt-adapter) module subscribes to the same broker and forwards the observations into the agent. Use this transport when the adapter and the agent sit on opposite sides of a network boundary that does not allow direct TCP connections, or when a centralized broker already mediates the deployment's data movement. + +::: warning Module status +This module is under development and may be deprecated in a future release. Please file feedback or issues on the public GitHub tracker. +::: + +## Configuration schema + +The module's configuration class is `ModuleConfiguration` (under `MTConnect.Configurations` in the `MTConnect.NET-AdapterModule-MQTT` assembly). The keys below describe the YAML map under `mqtt:`. + +| Key | Type | Default | Permissible values | Notes | +| --- | --- | --- | --- | --- | +| `server` | string | `localhost` | hostname, IP, or fully qualified domain name | The MQTT broker's address. | +| `port` | int | `7878` | 1-65535 | The MQTT broker's port. `1883` for plaintext, `8883` for TLS — the default `7878` matches the SHDR convention rather than the MQTT convention and is typically overridden. | +| `username` | string | `null` | any | Username for username + password authentication. | +| `password` | string | `null` | any | Password for username + password authentication. | +| `clientId` | string | `null` (auto-generated) | any MQTT client-id string | Client identifier presented to the broker. | +| `qos` | int | `0` | `0` (at-most-once), `1` (at-least-once), `2` (exactly-once) | The QoS level used on every publish. | +| `useTls` | bool | `false` | `true`, `false` | Switches the connection to TLS (mqtts). | +| `certificateAuthority` | string | `null` | filesystem path | Path to the CA certificate. | +| `pemCertificate` | string | `null` | filesystem path | Path to the PEM client-certificate file. | +| `pemPrivateKey` | string | `null` | filesystem path | Path to the PEM private-key file. | +| `allowUntrustedCertificates` | bool | `false` | `true`, `false` | Disables certificate-chain verification (development only). | +| `connectionTimeout` | int | `5000` | milliseconds | Connection and read / write timeout. | +| `reconnectInterval` | int | `10000` | milliseconds | Delay between reconnect attempts after a disconnect. | +| `topic` | string | `null` | any MQTT-valid topic | Root topic the module publishes on; observation payloads land at `/Observations`. | +| `deviceKey` | string | `null` | device name or UUID | Identifies which Device the published observations target. | +| `documentFormat` | string | `json` | `XML`, `JSON`, `JSON-cppAgent` | The document format used for the published payloads. | + +## Payload shape + +Payloads are gzip-compressed and published on `/Observations`. The default JSON shape: + +```json +[ + { + "timestamp": "2024-05-13T23:15:01.7754921Z", + "observations": [ + { + "dataItemKey": "avail", + "values": { "result": "AVAILABLE" } + }, + { + "dataItemKey": "estop", + "values": { "result": "ARMED" } + }, + { + "dataItemKey": "system", + "values": { + "level": "WARNING", + "nativeCode": "404" + } + } + ] + } +] +``` + +DATA_SET and TABLE observations use the same shape with structured values: + +```json +{ + "dataItemKey": "vars", + "values": { + "DATASET[E100]": "12.123", + "DATASET[E101]": "6574" + } +} +``` + +```json +{ + "dataItemKey": "toolTable", + "values": { + "TABLE[T1][LENGTH]": "142.654", + "TABLE[T1][DIAMETER]": "12.496" + } +} +``` + +## Wire interaction + +```mermaid +sequenceDiagram + autonumber + participant Source as Adapter data source + participant Adapter as Adapter host + participant Module as mqtt output module + participant Broker as External MQTT broker + participant Agent as MTConnect agent (mqtt-adapter) + participant Buffer as Agent sequence buffer + + Module->>Broker: CONNECT (clientId, optional TLS) + Broker-->>Module: CONNACK + Agent->>Broker: SUBSCRIBE /Observations + Broker-->>Agent: SUBACK + Source-->>Adapter: data update + Adapter->>Module: emit observations batch + Module->>Module: gzip + encode payload + Module->>Broker: PUBLISH /Observations + Broker-->>Agent: PUBLISH /Observations + Agent->>Buffer: append to sequence buffer + Note over Module,Broker: network outage + Module-xBroker: DISCONNECT + loop every ms + Module->>Broker: CONNECT (retry) + end +``` + +## Example configuration + +```yaml +modules: + - mqtt: + server: broker.example.com + port: 1883 + topic: MTConnect/Input + deviceKey: M12346 + documentFormat: json +``` + +For TLS with username + password: + +```yaml +modules: + - mqtt: + server: broker.example.com + port: 8883 + useTls: true + username: adapter + password: changeme + topic: MTConnect/Input + deviceKey: M12346 +``` + +For mutual TLS (AWS IoT shape): + +```yaml +modules: + - mqtt: + server: a1b2c3d4-ats.iot.us-east-1.amazonaws.com + port: 8883 + certificateAuthority: certs/AmazonRootCA1.pem + pemCertificate: certs/adapter-certificate.pem.crt + pemPrivateKey: certs/adapter-private.pem.key + topic: MTConnect/Input + deviceKey: M12346 +``` + +## Troubleshooting + +- **MQTT TLS handshake failures** — see [MQTT TLS handshake failures](/troubleshooting/#mqtt-tls-handshake-failures). +- **Topic mismatch** — the adapter's `topic` and the agent's `mqtt-adapter` `topicPrefix` must align. Conventionally the agent subscribes to `` and the adapter publishes at `/Observations`; verify against the agent module's [subscribed topics](./mqtt-adapter#subscribed-topics) list. +- **Compression failures** — payloads are gzip-compressed; an agent that subscribes to the topic without gzip-decoding will see opaque binary. The agent's `mqtt-adapter` module handles gzip transparently. +- **Reconnect loops** indicate broker-side rejection (bad credentials, malformed client-id, IP not allow-listed); enable verbose adapter logging to surface the CONNACK reason code. + +## API reference + +- [`ModuleConfiguration`](/api/) — the adapter-side MQTT module configuration class (under `MTConnect.Configurations` in the `MTConnect.NET-AdapterModule-MQTT` assembly). +- [`MTConnectAdapterModule`](/api/) — the base class adapter modules derive from. diff --git a/docs/modules/mqtt-relay.md b/docs/modules/mqtt-relay.md new file mode 100644 index 000000000..f74714ddc --- /dev/null +++ b/docs/modules/mqtt-relay.md @@ -0,0 +1,136 @@ +# MQTT relay + +- **Module name** — MTConnect MQTT Relay agent module +- **Identifier** — `mqtt-relay` +- **NuGet package** — `MTConnect.NET-AgentModule-MqttRelay` +- **Source path** — `agent/Modules/MTConnect.NET-AgentModule-MqttRelay/` + +## Purpose + +Publishes the agent's documents (Probe / Current / Sample / Asset) to an **external** MQTT broker. Use this module when consumers should connect to a centralized broker (AWS IoT, HiveMQ, Mosquitto, etc.) rather than directly to the agent process. The module connects to the broker as an MQTT client, reconnects on disconnect, and (optionally) persists unsent observations to disk so a network outage does not drop history. + +## Configuration schema + +The module's configuration class is `MqttRelayModuleConfiguration`. The keys below describe the YAML map under `mqtt-relay:`. + +| Key | Type | Default | Permissible values | Notes | +| --- | --- | --- | --- | --- | +| `server` | string | `localhost` | hostname, IP, or fully qualified domain name | The hostname of the external MQTT broker. | +| `port` | int | `1883` | 1-65535 | The broker's MQTT port. `8883` is conventional for TLS. | +| `timeout` | int | `5000` | milliseconds | Connection and read / write timeout. | +| `reconnectInterval` | int | `10000` | milliseconds | Delay between reconnect attempts after a disconnect. | +| `username` | string | `null` | any | Username for username + password authentication. | +| `password` | string | `null` | any | Password for username + password authentication. | +| `useTls` | bool | `false` | `true`, `false` | Switches the connection to TLS (mqtts). | +| `clientId` | string | `null` (auto-generated) | any MQTT client-id string | Client identifier presented to the broker. | +| `cleanSession` | bool | `false` | `true`, `false` | Sets the MQTT clean-session flag. | +| `qos` | int | `0` | `0` (at-most-once), `1` (at-least-once), `2` (exactly-once) | The QoS level used on every publish. | +| `tls` | map | `null` | see the [HTTP server's `tls` schema](./http-server#tls-schema) | TLS settings (client certificate, CA chain, mutual-TLS toggle). | +| `topicPrefix` | string | `MTConnect` | any MQTT-valid topic prefix | Root of the topic tree the module publishes on. | +| `topicStructure` | enum | `Document` | `Document`, `Entity` | Selects per-document publication or per-DataItem publication. | +| `documentFormat` | string | `json-cppAgent` | `XML`, `JSON`, `JSON-cppAgent` | The document format used for the published payloads. | +| `indentOutput` | bool | `false` | `true`, `false` | Indents the payload for readability. | +| `currentInterval` | int | `5000` | milliseconds | The interval at which Current envelopes are republished. | +| `sampleInterval` | int | `500` | milliseconds | The interval at which Sample envelopes are republished. | +| `durableRelay` | bool | `false` | `true`, `false` | When `true`, the module persists unsent observations to disk and replays them after a reconnect, so observations from a broker outage are not lost. | + +## Wire interaction + +```mermaid +sequenceDiagram + autonumber + participant Agent as MTConnect agent core + participant Relay as mqtt-relay module + participant Disk as Durable spool (optional) + participant Broker as External MQTT broker + participant Consumer as MQTT consumer + + Relay->>Broker: CONNECT (client-id, optional TLS handshake) + Broker-->>Relay: CONNACK + Consumer->>Broker: SUBSCRIBE MTConnect/Current/+ + loop every currentInterval ms + Agent->>Relay: emit Current envelope + alt durableRelay = true + Relay->>Disk: persist payload + end + Relay->>Broker: PUBLISH MTConnect/Current/ + Broker-->>Consumer: PUBLISH MTConnect/Current/ + end + Note over Relay,Broker: network outage + Relay-xBroker: DISCONNECT + loop every reconnectInterval ms + Relay->>Broker: CONNECT (retry) + end + Broker-->>Relay: CONNACK + alt durableRelay = true + Relay->>Disk: read spooled payloads + Disk-->>Relay: backlog + Relay->>Broker: PUBLISH backlog + end +``` + +## Example configuration + +```yaml +modules: + - mqtt-relay: + server: broker.example.com + port: 1883 + topicPrefix: enterprise/site/area/line/cell/MTConnect + topicStructure: Document + documentFormat: json-cppagent + currentInterval: 5000 + sampleInterval: 500 + reconnectInterval: 10000 + qos: 1 + durableRelay: true +``` + +For AWS IoT (mutual-TLS over port 8883): + +```yaml +modules: + - mqtt-relay: + server: a1b2c3d4e5f6g7-ats.iot.us-east-1.amazonaws.com + port: 8883 + clientId: mtconnect-agent-01 + tls: + pem: + certificateAuthority: certs/AmazonRootCA1.pem + certificatePath: certs/agent-certificate.pem.crt + privateKeyPath: certs/agent-private.pem.key + documentFormat: json-cppagent + currentInterval: 5000 + sampleInterval: 500 + topicPrefix: enterprise/site/area/line/cell/MTConnect +``` + +For HiveMQ Cloud (username + password over TLS): + +```yaml +modules: + - mqtt-relay: + server: a1b2c3d4e5f6.s1.eu.hivemq.cloud + port: 8883 + username: mtconnect + password: changeme + useTls: true + documentFormat: json-cppagent + currentInterval: 5000 + sampleInterval: 500 + topicPrefix: enterprise/site/area/line/cell/MTConnect +``` + +## Troubleshooting + +- **MQTT TLS handshake failures** — see [MQTT TLS handshake failures](/troubleshooting/#mqtt-tls-handshake-failures). The most common cause is a CA path that the agent cannot read or that does not chain to the broker's certificate. +- **Reconnect loops** — when the broker rejects the connection (bad credentials, malformed client-id, IP not allow-listed), the module retries every `reconnectInterval` ms. Lower the interval during diagnostic runs so the error appears more frequently in the log. +- **`durableRelay` backlog growth** — disk usage scales with the broker outage window. Monitor the spool directory and provision enough disk for the longest expected outage. +- **AWS IoT-specific** integration walkthroughs live under [Configure & Use / Integrations](/configure/). + +## API reference + +- [`MqttRelayModuleConfiguration`](/api/) — the module's configuration class. +- [`MqttTopicStructure`](/api/) — the `Document` / `Entity` enum. +- [`IMTConnectMqttDocumentServerConfiguration`](/api/) — the configuration interface this module implements. +- [`TlsConfiguration`](/api/) — the TLS configuration schema. diff --git a/docs/modules/shdr-adapter.md b/docs/modules/shdr-adapter.md new file mode 100644 index 000000000..73ce79208 --- /dev/null +++ b/docs/modules/shdr-adapter.md @@ -0,0 +1,117 @@ +# SHDR adapter + +- **Module name** — MTConnect SHDR Adapter agent module +- **Identifier** — `shdr-adapter` +- **NuGet package** — `MTConnect.NET-AgentModule-ShdrAdapter` +- **Source path** — `agent/Modules/MTConnect.NET-AgentModule-ShdrAdapter/` + +## Purpose + +Opens a TCP connection to an SHDR-protocol adapter (typically a piece of equipment exposing the SHDR protocol over a port) and feeds the received observations into the agent. SHDR is the original MTConnect ingestion protocol — line-oriented, pipe-delimited, optimized for streaming small observations from a PLC. This module is the most common adapter-side ingestion path in MTConnect deployments. + +## Configuration schema + +The module's configuration class is `ShdrAdapterModuleConfiguration` (it derives from `ShdrAdapterClientConfiguration`, which derives from `ShdrClientConfiguration`). The keys below describe the YAML map under `shdr-adapter:`. + +| Key | Type | Default | Permissible values | Notes | +| --- | --- | --- | --- | --- | +| `deviceKey` | string | `null` | device name or UUID | Matches the `Device@name` or `Device@uuid` in `Devices.xml` the inbound observations target. | +| `hostname` | string | `localhost` | hostname or IP address | The remote SHDR adapter's address. | +| `port` | int | `7878` | 1-65535 | The remote SHDR adapter's TCP port. | +| `heartbeat` | int | `10000` | milliseconds | Interval at which the module sends `* PING` keep-alive frames. | +| `connectionTimeout` | int | `5000` | milliseconds | Silence threshold (for legacy adapters that do not support heartbeats) before disconnect. Ignored when heartbeats are present. | +| `reconnectInterval` | int | `10000` | milliseconds | Delay between reconnect attempts after a disconnect. | +| `allowShdrDevice` | bool | `false` | `true`, `false` | When `true`, a `* device` frame from the adapter is accepted as a device-model update. | +| `availableOnConnection` | bool | `false` | `true`, `false` | For devices that do not emit their own availability event, setting this `true` sets `Availability = AVAILABLE` when the TCP connection comes up. | +| `convertUnits` | bool | `true` | `true`, `false` | Whether the agent converts the adapter's values to the DataItem's declared units. Set `false` if the adapter has already converted. | +| `ignoreObservationCase` | bool | `true` | `true`, `false` | Whether the agent ignores case when matching incoming string observations against the DataItem's enumerated values. | +| `ignoreTimestamps` | bool | `false` | `true`, `false` | When `true`, the agent stamps the observation with its own clock instead of trusting the adapter's timestamp. Corrects adapter clock drift at the cost of network-latency error. | +| `outputConnectionInformation` | bool | `true` | `true`, `false` | Emits the adapter's host / port as an observation. | +| `ignoreHeartbeatOnChange` | bool | `true` | `true`, `false` | When `true`, the heartbeat `PING` is suppressed if any data has been received within the heartbeat window. | + +## Wire interaction + +```mermaid +sequenceDiagram + autonumber + participant SHDR as Remote SHDR adapter + participant Module as shdr-adapter module + participant Agent as MTConnect agent core + participant Buffer as Sequence buffer + + Module->>SHDR: TCP connect : + SHDR-->>Module: connection accepted + opt availableOnConnection = true + Module->>Agent: AddObservation(avail, AVAILABLE) + end + loop heartbeat every ms + Module->>SHDR: * PING + SHDR-->>Module: * PONG + end + SHDR-->>Module: 2024-05-13T12:00:00Z|avail|AVAILABLE + Module->>Agent: AddObservation(deviceKey, avail, AVAILABLE) + Agent->>Buffer: append to sequence buffer + SHDR-->>Module: 2024-05-13T12:00:01Z|estop|ARMED + Module->>Agent: AddObservation(deviceKey, estop, ARMED) + Note over Module,SHDR: connection drop + Module-xSHDR: disconnected + loop every ms + Module->>SHDR: TCP connect : + end +``` + +## Example configuration + +```yaml +modules: + - shdr-adapter: + deviceKey: M12346 + hostname: 192.168.1.50 + port: 7878 + heartbeat: 10000 + reconnectInterval: 10000 + availableOnConnection: true + ignoreTimestamps: false + convertUnits: true +``` + +For a legacy SHDR adapter that does not respond to `PING`: + +```yaml +modules: + - shdr-adapter: + deviceKey: M12346 + hostname: 192.168.1.50 + port: 7878 + connectionTimeout: 5000 + ignoreHeartbeatOnChange: false + heartbeat: 0 +``` + +For multiple adapters, declare the module several times — each entry connects to a different remote adapter: + +```yaml +modules: + - shdr-adapter: + deviceKey: M12346 + hostname: 192.168.1.50 + port: 7878 + - shdr-adapter: + deviceKey: M67890 + hostname: 192.168.1.51 + port: 7878 +``` + +## Troubleshooting + +- **Empty `name` attributes on probe DataItems** — see [Empty `name` attributes on probe DataItems](/troubleshooting/#empty-name-attributes-on-probe-dataitems). The SHDR protocol does not transmit DataItem metadata; the `name` attribute must exist in the agent's `Devices.xml`. +- **Asset count emitted as a scalar EVENT instead of DATA_SET** — see [Asset count emitted as scalar](/troubleshooting/#asset-count-emitted-as-a-scalar-event-instead-of-a-data_set). +- **Clock drift** — set `ignoreTimestamps: true` if the adapter's system clock cannot be kept in sync. +- **Heartbeat tuning** — set `heartbeat: 0` to disable heartbeats entirely and rely on `connectionTimeout` only. This is rarely the right choice but is required for adapters that mis-handle `PING`. +- **`deviceKey` mismatch** drops observations silently; verify against `/probe` output before declaring the deployment working. + +## API reference + +- [`ShdrAdapterModuleConfiguration`](/api/) — the module's configuration class. +- [`ShdrAdapterClientConfiguration`](/api/) — the base SHDR adapter-client configuration shape. +- [`ShdrClientConfiguration`](/api/) — the SHDR client configuration shape. diff --git a/docs/modules/shdr-output.md b/docs/modules/shdr-output.md new file mode 100644 index 000000000..9f26988ba --- /dev/null +++ b/docs/modules/shdr-output.md @@ -0,0 +1,94 @@ +# SHDR output (adapter module) + +- **Module name** — MTConnect SHDR adapter module (adapter-side) +- **Identifier** — `shdr` +- **NuGet package** — `MTConnect.NET-AdapterModule-SHDR` +- **Source path** — `adapter/Modules/MTConnect.NET-AdapterModule-SHDR/` + +## Purpose + +Hosts an SHDR-protocol TCP server on the adapter host. The adapter publishes observation values it has read from its data source (PLC, CNC, sensor, simulator, etc.) to this server; an MTConnect agent's [`shdr-adapter`](./shdr-adapter) module connects to it and forwards the observations into the agent. This is the canonical adapter-to-agent transport in MTConnect deployments — line-oriented, pipe-delimited, low-latency. + +## Configuration schema + +The module's configuration class is `ModuleConfiguration` (under `MTConnect.Configurations` in the `MTConnect.NET-AdapterModule-SHDR` assembly). The keys below describe the YAML map under `shdr:`. + +| Key | Type | Default | Permissible values | Notes | +| --- | --- | --- | --- | --- | +| `hostname` | string | `localhost` | hostname or IP address | The address the SHDR server binds to. `localhost` accepts loopback only; set to `0.0.0.0` to accept from any interface. | +| `port` | int | `7878` | 1-65535 | The TCP port the SHDR server listens on. `7878` is the conventional MTConnect SHDR port. | +| `heartbeat` | int | `10000` | milliseconds | The heartbeat interval advertised in the server's `* PONG` response. | +| `connectionTimeout` | int | `5000` | milliseconds | Silence threshold (for legacy clients that do not heartbeat) before disconnecting the client. Ignored when the client heartbeats. | +| `reconnectInterval` | int | `10000` | milliseconds | Delay between adapter-source reconnection attempts. | +| `timeZoneOutput` | string | `Z` | IANA TZ identifier or fixed offset (`Z`, `+05:30`, etc.) | The time-zone identifier appended to outbound timestamps. `Z` is UTC. | +| `deviceKey` | string | (none) | device name or UUID | Identifies which Device the observations target. Required for the agent's `shdr-adapter` to bind incoming observations. | + +::: tip Adapter-host vs module config +The `shdr` module is loaded by the adapter host's `adapter.config.yaml`. Some adapter-host implementations expose a top-level `deviceKey` rather than a per-module one — check the adapter-host's documentation for whether the key sits on the module entry or on the surrounding `adapter:` block. +::: + +## Wire interaction + +```mermaid +sequenceDiagram + autonumber + participant Source as Adapter data source + participant Adapter as Adapter host + participant Module as shdr output module + participant Agent as MTConnect agent (shdr-adapter module) + participant Buffer as Agent sequence buffer + + Module->>Module: TCP listen : + Agent->>Module: TCP connect : + Module-->>Agent: connection accepted + Source-->>Adapter: data update (avail = AVAILABLE) + Adapter->>Module: emit avail|AVAILABLE + Module-->>Agent: 2024-05-13T12:00:00Z|avail|AVAILABLE + Agent->>Buffer: append to sequence buffer + loop heartbeat + Agent->>Module: * PING + Module-->>Agent: * PONG 10000 + end + Note over Adapter,Module: data source reconnect + Source-xAdapter: source disconnected + loop every ms + Adapter->>Source: reconnect + end +``` + +## Example configuration + +```yaml +modules: + - shdr: + hostname: 0.0.0.0 + port: 7878 + heartbeat: 10000 + connectionTimeout: 5000 + reconnectInterval: 10000 + timeZoneOutput: Z +``` + +For multiple SHDR endpoints on a single adapter host, declare the module several times — each entry binds a different port: + +```yaml +modules: + - shdr: + port: 7878 + deviceKey: M12346 + - shdr: + port: 7879 + deviceKey: M67890 +``` + +## Troubleshooting + +- **Port already in use** — pick a different `port`. The MTConnect SHDR spec does not mandate `7878`; conventionally many CNC adapters use it. +- **Agent shows the device as `UNAVAILABLE`** — the adapter-side module must be connected to a data source, and the data source must publish an `avail` observation (or set `availableOnConnection: true` on the agent's `shdr-adapter` to default to `AVAILABLE` whenever the TCP connection is up). +- **Time-zone offset mismatch** — the `timeZoneOutput` of the adapter and the timestamp parsing in the agent must agree. `Z` (UTC) is the safest default. +- **Asset count emitted as scalar EVENT** — see [Asset count emitted as scalar](/troubleshooting/#asset-count-emitted-as-a-scalar-event-instead-of-a-data_set); the adapter must emit asset counts as `DATA_SET` observations. + +## API reference + +- [`ModuleConfiguration`](/api/) — the adapter-side SHDR module configuration class (under `MTConnect.Configurations` in the `MTConnect.NET-AdapterModule-SHDR` assembly). +- [`MTConnectAdapterModule`](/api/) — the base class adapter modules derive from. diff --git a/docs/package-lock.json b/docs/package-lock.json new file mode 100644 index 000000000..b6b56c424 --- /dev/null +++ b/docs/package-lock.json @@ -0,0 +1,3632 @@ +{ + "name": "mtconnect.net-docs", + "version": "0.1.0", + "lockfileVersion": 3, + "requires": true, + "packages": { + "": { + "name": "mtconnect.net-docs", + "version": "0.1.0", + "devDependencies": { + "mermaid": "^11.0.0", + "vitepress": "^1.5.0", + "vitepress-plugin-mermaid": "^2.0.17" + } + }, + "node_modules/@algolia/abtesting": { + "version": "1.18.0", + "resolved": "https://registry.npmjs.org/@algolia/abtesting/-/abtesting-1.18.0.tgz", + "integrity": "sha512-8siuLG+FIns1AjZ/g2SDVwHz9S+ObacDQISEJvS8XsNei1zl3FXqfqQrBpmrG7ACWCyesXHbicMJtvRbg00FEw==", + "dev": true, + "dependencies": { + "@algolia/client-common": "5.52.0", + "@algolia/requester-browser-xhr": "5.52.0", + "@algolia/requester-fetch": "5.52.0", + "@algolia/requester-node-http": "5.52.0" + }, + "engines": { + "node": ">= 14.0.0" + } + }, + "node_modules/@algolia/autocomplete-core": { + "version": "1.17.7", + "resolved": "https://registry.npmjs.org/@algolia/autocomplete-core/-/autocomplete-core-1.17.7.tgz", + "integrity": "sha512-BjiPOW6ks90UKl7TwMv7oNQMnzU+t/wk9mgIDi6b1tXpUek7MW0lbNOUHpvam9pe3lVCf4xPFT+lK7s+e+fs7Q==", + "dev": true, + "dependencies": { + "@algolia/autocomplete-plugin-algolia-insights": "1.17.7", + "@algolia/autocomplete-shared": "1.17.7" + } + }, + "node_modules/@algolia/autocomplete-plugin-algolia-insights": { + "version": "1.17.7", + "resolved": "https://registry.npmjs.org/@algolia/autocomplete-plugin-algolia-insights/-/autocomplete-plugin-algolia-insights-1.17.7.tgz", + "integrity": "sha512-Jca5Ude6yUOuyzjnz57og7Et3aXjbwCSDf/8onLHSQgw1qW3ALl9mrMWaXb5FmPVkV3EtkD2F/+NkT6VHyPu9A==", + "dev": true, + "dependencies": { + "@algolia/autocomplete-shared": "1.17.7" + }, + "peerDependencies": { + "search-insights": ">= 1 < 3" + } + }, + "node_modules/@algolia/autocomplete-preset-algolia": { + "version": "1.17.7", + "resolved": "https://registry.npmjs.org/@algolia/autocomplete-preset-algolia/-/autocomplete-preset-algolia-1.17.7.tgz", + "integrity": "sha512-ggOQ950+nwbWROq2MOCIL71RE0DdQZsceqrg32UqnhDz8FlO9rL8ONHNsI2R1MH0tkgVIDKI/D0sMiUchsFdWA==", + "dev": true, + "dependencies": { + "@algolia/autocomplete-shared": "1.17.7" + }, + "peerDependencies": { + "@algolia/client-search": ">= 4.9.1 < 6", + "algoliasearch": ">= 4.9.1 < 6" + } + }, + "node_modules/@algolia/autocomplete-shared": { + "version": "1.17.7", + "resolved": "https://registry.npmjs.org/@algolia/autocomplete-shared/-/autocomplete-shared-1.17.7.tgz", + "integrity": "sha512-o/1Vurr42U/qskRSuhBH+VKxMvkkUVTLU6WZQr+L5lGZZLYWyhdzWjW0iGXY7EkwRTjBqvN2EsR81yCTGV/kmg==", + "dev": true, + "peerDependencies": { + "@algolia/client-search": ">= 4.9.1 < 6", + "algoliasearch": ">= 4.9.1 < 6" + } + }, + "node_modules/@algolia/client-abtesting": { + "version": "5.52.0", + "resolved": "https://registry.npmjs.org/@algolia/client-abtesting/-/client-abtesting-5.52.0.tgz", + "integrity": "sha512-wtwPgyPmO7b7sQPVgoK29c1VpfS08DnnJCmxX/oU1pV2DlMRJCzQcLN7JSloYpodyKHwM8+9wOzlAM0co3TDmA==", + "dev": true, + "dependencies": { + "@algolia/client-common": "5.52.0", + "@algolia/requester-browser-xhr": "5.52.0", + "@algolia/requester-fetch": "5.52.0", + "@algolia/requester-node-http": "5.52.0" + }, + "engines": { + "node": ">= 14.0.0" + } + }, + "node_modules/@algolia/client-analytics": { + "version": "5.52.0", + "resolved": "https://registry.npmjs.org/@algolia/client-analytics/-/client-analytics-5.52.0.tgz", + "integrity": "sha512-9KY36bRl4AH7RjqSeDDOKnjsz4IxQFBEOB8/fWmEbdQe+Isbs5jGzVJu9NEPQ1Tgwxlf8Uf07Swj3jZyMNUZ2g==", + "dev": true, + "dependencies": { + "@algolia/client-common": "5.52.0", + "@algolia/requester-browser-xhr": "5.52.0", + "@algolia/requester-fetch": "5.52.0", + "@algolia/requester-node-http": "5.52.0" + }, + "engines": { + "node": ">= 14.0.0" + } + }, + "node_modules/@algolia/client-common": { + "version": "5.52.0", + "resolved": "https://registry.npmjs.org/@algolia/client-common/-/client-common-5.52.0.tgz", + "integrity": "sha512-3a/qM3dzJqqfTx7Yrw7uGQ98I3Q0rDfb4Vkv0wEzko96l7YQMxfBVz/VbLq2N+c59GweYv6Vhp8mPeqnWJSITw==", + "dev": true, + "engines": { + "node": ">= 14.0.0" + } + }, + "node_modules/@algolia/client-insights": { + "version": "5.52.0", + "resolved": "https://registry.npmjs.org/@algolia/client-insights/-/client-insights-5.52.0.tgz", + "integrity": "sha512-Rki7ACbMcvbQW0BuM84x9dkGHY47ABmv4jU6tYssat2k02p3mIUms2YOLUAMeknhmnFsj6lb6ZzOXdMWMyc1sA==", + "dev": true, + "dependencies": { + "@algolia/client-common": "5.52.0", + "@algolia/requester-browser-xhr": "5.52.0", + "@algolia/requester-fetch": "5.52.0", + "@algolia/requester-node-http": "5.52.0" + }, + "engines": { + "node": ">= 14.0.0" + } + }, + "node_modules/@algolia/client-personalization": { + "version": "5.52.0", + "resolved": "https://registry.npmjs.org/@algolia/client-personalization/-/client-personalization-5.52.0.tgz", + "integrity": "sha512-96s4Uzc3kk+/f4jJXIVVGWP5XlngOGNQ1x6hW9AT59pOixHlOs5tqJg+ZUS/GQ6h/iYP0ceQcmxDQeLyCLTaDQ==", + "dev": true, + "dependencies": { + "@algolia/client-common": "5.52.0", + "@algolia/requester-browser-xhr": "5.52.0", + "@algolia/requester-fetch": "5.52.0", + "@algolia/requester-node-http": "5.52.0" + }, + "engines": { + "node": ">= 14.0.0" + } + }, + "node_modules/@algolia/client-query-suggestions": { + "version": "5.52.0", + "resolved": "https://registry.npmjs.org/@algolia/client-query-suggestions/-/client-query-suggestions-5.52.0.tgz", + "integrity": "sha512-lqeycNpSPe5Qa0OUWpejVvYQjQWV5nQuLT0a4aq7XzRAvCxprV/6Lf841EygdD2nrFnuS58ok7Au1uOtXzpnkg==", + "dev": true, + "dependencies": { + "@algolia/client-common": "5.52.0", + "@algolia/requester-browser-xhr": "5.52.0", + "@algolia/requester-fetch": "5.52.0", + "@algolia/requester-node-http": "5.52.0" + }, + "engines": { + "node": ">= 14.0.0" + } + }, + "node_modules/@algolia/client-search": { + "version": "5.52.0", + "resolved": "https://registry.npmjs.org/@algolia/client-search/-/client-search-5.52.0.tgz", + "integrity": "sha512-ly1wETVGRo30cx61O7fetESN+ElL9c9K+bD/AVgnT1ar4c6v+/Yqjrhdtu6Fm4D0s4NZP081Isf6tunH1wUXHg==", + "dev": true, + "dependencies": { + "@algolia/client-common": "5.52.0", + "@algolia/requester-browser-xhr": "5.52.0", + "@algolia/requester-fetch": "5.52.0", + "@algolia/requester-node-http": "5.52.0" + }, + "engines": { + "node": ">= 14.0.0" + } + }, + "node_modules/@algolia/ingestion": { + "version": "1.52.0", + "resolved": "https://registry.npmjs.org/@algolia/ingestion/-/ingestion-1.52.0.tgz", + "integrity": "sha512-U4EeTvgmluRjj39ykZSAd5X+a6LD5m7/mcOWDmB7hqm1R6QY0yT8jLxpNVEjYhzgEN5hcDGW6X67EWQY8KiYGQ==", + "dev": true, + "dependencies": { + "@algolia/client-common": "5.52.0", + "@algolia/requester-browser-xhr": "5.52.0", + "@algolia/requester-fetch": "5.52.0", + "@algolia/requester-node-http": "5.52.0" + }, + "engines": { + "node": ">= 14.0.0" + } + }, + "node_modules/@algolia/monitoring": { + "version": "1.52.0", + "resolved": "https://registry.npmjs.org/@algolia/monitoring/-/monitoring-1.52.0.tgz", + "integrity": "sha512-FCPnDcILfpTE94u7BVlV4DmnSV5wE3+j25EEF+3dYPrVzkVCSoAHs318oWDGxnxsAgiL4HpL12Jc4XHmw9shpA==", + "dev": true, + "dependencies": { + "@algolia/client-common": "5.52.0", + "@algolia/requester-browser-xhr": "5.52.0", + "@algolia/requester-fetch": "5.52.0", + "@algolia/requester-node-http": "5.52.0" + }, + "engines": { + "node": ">= 14.0.0" + } + }, + "node_modules/@algolia/recommend": { + "version": "5.52.0", + "resolved": "https://registry.npmjs.org/@algolia/recommend/-/recommend-5.52.0.tgz", + "integrity": "sha512-br3DO7n4N8CXwTRbZS0MnB4WQ9YHfNjCwkCEzVR/wek/qNTDQKDb0nROmkFaNZ8ucUqUVKZi074dbwMwRDlK8Q==", + "dev": true, + "dependencies": { + "@algolia/client-common": "5.52.0", + "@algolia/requester-browser-xhr": "5.52.0", + "@algolia/requester-fetch": "5.52.0", + "@algolia/requester-node-http": "5.52.0" + }, + "engines": { + "node": ">= 14.0.0" + } + }, + "node_modules/@algolia/requester-browser-xhr": { + "version": "5.52.0", + "resolved": "https://registry.npmjs.org/@algolia/requester-browser-xhr/-/requester-browser-xhr-5.52.0.tgz", + "integrity": "sha512-b0T/Ca2c9KyEslKsVrGZvbe1UrrKKSdfXhBZ2pbpKahFUzJfziRZ0urbOm7V65O0tO/jwU+Lo/+bIiiyhzGt8w==", + "dev": true, + "dependencies": { + "@algolia/client-common": "5.52.0" + }, + "engines": { + "node": ">= 14.0.0" + } + }, + "node_modules/@algolia/requester-fetch": { + "version": "5.52.0", + "resolved": "https://registry.npmjs.org/@algolia/requester-fetch/-/requester-fetch-5.52.0.tgz", + "integrity": "sha512-ozBT8J/mtD4H4IAojw8QPirlcL2gHrI1BGuZ4/ZXXO/rTE1yQ4VIPJj4mTTbwo4FbkS1MoJsD/DsrqLzhnc4/g==", + "dev": true, + "dependencies": { + "@algolia/client-common": "5.52.0" + }, + "engines": { + "node": ">= 14.0.0" + } + }, + "node_modules/@algolia/requester-node-http": { + "version": "5.52.0", + "resolved": "https://registry.npmjs.org/@algolia/requester-node-http/-/requester-node-http-5.52.0.tgz", + "integrity": "sha512-gyyWcLD22tnabmoit4iukCXuoRc5HYJuUjPSEa8a0D/f/NlRafpWi52AlAaa4Uu/rsl7saHsJFTNjTptWbu2+A==", + "dev": true, + "dependencies": { + "@algolia/client-common": "5.52.0" + }, + "engines": { + "node": ">= 14.0.0" + } + }, + "node_modules/@antfu/install-pkg": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@antfu/install-pkg/-/install-pkg-1.1.0.tgz", + "integrity": "sha512-MGQsmw10ZyI+EJo45CdSER4zEb+p31LpDAFp2Z3gkSd1yqVZGi0Ebx++YTEMonJy4oChEMLsxZ64j8FH6sSqtQ==", + "dev": true, + "dependencies": { + "package-manager-detector": "^1.3.0", + "tinyexec": "^1.0.1" + }, + "funding": { + "url": "https://github.com/sponsors/antfu" + } + }, + "node_modules/@babel/helper-string-parser": { + "version": "7.27.1", + "resolved": "https://registry.npmjs.org/@babel/helper-string-parser/-/helper-string-parser-7.27.1.tgz", + "integrity": "sha512-qMlSxKbpRlAridDExk92nSobyDdpPijUq2DW6oDnUqd0iOGxmQjyqhMIihI9+zv4LPyZdRje2cavWPbCbWm3eA==", + "dev": true, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-validator-identifier": { + "version": "7.28.5", + "resolved": "https://registry.npmjs.org/@babel/helper-validator-identifier/-/helper-validator-identifier-7.28.5.tgz", + "integrity": "sha512-qSs4ifwzKJSV39ucNjsvc6WVHs6b7S03sOh2OcHF9UHfVPqWWALUsNUVzhSBiItjRZoLHx7nIarVjqKVusUZ1Q==", + "dev": true, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/parser": { + "version": "7.29.3", + "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.29.3.tgz", + "integrity": "sha512-b3ctpQwp+PROvU/cttc4OYl4MzfJUWy6FZg+PMXfzmt/+39iHVF0sDfqay8TQM3JA2EUOyKcFZt75jWriQijsA==", + "dev": true, + "dependencies": { + "@babel/types": "^7.29.0" + }, + "bin": { + "parser": "bin/babel-parser.js" + }, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@babel/types": { + "version": "7.29.0", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.29.0.tgz", + "integrity": "sha512-LwdZHpScM4Qz8Xw2iKSzS+cfglZzJGvofQICy7W7v4caru4EaAmyUuO6BGrbyQ2mYV11W0U8j5mBhd14dd3B0A==", + "dev": true, + "dependencies": { + "@babel/helper-string-parser": "^7.27.1", + "@babel/helper-validator-identifier": "^7.28.5" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@braintree/sanitize-url": { + "version": "7.1.2", + "resolved": "https://registry.npmjs.org/@braintree/sanitize-url/-/sanitize-url-7.1.2.tgz", + "integrity": "sha512-jigsZK+sMF/cuiB7sERuo9V7N9jx+dhmHHnQyDSVdpZwVutaBu7WvNYqMDLSgFgfB30n452TP3vjDAvFC973mA==", + "dev": true + }, + "node_modules/@chevrotain/cst-dts-gen": { + "version": "12.0.0", + "resolved": "https://registry.npmjs.org/@chevrotain/cst-dts-gen/-/cst-dts-gen-12.0.0.tgz", + "integrity": "sha512-fSL4KXjTl7cDgf0B5Rip9Q05BOrYvkJV/RrBTE/bKDN096E4hN/ySpcBK5B24T76dlQ2i32Zc3PAE27jFnFrKg==", + "dev": true, + "dependencies": { + "@chevrotain/gast": "12.0.0", + "@chevrotain/types": "12.0.0" + } + }, + "node_modules/@chevrotain/gast": { + "version": "12.0.0", + "resolved": "https://registry.npmjs.org/@chevrotain/gast/-/gast-12.0.0.tgz", + "integrity": "sha512-1ne/m3XsIT8aEdrvT33so0GUC+wkctpUPK6zU9IlOyJLUbR0rg4G7ZiApiJbggpgPir9ERy3FRjT6T7lpgetnQ==", + "dev": true, + "dependencies": { + "@chevrotain/types": "12.0.0" + } + }, + "node_modules/@chevrotain/regexp-to-ast": { + "version": "12.0.0", + "resolved": "https://registry.npmjs.org/@chevrotain/regexp-to-ast/-/regexp-to-ast-12.0.0.tgz", + "integrity": "sha512-p+EW9MaJwgaHguhoqwOtx/FwuGr+DnNn857sXWOi/mClXIkPGl3rn7hGNWvo31HA3vyeQxjqe+H36yZJwYU8cA==", + "dev": true + }, + "node_modules/@chevrotain/types": { + "version": "12.0.0", + "resolved": "https://registry.npmjs.org/@chevrotain/types/-/types-12.0.0.tgz", + "integrity": "sha512-S+04vjFQKeuYw0/eW3U52LkAHQsB1ASxsPGsLPUyQgrZ2iNNibQrsidruDzjEX2JYfespXMG0eZmXlhA6z7nWA==", + "dev": true + }, + "node_modules/@chevrotain/utils": { + "version": "12.0.0", + "resolved": "https://registry.npmjs.org/@chevrotain/utils/-/utils-12.0.0.tgz", + "integrity": "sha512-lB59uJoaGIfOOL9knQqQRfhl9g7x8/wqFkp13zTdkRu1huG9kg6IJs1O8hqj9rs6h7orGxHJUKb+mX3rPbWGhA==", + "dev": true + }, + "node_modules/@docsearch/css": { + "version": "3.8.2", + "resolved": "https://registry.npmjs.org/@docsearch/css/-/css-3.8.2.tgz", + "integrity": "sha512-y05ayQFyUmCXze79+56v/4HpycYF3uFqB78pLPrSV5ZKAlDuIAAJNhaRi8tTdRNXh05yxX/TyNnzD6LwSM89vQ==", + "dev": true + }, + "node_modules/@docsearch/js": { + "version": "3.8.2", + "resolved": "https://registry.npmjs.org/@docsearch/js/-/js-3.8.2.tgz", + "integrity": "sha512-Q5wY66qHn0SwA7Taa0aDbHiJvaFJLOJyHmooQ7y8hlwwQLQ/5WwCcoX0g7ii04Qi2DJlHsd0XXzJ8Ypw9+9YmQ==", + "dev": true, + "dependencies": { + "@docsearch/react": "3.8.2", + "preact": "^10.0.0" + } + }, + "node_modules/@docsearch/react": { + "version": "3.8.2", + "resolved": "https://registry.npmjs.org/@docsearch/react/-/react-3.8.2.tgz", + "integrity": "sha512-xCRrJQlTt8N9GU0DG4ptwHRkfnSnD/YpdeaXe02iKfqs97TkZJv60yE+1eq/tjPcVnTW8dP5qLP7itifFVV5eg==", + "dev": true, + "dependencies": { + "@algolia/autocomplete-core": "1.17.7", + "@algolia/autocomplete-preset-algolia": "1.17.7", + "@docsearch/css": "3.8.2", + "algoliasearch": "^5.14.2" + }, + "peerDependencies": { + "@types/react": ">= 16.8.0 < 19.0.0", + "react": ">= 16.8.0 < 19.0.0", + "react-dom": ">= 16.8.0 < 19.0.0", + "search-insights": ">= 1 < 3" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + }, + "react": { + "optional": true + }, + "react-dom": { + "optional": true + }, + "search-insights": { + "optional": true + } + } + }, + "node_modules/@esbuild/aix-ppc64": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/aix-ppc64/-/aix-ppc64-0.21.5.tgz", + "integrity": "sha512-1SDgH6ZSPTlggy1yI6+Dbkiz8xzpHJEVAlF/AM1tHPLsf5STom9rwtjE4hKAF20FfXXNTFqEYXyJNWh1GiZedQ==", + "cpu": [ + "ppc64" + ], + "dev": true, + "optional": true, + "os": [ + "aix" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/android-arm": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/android-arm/-/android-arm-0.21.5.tgz", + "integrity": "sha512-vCPvzSjpPHEi1siZdlvAlsPxXl7WbOVUBBAowWug4rJHb68Ox8KualB+1ocNvT5fjv6wpkX6o/iEpbDrf68zcg==", + "cpu": [ + "arm" + ], + "dev": true, + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/android-arm64": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/android-arm64/-/android-arm64-0.21.5.tgz", + "integrity": "sha512-c0uX9VAUBQ7dTDCjq+wdyGLowMdtR/GoC2U5IYk/7D1H1JYC0qseD7+11iMP2mRLN9RcCMRcjC4YMclCzGwS/A==", + "cpu": [ + "arm64" + ], + "dev": true, + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/android-x64": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/android-x64/-/android-x64-0.21.5.tgz", + "integrity": "sha512-D7aPRUUNHRBwHxzxRvp856rjUHRFW1SdQATKXH2hqA0kAZb1hKmi02OpYRacl0TxIGz/ZmXWlbZgjwWYaCakTA==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/darwin-arm64": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/darwin-arm64/-/darwin-arm64-0.21.5.tgz", + "integrity": "sha512-DwqXqZyuk5AiWWf3UfLiRDJ5EDd49zg6O9wclZ7kUMv2WRFr4HKjXp/5t8JZ11QbQfUS6/cRCKGwYhtNAY88kQ==", + "cpu": [ + "arm64" + ], + "dev": true, + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/darwin-x64": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/darwin-x64/-/darwin-x64-0.21.5.tgz", + "integrity": "sha512-se/JjF8NlmKVG4kNIuyWMV/22ZaerB+qaSi5MdrXtd6R08kvs2qCN4C09miupktDitvh8jRFflwGFBQcxZRjbw==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/freebsd-arm64": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/freebsd-arm64/-/freebsd-arm64-0.21.5.tgz", + "integrity": "sha512-5JcRxxRDUJLX8JXp/wcBCy3pENnCgBR9bN6JsY4OmhfUtIHe3ZW0mawA7+RDAcMLrMIZaf03NlQiX9DGyB8h4g==", + "cpu": [ + "arm64" + ], + "dev": true, + "optional": true, + "os": [ + "freebsd" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/freebsd-x64": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/freebsd-x64/-/freebsd-x64-0.21.5.tgz", + "integrity": "sha512-J95kNBj1zkbMXtHVH29bBriQygMXqoVQOQYA+ISs0/2l3T9/kj42ow2mpqerRBxDJnmkUDCaQT/dfNXWX/ZZCQ==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "freebsd" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/linux-arm": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/linux-arm/-/linux-arm-0.21.5.tgz", + "integrity": "sha512-bPb5AHZtbeNGjCKVZ9UGqGwo8EUu4cLq68E95A53KlxAPRmUyYv2D6F0uUI65XisGOL1hBP5mTronbgo+0bFcA==", + "cpu": [ + "arm" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/linux-arm64": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/linux-arm64/-/linux-arm64-0.21.5.tgz", + "integrity": "sha512-ibKvmyYzKsBeX8d8I7MH/TMfWDXBF3db4qM6sy+7re0YXya+K1cem3on9XgdT2EQGMu4hQyZhan7TeQ8XkGp4Q==", + "cpu": [ + "arm64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/linux-ia32": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/linux-ia32/-/linux-ia32-0.21.5.tgz", + "integrity": "sha512-YvjXDqLRqPDl2dvRODYmmhz4rPeVKYvppfGYKSNGdyZkA01046pLWyRKKI3ax8fbJoK5QbxblURkwK/MWY18Tg==", + "cpu": [ + "ia32" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/linux-loong64": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/linux-loong64/-/linux-loong64-0.21.5.tgz", + "integrity": "sha512-uHf1BmMG8qEvzdrzAqg2SIG/02+4/DHB6a9Kbya0XDvwDEKCoC8ZRWI5JJvNdUjtciBGFQ5PuBlpEOXQj+JQSg==", + "cpu": [ + "loong64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/linux-mips64el": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/linux-mips64el/-/linux-mips64el-0.21.5.tgz", + "integrity": "sha512-IajOmO+KJK23bj52dFSNCMsz1QP1DqM6cwLUv3W1QwyxkyIWecfafnI555fvSGqEKwjMXVLokcV5ygHW5b3Jbg==", + "cpu": [ + "mips64el" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/linux-ppc64": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/linux-ppc64/-/linux-ppc64-0.21.5.tgz", + "integrity": "sha512-1hHV/Z4OEfMwpLO8rp7CvlhBDnjsC3CttJXIhBi+5Aj5r+MBvy4egg7wCbe//hSsT+RvDAG7s81tAvpL2XAE4w==", + "cpu": [ + "ppc64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/linux-riscv64": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/linux-riscv64/-/linux-riscv64-0.21.5.tgz", + "integrity": "sha512-2HdXDMd9GMgTGrPWnJzP2ALSokE/0O5HhTUvWIbD3YdjME8JwvSCnNGBnTThKGEB91OZhzrJ4qIIxk/SBmyDDA==", + "cpu": [ + "riscv64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/linux-s390x": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/linux-s390x/-/linux-s390x-0.21.5.tgz", + "integrity": "sha512-zus5sxzqBJD3eXxwvjN1yQkRepANgxE9lgOW2qLnmr8ikMTphkjgXu1HR01K4FJg8h1kEEDAqDcZQtbrRnB41A==", + "cpu": [ + "s390x" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/linux-x64": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/linux-x64/-/linux-x64-0.21.5.tgz", + "integrity": "sha512-1rYdTpyv03iycF1+BhzrzQJCdOuAOtaqHTWJZCWvijKD2N5Xu0TtVC8/+1faWqcP9iBCWOmjmhoH94dH82BxPQ==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/netbsd-x64": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/netbsd-x64/-/netbsd-x64-0.21.5.tgz", + "integrity": "sha512-Woi2MXzXjMULccIwMnLciyZH4nCIMpWQAs049KEeMvOcNADVxo0UBIQPfSmxB3CWKedngg7sWZdLvLczpe0tLg==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "netbsd" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/openbsd-x64": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/openbsd-x64/-/openbsd-x64-0.21.5.tgz", + "integrity": "sha512-HLNNw99xsvx12lFBUwoT8EVCsSvRNDVxNpjZ7bPn947b8gJPzeHWyNVhFsaerc0n3TsbOINvRP2byTZ5LKezow==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "openbsd" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/sunos-x64": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/sunos-x64/-/sunos-x64-0.21.5.tgz", + "integrity": "sha512-6+gjmFpfy0BHU5Tpptkuh8+uw3mnrvgs+dSPQXQOv3ekbordwnzTVEb4qnIvQcYXq6gzkyTnoZ9dZG+D4garKg==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "sunos" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/win32-arm64": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/win32-arm64/-/win32-arm64-0.21.5.tgz", + "integrity": "sha512-Z0gOTd75VvXqyq7nsl93zwahcTROgqvuAcYDUr+vOv8uHhNSKROyU961kgtCD1e95IqPKSQKH7tBTslnS3tA8A==", + "cpu": [ + "arm64" + ], + "dev": true, + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/win32-ia32": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/win32-ia32/-/win32-ia32-0.21.5.tgz", + "integrity": "sha512-SWXFF1CL2RVNMaVs+BBClwtfZSvDgtL//G/smwAc5oVK/UPu2Gu9tIaRgFmYFFKrmg3SyAjSrElf0TiJ1v8fYA==", + "cpu": [ + "ia32" + ], + "dev": true, + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/win32-x64": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/@esbuild/win32-x64/-/win32-x64-0.21.5.tgz", + "integrity": "sha512-tQd/1efJuzPC6rCFwEvLtci/xNFcTZknmXs98FYDfGE4wP9ClFV98nyKrzJKVPMhdDnjzLhdUyMX4PsQAPjwIw==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@iconify-json/simple-icons": { + "version": "1.2.80", + "resolved": "https://registry.npmjs.org/@iconify-json/simple-icons/-/simple-icons-1.2.80.tgz", + "integrity": "sha512-iglncJJ6X/dVuzFDU32MrHwwo4RBwivGf108dgyYg+HKS78ifx0h7sTenpDZMVT+UhdS6CSgZcvY/SvRXlIEUg==", + "dev": true, + "dependencies": { + "@iconify/types": "*" + } + }, + "node_modules/@iconify/types": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/@iconify/types/-/types-2.0.0.tgz", + "integrity": "sha512-+wluvCrRhXrhyOmRDJ3q8mux9JkKy5SJ/v8ol2tu4FVjyYvtEzkc/3pK15ET6RKg4b4w4BmTk1+gsCUhf21Ykg==", + "dev": true + }, + "node_modules/@iconify/utils": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/@iconify/utils/-/utils-3.1.1.tgz", + "integrity": "sha512-MwzoDtw9rO1x+qfgLTV/IVXsHDBqeYZoMIQC8SfxfYSlaSUG+oWiAcoiB1yajAda6mqblm4/1/w2E8tRu7a7Tw==", + "dev": true, + "dependencies": { + "@antfu/install-pkg": "^1.1.0", + "@iconify/types": "^2.0.0", + "mlly": "^1.8.2" + } + }, + "node_modules/@jridgewell/sourcemap-codec": { + "version": "1.5.5", + "resolved": "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.5.5.tgz", + "integrity": "sha512-cYQ9310grqxueWbl+WuIUIaiUaDcj7WOq5fVhEljNVgRfOUhY9fy2zTvfoqWsnebh8Sl70VScFbICvJnLKB0Og==", + "dev": true + }, + "node_modules/@mermaid-js/mermaid-mindmap": { + "version": "9.3.0", + "resolved": "https://registry.npmjs.org/@mermaid-js/mermaid-mindmap/-/mermaid-mindmap-9.3.0.tgz", + "integrity": "sha512-IhtYSVBBRYviH1Ehu8gk69pMDF8DSRqXBRDMWrEfHoaMruHeaP2DXA3PBnuwsMaCdPQhlUUcy/7DBLAEIXvCAw==", + "dev": true, + "optional": true, + "dependencies": { + "@braintree/sanitize-url": "^6.0.0", + "cytoscape": "^3.23.0", + "cytoscape-cose-bilkent": "^4.1.0", + "cytoscape-fcose": "^2.1.0", + "d3": "^7.0.0", + "khroma": "^2.0.0", + "non-layered-tidy-tree-layout": "^2.0.2" + } + }, + "node_modules/@mermaid-js/mermaid-mindmap/node_modules/@braintree/sanitize-url": { + "version": "6.0.4", + "resolved": "https://registry.npmjs.org/@braintree/sanitize-url/-/sanitize-url-6.0.4.tgz", + "integrity": "sha512-s3jaWicZd0pkP0jf5ysyHUI/RE7MHos6qlToFcGWXVp+ykHOy77OUMrfbgJ9it2C5bow7OIQwYYaHjk9XlBQ2A==", + "dev": true, + "optional": true + }, + "node_modules/@mermaid-js/parser": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@mermaid-js/parser/-/parser-1.1.0.tgz", + "integrity": "sha512-gxK9ZX2+Fex5zu8LhRQoMeMPEHbc73UKZ0FQ54YrQtUxE1VVhMwzeNtKRPAu5aXks4FasbMe4xB4bWrmq6Jlxw==", + "dev": true, + "dependencies": { + "langium": "^4.0.0" + } + }, + "node_modules/@rollup/rollup-android-arm-eabi": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.60.2.tgz", + "integrity": "sha512-dnlp69efPPg6Uaw2dVqzWRfAWRnYVb1XJ8CyyhIbZeaq4CA5/mLeZ1IEt9QqQxmbdvagjLIm2ZL8BxXv5lH4Yw==", + "cpu": [ + "arm" + ], + "dev": true, + "optional": true, + "os": [ + "android" + ] + }, + "node_modules/@rollup/rollup-android-arm64": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.60.2.tgz", + "integrity": "sha512-OqZTwDRDchGRHHm/hwLOL7uVPB9aUvI0am/eQuWMNyFHf5PSEQmyEeYYheA0EPPKUO/l0uigCp+iaTjoLjVoHg==", + "cpu": [ + "arm64" + ], + "dev": true, + "optional": true, + "os": [ + "android" + ] + }, + "node_modules/@rollup/rollup-darwin-arm64": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.60.2.tgz", + "integrity": "sha512-UwRE7CGpvSVEQS8gUMBe1uADWjNnVgP3Iusyda1nSRwNDCsRjnGc7w6El6WLQsXmZTbLZx9cecegumcitNfpmA==", + "cpu": [ + "arm64" + ], + "dev": true, + "optional": true, + "os": [ + "darwin" + ] + }, + "node_modules/@rollup/rollup-darwin-x64": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.60.2.tgz", + "integrity": "sha512-gjEtURKLCC5VXm1I+2i1u9OhxFsKAQJKTVB8WvDAHF+oZlq0GTVFOlTlO1q3AlCTE/DF32c16ESvfgqR7343/g==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "darwin" + ] + }, + "node_modules/@rollup/rollup-freebsd-arm64": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-arm64/-/rollup-freebsd-arm64-4.60.2.tgz", + "integrity": "sha512-Bcl6CYDeAgE70cqZaMojOi/eK63h5Me97ZqAQoh77VPjMysA/4ORQBRGo3rRy45x4MzVlU9uZxs8Uwy7ZaKnBw==", + "cpu": [ + "arm64" + ], + "dev": true, + "optional": true, + "os": [ + "freebsd" + ] + }, + "node_modules/@rollup/rollup-freebsd-x64": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-x64/-/rollup-freebsd-x64-4.60.2.tgz", + "integrity": "sha512-LU+TPda3mAE2QB0/Hp5VyeKJivpC6+tlOXd1VMoXV/YFMvk/MNk5iXeBfB4MQGRWyOYVJ01625vjkr0Az98OJQ==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "freebsd" + ] + }, + "node_modules/@rollup/rollup-linux-arm-gnueabihf": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.60.2.tgz", + "integrity": "sha512-2QxQrM+KQ7DAW4o22j+XZ6RKdxjLD7BOWTP0Bv0tmjdyhXSsr2Ul1oJDQqh9Zf5qOwTuTc7Ek83mOFaKnodPjg==", + "cpu": [ + "arm" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-arm-musleabihf": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-musleabihf/-/rollup-linux-arm-musleabihf-4.60.2.tgz", + "integrity": "sha512-TbziEu2DVsTEOPif2mKWkMeDMLoYjx95oESa9fkQQK7r/Orta0gnkcDpzwufEcAO2BLBsD7mZkXGFqEdMRRwfw==", + "cpu": [ + "arm" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-arm64-gnu": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.60.2.tgz", + "integrity": "sha512-bO/rVDiDUuM2YfuCUwZ1t1cP+/yqjqz+Xf2VtkdppefuOFS2OSeAfgafaHNkFn0t02hEyXngZkxtGqXcXwO8Rg==", + "cpu": [ + "arm64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-arm64-musl": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.60.2.tgz", + "integrity": "sha512-hr26p7e93Rl0Za+JwW7EAnwAvKkehh12BU1Llm9Ykiibg4uIr2rbpxG9WCf56GuvidlTG9KiiQT/TXT1yAWxTA==", + "cpu": [ + "arm64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-loong64-gnu": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-gnu/-/rollup-linux-loong64-gnu-4.60.2.tgz", + "integrity": "sha512-pOjB/uSIyDt+ow3k/RcLvUAOGpysT2phDn7TTUB3n75SlIgZzM6NKAqlErPhoFU+npgY3/n+2HYIQVbF70P9/A==", + "cpu": [ + "loong64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-loong64-musl": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-musl/-/rollup-linux-loong64-musl-4.60.2.tgz", + "integrity": "sha512-2/w+q8jszv9Ww1c+6uJT3OwqhdmGP2/4T17cu8WuwyUuuaCDDJ2ojdyYwZzCxx0GcsZBhzi3HmH+J5pZNXnd+Q==", + "cpu": [ + "loong64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-ppc64-gnu": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-gnu/-/rollup-linux-ppc64-gnu-4.60.2.tgz", + "integrity": "sha512-11+aL5vKheYgczxtPVVRhdptAM2H7fcDR5Gw4/bTcteuZBlH4oP9f5s9zYO9aGZvoGeBpqXI/9TZZihZ609wKw==", + "cpu": [ + "ppc64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-ppc64-musl": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-musl/-/rollup-linux-ppc64-musl-4.60.2.tgz", + "integrity": "sha512-i16fokAGK46IVZuV8LIIwMdtqhin9hfYkCh8pf8iC3QU3LpwL+1FSFGej+O7l3E/AoknL6Dclh2oTdnRMpTzFQ==", + "cpu": [ + "ppc64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-riscv64-gnu": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.60.2.tgz", + "integrity": "sha512-49FkKS6RGQoriDSK/6E2GkAsAuU5kETFCh7pG4yD/ylj9rKhTmO3elsnmBvRD4PgJPds5W2PkhC82aVwmUcJ7A==", + "cpu": [ + "riscv64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-riscv64-musl": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-musl/-/rollup-linux-riscv64-musl-4.60.2.tgz", + "integrity": "sha512-mjYNkHPfGpUR00DuM1ZZIgs64Hpf4bWcz9Z41+4Q+pgDx73UwWdAYyf6EG/lRFldmdHHzgrYyge5akFUW0D3mQ==", + "cpu": [ + "riscv64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-s390x-gnu": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-s390x-gnu/-/rollup-linux-s390x-gnu-4.60.2.tgz", + "integrity": "sha512-ALyvJz965BQk8E9Al/JDKKDLH2kfKFLTGMlgkAbbYtZuJt9LU8DW3ZoDMCtQpXAltZxwBHevXz5u+gf0yA0YoA==", + "cpu": [ + "s390x" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-x64-gnu": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.60.2.tgz", + "integrity": "sha512-UQjrkIdWrKI626Du8lCQ6MJp/6V1LAo2bOK9OTu4mSn8GGXIkPXk/Vsp4bLHCd9Z9Iz2OTEaokUE90VweJgIYQ==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-x64-musl": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.60.2.tgz", + "integrity": "sha512-bTsRGj6VlSdn/XD4CGyzMnzaBs9bsRxy79eTqTCBsA8TMIEky7qg48aPkvJvFe1HyzQ5oMZdg7AnVlWQSKLTnw==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-openbsd-x64": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-openbsd-x64/-/rollup-openbsd-x64-4.60.2.tgz", + "integrity": "sha512-6d4Z3534xitaA1FcMWP7mQPq5zGwBmGbhphh2DwaA1aNIXUu3KTOfwrWpbwI4/Gr0uANo7NTtaykFyO2hPuFLg==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "openbsd" + ] + }, + "node_modules/@rollup/rollup-openharmony-arm64": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-openharmony-arm64/-/rollup-openharmony-arm64-4.60.2.tgz", + "integrity": "sha512-NetAg5iO2uN7eB8zE5qrZ3CSil+7IJt4WDFLcC75Ymywq1VZVD6qJ6EvNLjZ3rEm6gB7XW5JdT60c6MN35Z85Q==", + "cpu": [ + "arm64" + ], + "dev": true, + "optional": true, + "os": [ + "openharmony" + ] + }, + "node_modules/@rollup/rollup-win32-arm64-msvc": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.60.2.tgz", + "integrity": "sha512-NCYhOotpgWZ5kdxCZsv6Iudx0wX8980Q/oW4pNFNihpBKsDbEA1zpkfxJGC0yugsUuyDZ7gL37dbzwhR0VI7pQ==", + "cpu": [ + "arm64" + ], + "dev": true, + "optional": true, + "os": [ + "win32" + ] + }, + "node_modules/@rollup/rollup-win32-ia32-msvc": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.60.2.tgz", + "integrity": "sha512-RXsaOqXxfoUBQoOgvmmijVxJnW2IGB0eoMO7F8FAjaj0UTywUO/luSqimWBJn04WNgUkeNhh7fs7pESXajWmkg==", + "cpu": [ + "ia32" + ], + "dev": true, + "optional": true, + "os": [ + "win32" + ] + }, + "node_modules/@rollup/rollup-win32-x64-gnu": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-gnu/-/rollup-win32-x64-gnu-4.60.2.tgz", + "integrity": "sha512-qdAzEULD+/hzObedtmV6iBpdL5TIbKVztGiK7O3/KYSf+HIzU257+MX1EXJcyIiDbMAqmbwaufcYPvyRryeZtA==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "win32" + ] + }, + "node_modules/@rollup/rollup-win32-x64-msvc": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.60.2.tgz", + "integrity": "sha512-Nd/SgG27WoA9e+/TdK74KnHz852TLa94ovOYySo/yMPuTmpckK/jIF2jSwS3g7ELSKXK13/cVdmg1Z/DaCWKxA==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "win32" + ] + }, + "node_modules/@shikijs/core": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/@shikijs/core/-/core-2.5.0.tgz", + "integrity": "sha512-uu/8RExTKtavlpH7XqnVYBrfBkUc20ngXiX9NSrBhOVZYv/7XQRKUyhtkeflY5QsxC0GbJThCerruZfsUaSldg==", + "dev": true, + "dependencies": { + "@shikijs/engine-javascript": "2.5.0", + "@shikijs/engine-oniguruma": "2.5.0", + "@shikijs/types": "2.5.0", + "@shikijs/vscode-textmate": "^10.0.2", + "@types/hast": "^3.0.4", + "hast-util-to-html": "^9.0.4" + } + }, + "node_modules/@shikijs/engine-javascript": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/@shikijs/engine-javascript/-/engine-javascript-2.5.0.tgz", + "integrity": "sha512-VjnOpnQf8WuCEZtNUdjjwGUbtAVKuZkVQ/5cHy/tojVVRIRtlWMYVjyWhxOmIq05AlSOv72z7hRNRGVBgQOl0w==", + "dev": true, + "dependencies": { + "@shikijs/types": "2.5.0", + "@shikijs/vscode-textmate": "^10.0.2", + "oniguruma-to-es": "^3.1.0" + } + }, + "node_modules/@shikijs/engine-oniguruma": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/@shikijs/engine-oniguruma/-/engine-oniguruma-2.5.0.tgz", + "integrity": "sha512-pGd1wRATzbo/uatrCIILlAdFVKdxImWJGQ5rFiB5VZi2ve5xj3Ax9jny8QvkaV93btQEwR/rSz5ERFpC5mKNIw==", + "dev": true, + "dependencies": { + "@shikijs/types": "2.5.0", + "@shikijs/vscode-textmate": "^10.0.2" + } + }, + "node_modules/@shikijs/langs": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/@shikijs/langs/-/langs-2.5.0.tgz", + "integrity": "sha512-Qfrrt5OsNH5R+5tJ/3uYBBZv3SuGmnRPejV9IlIbFH3HTGLDlkqgHymAlzklVmKBjAaVmkPkyikAV/sQ1wSL+w==", + "dev": true, + "dependencies": { + "@shikijs/types": "2.5.0" + } + }, + "node_modules/@shikijs/themes": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/@shikijs/themes/-/themes-2.5.0.tgz", + "integrity": "sha512-wGrk+R8tJnO0VMzmUExHR+QdSaPUl/NKs+a4cQQRWyoc3YFbUzuLEi/KWK1hj+8BfHRKm2jNhhJck1dfstJpiw==", + "dev": true, + "dependencies": { + "@shikijs/types": "2.5.0" + } + }, + "node_modules/@shikijs/transformers": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/@shikijs/transformers/-/transformers-2.5.0.tgz", + "integrity": "sha512-SI494W5X60CaUwgi8u4q4m4s3YAFSxln3tzNjOSYqq54wlVgz0/NbbXEb3mdLbqMBztcmS7bVTaEd2w0qMmfeg==", + "dev": true, + "dependencies": { + "@shikijs/core": "2.5.0", + "@shikijs/types": "2.5.0" + } + }, + "node_modules/@shikijs/types": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/@shikijs/types/-/types-2.5.0.tgz", + "integrity": "sha512-ygl5yhxki9ZLNuNpPitBWvcy9fsSKKaRuO4BAlMyagszQidxcpLAr0qiW/q43DtSIDxO6hEbtYLiFZNXO/hdGw==", + "dev": true, + "dependencies": { + "@shikijs/vscode-textmate": "^10.0.2", + "@types/hast": "^3.0.4" + } + }, + "node_modules/@shikijs/vscode-textmate": { + "version": "10.0.2", + "resolved": "https://registry.npmjs.org/@shikijs/vscode-textmate/-/vscode-textmate-10.0.2.tgz", + "integrity": "sha512-83yeghZ2xxin3Nj8z1NMd/NCuca+gsYXswywDy5bHvwlWL8tpTQmzGeUuHd9FC3E/SBEMvzJRwWEOz5gGes9Qg==", + "dev": true + }, + "node_modules/@types/d3": { + "version": "7.4.3", + "resolved": "https://registry.npmjs.org/@types/d3/-/d3-7.4.3.tgz", + "integrity": "sha512-lZXZ9ckh5R8uiFVt8ogUNf+pIrK4EsWrx2Np75WvF/eTpJ0FMHNhjXk8CKEx/+gpHbNQyJWehbFaTvqmHWB3ww==", + "dev": true, + "dependencies": { + "@types/d3-array": "*", + "@types/d3-axis": "*", + "@types/d3-brush": "*", + "@types/d3-chord": "*", + "@types/d3-color": "*", + "@types/d3-contour": "*", + "@types/d3-delaunay": "*", + "@types/d3-dispatch": "*", + "@types/d3-drag": "*", + "@types/d3-dsv": "*", + "@types/d3-ease": "*", + "@types/d3-fetch": "*", + "@types/d3-force": "*", + "@types/d3-format": "*", + "@types/d3-geo": "*", + "@types/d3-hierarchy": "*", + "@types/d3-interpolate": "*", + "@types/d3-path": "*", + "@types/d3-polygon": "*", + "@types/d3-quadtree": "*", + "@types/d3-random": "*", + "@types/d3-scale": "*", + "@types/d3-scale-chromatic": "*", + "@types/d3-selection": "*", + "@types/d3-shape": "*", + "@types/d3-time": "*", + "@types/d3-time-format": "*", + "@types/d3-timer": "*", + "@types/d3-transition": "*", + "@types/d3-zoom": "*" + } + }, + "node_modules/@types/d3-array": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/@types/d3-array/-/d3-array-3.2.2.tgz", + "integrity": "sha512-hOLWVbm7uRza0BYXpIIW5pxfrKe0W+D5lrFiAEYR+pb6w3N2SwSMaJbXdUfSEv+dT4MfHBLtn5js0LAWaO6otw==", + "dev": true + }, + "node_modules/@types/d3-axis": { + "version": "3.0.6", + "resolved": "https://registry.npmjs.org/@types/d3-axis/-/d3-axis-3.0.6.tgz", + "integrity": "sha512-pYeijfZuBd87T0hGn0FO1vQ/cgLk6E1ALJjfkC0oJ8cbwkZl3TpgS8bVBLZN+2jjGgg38epgxb2zmoGtSfvgMw==", + "dev": true, + "dependencies": { + "@types/d3-selection": "*" + } + }, + "node_modules/@types/d3-brush": { + "version": "3.0.6", + "resolved": "https://registry.npmjs.org/@types/d3-brush/-/d3-brush-3.0.6.tgz", + "integrity": "sha512-nH60IZNNxEcrh6L1ZSMNA28rj27ut/2ZmI3r96Zd+1jrZD++zD3LsMIjWlvg4AYrHn/Pqz4CF3veCxGjtbqt7A==", + "dev": true, + "dependencies": { + "@types/d3-selection": "*" + } + }, + "node_modules/@types/d3-chord": { + "version": "3.0.6", + "resolved": "https://registry.npmjs.org/@types/d3-chord/-/d3-chord-3.0.6.tgz", + "integrity": "sha512-LFYWWd8nwfwEmTZG9PfQxd17HbNPksHBiJHaKuY1XeqscXacsS2tyoo6OdRsjf+NQYeB6XrNL3a25E3gH69lcg==", + "dev": true + }, + "node_modules/@types/d3-color": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/@types/d3-color/-/d3-color-3.1.3.tgz", + "integrity": "sha512-iO90scth9WAbmgv7ogoq57O9YpKmFBbmoEoCHDB2xMBY0+/KVrqAaCDyCE16dUspeOvIxFFRI+0sEtqDqy2b4A==", + "dev": true + }, + "node_modules/@types/d3-contour": { + "version": "3.0.6", + "resolved": "https://registry.npmjs.org/@types/d3-contour/-/d3-contour-3.0.6.tgz", + "integrity": "sha512-BjzLgXGnCWjUSYGfH1cpdo41/hgdWETu4YxpezoztawmqsvCeep+8QGfiY6YbDvfgHz/DkjeIkkZVJavB4a3rg==", + "dev": true, + "dependencies": { + "@types/d3-array": "*", + "@types/geojson": "*" + } + }, + "node_modules/@types/d3-delaunay": { + "version": "6.0.4", + "resolved": "https://registry.npmjs.org/@types/d3-delaunay/-/d3-delaunay-6.0.4.tgz", + "integrity": "sha512-ZMaSKu4THYCU6sV64Lhg6qjf1orxBthaC161plr5KuPHo3CNm8DTHiLw/5Eq2b6TsNP0W0iJrUOFscY6Q450Hw==", + "dev": true + }, + "node_modules/@types/d3-dispatch": { + "version": "3.0.7", + "resolved": "https://registry.npmjs.org/@types/d3-dispatch/-/d3-dispatch-3.0.7.tgz", + "integrity": "sha512-5o9OIAdKkhN1QItV2oqaE5KMIiXAvDWBDPrD85e58Qlz1c1kI/J0NcqbEG88CoTwJrYe7ntUCVfeUl2UJKbWgA==", + "dev": true + }, + "node_modules/@types/d3-drag": { + "version": "3.0.7", + "resolved": "https://registry.npmjs.org/@types/d3-drag/-/d3-drag-3.0.7.tgz", + "integrity": "sha512-HE3jVKlzU9AaMazNufooRJ5ZpWmLIoc90A37WU2JMmeq28w1FQqCZswHZ3xR+SuxYftzHq6WU6KJHvqxKzTxxQ==", + "dev": true, + "dependencies": { + "@types/d3-selection": "*" + } + }, + "node_modules/@types/d3-dsv": { + "version": "3.0.7", + "resolved": "https://registry.npmjs.org/@types/d3-dsv/-/d3-dsv-3.0.7.tgz", + "integrity": "sha512-n6QBF9/+XASqcKK6waudgL0pf/S5XHPPI8APyMLLUHd8NqouBGLsU8MgtO7NINGtPBtk9Kko/W4ea0oAspwh9g==", + "dev": true + }, + "node_modules/@types/d3-ease": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/@types/d3-ease/-/d3-ease-3.0.2.tgz", + "integrity": "sha512-NcV1JjO5oDzoK26oMzbILE6HW7uVXOHLQvHshBUW4UMdZGfiY6v5BeQwh9a9tCzv+CeefZQHJt5SRgK154RtiA==", + "dev": true + }, + "node_modules/@types/d3-fetch": { + "version": "3.0.7", + "resolved": "https://registry.npmjs.org/@types/d3-fetch/-/d3-fetch-3.0.7.tgz", + "integrity": "sha512-fTAfNmxSb9SOWNB9IoG5c8Hg6R+AzUHDRlsXsDZsNp6sxAEOP0tkP3gKkNSO/qmHPoBFTxNrjDprVHDQDvo5aA==", + "dev": true, + "dependencies": { + "@types/d3-dsv": "*" + } + }, + "node_modules/@types/d3-force": { + "version": "3.0.10", + "resolved": "https://registry.npmjs.org/@types/d3-force/-/d3-force-3.0.10.tgz", + "integrity": "sha512-ZYeSaCF3p73RdOKcjj+swRlZfnYpK1EbaDiYICEEp5Q6sUiqFaFQ9qgoshp5CzIyyb/yD09kD9o2zEltCexlgw==", + "dev": true + }, + "node_modules/@types/d3-format": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/@types/d3-format/-/d3-format-3.0.4.tgz", + "integrity": "sha512-fALi2aI6shfg7vM5KiR1wNJnZ7r6UuggVqtDA+xiEdPZQwy/trcQaHnwShLuLdta2rTymCNpxYTiMZX/e09F4g==", + "dev": true + }, + "node_modules/@types/d3-geo": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/@types/d3-geo/-/d3-geo-3.1.0.tgz", + "integrity": "sha512-856sckF0oP/diXtS4jNsiQw/UuK5fQG8l/a9VVLeSouf1/PPbBE1i1W852zVwKwYCBkFJJB7nCFTbk6UMEXBOQ==", + "dev": true, + "dependencies": { + "@types/geojson": "*" + } + }, + "node_modules/@types/d3-hierarchy": { + "version": "3.1.7", + "resolved": "https://registry.npmjs.org/@types/d3-hierarchy/-/d3-hierarchy-3.1.7.tgz", + "integrity": "sha512-tJFtNoYBtRtkNysX1Xq4sxtjK8YgoWUNpIiUee0/jHGRwqvzYxkq0hGVbbOGSz+JgFxxRu4K8nb3YpG3CMARtg==", + "dev": true + }, + "node_modules/@types/d3-interpolate": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/@types/d3-interpolate/-/d3-interpolate-3.0.4.tgz", + "integrity": "sha512-mgLPETlrpVV1YRJIglr4Ez47g7Yxjl1lj7YKsiMCb27VJH9W8NVM6Bb9d8kkpG/uAQS5AmbA48q2IAolKKo1MA==", + "dev": true, + "dependencies": { + "@types/d3-color": "*" + } + }, + "node_modules/@types/d3-path": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/@types/d3-path/-/d3-path-3.1.1.tgz", + "integrity": "sha512-VMZBYyQvbGmWyWVea0EHs/BwLgxc+MKi1zLDCONksozI4YJMcTt8ZEuIR4Sb1MMTE8MMW49v0IwI5+b7RmfWlg==", + "dev": true + }, + "node_modules/@types/d3-polygon": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/@types/d3-polygon/-/d3-polygon-3.0.2.tgz", + "integrity": "sha512-ZuWOtMaHCkN9xoeEMr1ubW2nGWsp4nIql+OPQRstu4ypeZ+zk3YKqQT0CXVe/PYqrKpZAi+J9mTs05TKwjXSRA==", + "dev": true + }, + "node_modules/@types/d3-quadtree": { + "version": "3.0.6", + "resolved": "https://registry.npmjs.org/@types/d3-quadtree/-/d3-quadtree-3.0.6.tgz", + "integrity": "sha512-oUzyO1/Zm6rsxKRHA1vH0NEDG58HrT5icx/azi9MF1TWdtttWl0UIUsjEQBBh+SIkrpd21ZjEv7ptxWys1ncsg==", + "dev": true + }, + "node_modules/@types/d3-random": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/@types/d3-random/-/d3-random-3.0.3.tgz", + "integrity": "sha512-Imagg1vJ3y76Y2ea0871wpabqp613+8/r0mCLEBfdtqC7xMSfj9idOnmBYyMoULfHePJyxMAw3nWhJxzc+LFwQ==", + "dev": true + }, + "node_modules/@types/d3-scale": { + "version": "4.0.9", + "resolved": "https://registry.npmjs.org/@types/d3-scale/-/d3-scale-4.0.9.tgz", + "integrity": "sha512-dLmtwB8zkAeO/juAMfnV+sItKjlsw2lKdZVVy6LRr0cBmegxSABiLEpGVmSJJ8O08i4+sGR6qQtb6WtuwJdvVw==", + "dev": true, + "dependencies": { + "@types/d3-time": "*" + } + }, + "node_modules/@types/d3-scale-chromatic": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/@types/d3-scale-chromatic/-/d3-scale-chromatic-3.1.0.tgz", + "integrity": "sha512-iWMJgwkK7yTRmWqRB5plb1kadXyQ5Sj8V/zYlFGMUBbIPKQScw+Dku9cAAMgJG+z5GYDoMjWGLVOvjghDEFnKQ==", + "dev": true + }, + "node_modules/@types/d3-selection": { + "version": "3.0.11", + "resolved": "https://registry.npmjs.org/@types/d3-selection/-/d3-selection-3.0.11.tgz", + "integrity": "sha512-bhAXu23DJWsrI45xafYpkQ4NtcKMwWnAC/vKrd2l+nxMFuvOT3XMYTIj2opv8vq8AO5Yh7Qac/nSeP/3zjTK0w==", + "dev": true + }, + "node_modules/@types/d3-shape": { + "version": "3.1.8", + "resolved": "https://registry.npmjs.org/@types/d3-shape/-/d3-shape-3.1.8.tgz", + "integrity": "sha512-lae0iWfcDeR7qt7rA88BNiqdvPS5pFVPpo5OfjElwNaT2yyekbM0C9vK+yqBqEmHr6lDkRnYNoTBYlAgJa7a4w==", + "dev": true, + "dependencies": { + "@types/d3-path": "*" + } + }, + "node_modules/@types/d3-time": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/@types/d3-time/-/d3-time-3.0.4.tgz", + "integrity": "sha512-yuzZug1nkAAaBlBBikKZTgzCeA+k1uy4ZFwWANOfKw5z5LRhV0gNA7gNkKm7HoK+HRN0wX3EkxGk0fpbWhmB7g==", + "dev": true + }, + "node_modules/@types/d3-time-format": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/@types/d3-time-format/-/d3-time-format-4.0.3.tgz", + "integrity": "sha512-5xg9rC+wWL8kdDj153qZcsJ0FWiFt0J5RB6LYUNZjwSnesfblqrI/bJ1wBdJ8OQfncgbJG5+2F+qfqnqyzYxyg==", + "dev": true + }, + "node_modules/@types/d3-timer": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/@types/d3-timer/-/d3-timer-3.0.2.tgz", + "integrity": "sha512-Ps3T8E8dZDam6fUyNiMkekK3XUsaUEik+idO9/YjPtfj2qruF8tFBXS7XhtE4iIXBLxhmLjP3SXpLhVf21I9Lw==", + "dev": true + }, + "node_modules/@types/d3-transition": { + "version": "3.0.9", + "resolved": "https://registry.npmjs.org/@types/d3-transition/-/d3-transition-3.0.9.tgz", + "integrity": "sha512-uZS5shfxzO3rGlu0cC3bjmMFKsXv+SmZZcgp0KD22ts4uGXp5EVYGzu/0YdwZeKmddhcAccYtREJKkPfXkZuCg==", + "dev": true, + "dependencies": { + "@types/d3-selection": "*" + } + }, + "node_modules/@types/d3-zoom": { + "version": "3.0.8", + "resolved": "https://registry.npmjs.org/@types/d3-zoom/-/d3-zoom-3.0.8.tgz", + "integrity": "sha512-iqMC4/YlFCSlO8+2Ii1GGGliCAY4XdeG748w5vQUbevlbDu0zSjH/+jojorQVBK/se0j6DUFNPBGSqD3YWYnDw==", + "dev": true, + "dependencies": { + "@types/d3-interpolate": "*", + "@types/d3-selection": "*" + } + }, + "node_modules/@types/estree": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.8.tgz", + "integrity": "sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==", + "dev": true + }, + "node_modules/@types/geojson": { + "version": "7946.0.16", + "resolved": "https://registry.npmjs.org/@types/geojson/-/geojson-7946.0.16.tgz", + "integrity": "sha512-6C8nqWur3j98U6+lXDfTUWIfgvZU+EumvpHKcYjujKH7woYyLj2sUmff0tRhrqM7BohUw7Pz3ZB1jj2gW9Fvmg==", + "dev": true + }, + "node_modules/@types/hast": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/@types/hast/-/hast-3.0.4.tgz", + "integrity": "sha512-WPs+bbQw5aCj+x6laNGWLH3wviHtoCv/P3+otBhbOhJgG8qtpdAMlTCxLtsTWA7LH1Oh/bFCHsBn0TPS5m30EQ==", + "dev": true, + "dependencies": { + "@types/unist": "*" + } + }, + "node_modules/@types/linkify-it": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/@types/linkify-it/-/linkify-it-5.0.0.tgz", + "integrity": "sha512-sVDA58zAw4eWAffKOaQH5/5j3XeayukzDk+ewSsnv3p4yJEZHCCzMDiZM8e0OUrRvmpGZ85jf4yDHkHsgBNr9Q==", + "dev": true + }, + "node_modules/@types/markdown-it": { + "version": "14.1.2", + "resolved": "https://registry.npmjs.org/@types/markdown-it/-/markdown-it-14.1.2.tgz", + "integrity": "sha512-promo4eFwuiW+TfGxhi+0x3czqTYJkG8qB17ZUJiVF10Xm7NLVRSLUsfRTU/6h1e24VvRnXCx+hG7li58lkzog==", + "dev": true, + "dependencies": { + "@types/linkify-it": "^5", + "@types/mdurl": "^2" + } + }, + "node_modules/@types/mdast": { + "version": "4.0.4", + "resolved": "https://registry.npmjs.org/@types/mdast/-/mdast-4.0.4.tgz", + "integrity": "sha512-kGaNbPh1k7AFzgpud/gMdvIm5xuECykRR+JnWKQno9TAXVa6WIVCGTPvYGekIDL4uwCZQSYbUxNBSb1aUo79oA==", + "dev": true, + "dependencies": { + "@types/unist": "*" + } + }, + "node_modules/@types/mdurl": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/@types/mdurl/-/mdurl-2.0.0.tgz", + "integrity": "sha512-RGdgjQUZba5p6QEFAVx2OGb8rQDL/cPRG7GiedRzMcJ1tYnUANBncjbSB1NRGwbvjcPeikRABz2nshyPk1bhWg==", + "dev": true + }, + "node_modules/@types/trusted-types": { + "version": "2.0.7", + "resolved": "https://registry.npmjs.org/@types/trusted-types/-/trusted-types-2.0.7.tgz", + "integrity": "sha512-ScaPdn1dQczgbl0QFTeTOmVHFULt394XJgOQNoyVhZ6r2vLnMLJfBPd53SB52T/3G36VI1/g2MZaX0cwDuXsfw==", + "dev": true, + "optional": true + }, + "node_modules/@types/unist": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", + "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", + "dev": true + }, + "node_modules/@types/web-bluetooth": { + "version": "0.0.21", + "resolved": "https://registry.npmjs.org/@types/web-bluetooth/-/web-bluetooth-0.0.21.tgz", + "integrity": "sha512-oIQLCGWtcFZy2JW77j9k8nHzAOpqMHLQejDA48XXMWH6tjCQHz5RCFz1bzsmROyL6PUm+LLnUiI4BCn221inxA==", + "dev": true + }, + "node_modules/@ungap/structured-clone": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/@ungap/structured-clone/-/structured-clone-1.3.0.tgz", + "integrity": "sha512-WmoN8qaIAo7WTYWbAZuG8PYEhn5fkz7dZrqTBZ7dtt//lL2Gwms1IcnQ5yHqjDfX8Ft5j4YzDM23f87zBfDe9g==", + "dev": true + }, + "node_modules/@upsetjs/venn.js": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/@upsetjs/venn.js/-/venn.js-2.0.0.tgz", + "integrity": "sha512-WbBhLrooyePuQ1VZxrJjtLvTc4NVfpOyKx0sKqioq9bX1C1m7Jgykkn8gLrtwumBioXIqam8DLxp88Adbue6Hw==", + "dev": true, + "optionalDependencies": { + "d3-selection": "^3.0.0", + "d3-transition": "^3.0.1" + } + }, + "node_modules/@vitejs/plugin-vue": { + "version": "5.2.4", + "resolved": "https://registry.npmjs.org/@vitejs/plugin-vue/-/plugin-vue-5.2.4.tgz", + "integrity": "sha512-7Yx/SXSOcQq5HiiV3orevHUFn+pmMB4cgbEkDYgnkUWb0WfeQ/wa2yFv6D5ICiCQOVpjA7vYDXrC7AGO8yjDHA==", + "dev": true, + "engines": { + "node": "^18.0.0 || >=20.0.0" + }, + "peerDependencies": { + "vite": "^5.0.0 || ^6.0.0", + "vue": "^3.2.25" + } + }, + "node_modules/@vue/compiler-core": { + "version": "3.5.33", + "resolved": "https://registry.npmjs.org/@vue/compiler-core/-/compiler-core-3.5.33.tgz", + "integrity": "sha512-3PZLQwFw4Za3TC8t0FvTy3wI16Kt+pmwcgNZca4Pj9iWL2E72a/gZlpBtAJvEdDMdCxdG/qq0C7PN0bsJuv0Rw==", + "dev": true, + "dependencies": { + "@babel/parser": "^7.29.2", + "@vue/shared": "3.5.33", + "entities": "^7.0.1", + "estree-walker": "^2.0.2", + "source-map-js": "^1.2.1" + } + }, + "node_modules/@vue/compiler-dom": { + "version": "3.5.33", + "resolved": "https://registry.npmjs.org/@vue/compiler-dom/-/compiler-dom-3.5.33.tgz", + "integrity": "sha512-PXq0yrfCLzzL07rbXO4awtXY1Z06LG2eu6Adg3RJFa/j3Cii217XxxLXG22N330gw7GmALCY0Z8RgXEviwgpjA==", + "dev": true, + "dependencies": { + "@vue/compiler-core": "3.5.33", + "@vue/shared": "3.5.33" + } + }, + "node_modules/@vue/compiler-sfc": { + "version": "3.5.33", + "resolved": "https://registry.npmjs.org/@vue/compiler-sfc/-/compiler-sfc-3.5.33.tgz", + "integrity": "sha512-UTUvRO9cY+rROrx/pvN9P5Z7FgA6QGfokUCfhQE4EnmUj3rVnK+CHI0LsEO1pg+I7//iRYMUfcNcCPe7tg0CoA==", + "dev": true, + "dependencies": { + "@babel/parser": "^7.29.2", + "@vue/compiler-core": "3.5.33", + "@vue/compiler-dom": "3.5.33", + "@vue/compiler-ssr": "3.5.33", + "@vue/shared": "3.5.33", + "estree-walker": "^2.0.2", + "magic-string": "^0.30.21", + "postcss": "^8.5.10", + "source-map-js": "^1.2.1" + } + }, + "node_modules/@vue/compiler-ssr": { + "version": "3.5.33", + "resolved": "https://registry.npmjs.org/@vue/compiler-ssr/-/compiler-ssr-3.5.33.tgz", + "integrity": "sha512-IErjYdnj1qIupG5xxiVIYiiRvDhGWV4zuh/RCrwfYpuL+HWQzeU6lCk/nF9r7olWMnjKxCAkOctT2qFWFkzb1A==", + "dev": true, + "dependencies": { + "@vue/compiler-dom": "3.5.33", + "@vue/shared": "3.5.33" + } + }, + "node_modules/@vue/devtools-api": { + "version": "7.7.9", + "resolved": "https://registry.npmjs.org/@vue/devtools-api/-/devtools-api-7.7.9.tgz", + "integrity": "sha512-kIE8wvwlcZ6TJTbNeU2HQNtaxLx3a84aotTITUuL/4bzfPxzajGBOoqjMhwZJ8L9qFYDU/lAYMEEm11dnZOD6g==", + "dev": true, + "dependencies": { + "@vue/devtools-kit": "^7.7.9" + } + }, + "node_modules/@vue/devtools-kit": { + "version": "7.7.9", + "resolved": "https://registry.npmjs.org/@vue/devtools-kit/-/devtools-kit-7.7.9.tgz", + "integrity": "sha512-PyQ6odHSgiDVd4hnTP+aDk2X4gl2HmLDfiyEnn3/oV+ckFDuswRs4IbBT7vacMuGdwY/XemxBoh302ctbsptuA==", + "dev": true, + "dependencies": { + "@vue/devtools-shared": "^7.7.9", + "birpc": "^2.3.0", + "hookable": "^5.5.3", + "mitt": "^3.0.1", + "perfect-debounce": "^1.0.0", + "speakingurl": "^14.0.1", + "superjson": "^2.2.2" + } + }, + "node_modules/@vue/devtools-shared": { + "version": "7.7.9", + "resolved": "https://registry.npmjs.org/@vue/devtools-shared/-/devtools-shared-7.7.9.tgz", + "integrity": "sha512-iWAb0v2WYf0QWmxCGy0seZNDPdO3Sp5+u78ORnyeonS6MT4PC7VPrryX2BpMJrwlDeaZ6BD4vP4XKjK0SZqaeA==", + "dev": true, + "dependencies": { + "rfdc": "^1.4.1" + } + }, + "node_modules/@vue/reactivity": { + "version": "3.5.33", + "resolved": "https://registry.npmjs.org/@vue/reactivity/-/reactivity-3.5.33.tgz", + "integrity": "sha512-p8UfIqyIhb0rYGlSgSBV+lPhF2iUSBcRy7enhTmPqKWadHy9kcOFYF1AejYBP9P+avnd3OBbD49DU4pLWX/94A==", + "dev": true, + "dependencies": { + "@vue/shared": "3.5.33" + } + }, + "node_modules/@vue/runtime-core": { + "version": "3.5.33", + "resolved": "https://registry.npmjs.org/@vue/runtime-core/-/runtime-core-3.5.33.tgz", + "integrity": "sha512-UpFF45RI9//a7rvq7RdOQblb4tup7hHG9QsmIrxkFQLzQ7R8/iNQ5LE15NhLZ1/WcHMU2b47u6P33CPUelHyIQ==", + "dev": true, + "dependencies": { + "@vue/reactivity": "3.5.33", + "@vue/shared": "3.5.33" + } + }, + "node_modules/@vue/runtime-dom": { + "version": "3.5.33", + "resolved": "https://registry.npmjs.org/@vue/runtime-dom/-/runtime-dom-3.5.33.tgz", + "integrity": "sha512-IOxMsAOwquhfITgmOgaPYl7/j8gKUxUFoflRc+u4LxyD3+783xne8vNta1PONVCvCV9A0w7hkyEepINDqfO0tw==", + "dev": true, + "dependencies": { + "@vue/reactivity": "3.5.33", + "@vue/runtime-core": "3.5.33", + "@vue/shared": "3.5.33", + "csstype": "^3.2.3" + } + }, + "node_modules/@vue/server-renderer": { + "version": "3.5.33", + "resolved": "https://registry.npmjs.org/@vue/server-renderer/-/server-renderer-3.5.33.tgz", + "integrity": "sha512-0xylq/8/h44lVG0pZFknv1XIdEgymq2E9n59uTWJBG+dIgiT0TMCSsxrN7nO16Z0MU0MPjFcguBbZV8Itk52Hw==", + "dev": true, + "dependencies": { + "@vue/compiler-ssr": "3.5.33", + "@vue/shared": "3.5.33" + }, + "peerDependencies": { + "vue": "3.5.33" + } + }, + "node_modules/@vue/shared": { + "version": "3.5.33", + "resolved": "https://registry.npmjs.org/@vue/shared/-/shared-3.5.33.tgz", + "integrity": "sha512-5vR2QIlmaLG77Ygd4pMP6+SGQ5yox9VhtnbDWTy9DzMzdmeLxZ1QqxrywEZ9sa1AVubfIJyaCG3ytyWU81ufcQ==", + "dev": true + }, + "node_modules/@vueuse/core": { + "version": "12.8.2", + "resolved": "https://registry.npmjs.org/@vueuse/core/-/core-12.8.2.tgz", + "integrity": "sha512-HbvCmZdzAu3VGi/pWYm5Ut+Kd9mn1ZHnn4L5G8kOQTPs/IwIAmJoBrmYk2ckLArgMXZj0AW3n5CAejLUO+PhdQ==", + "dev": true, + "dependencies": { + "@types/web-bluetooth": "^0.0.21", + "@vueuse/metadata": "12.8.2", + "@vueuse/shared": "12.8.2", + "vue": "^3.5.13" + }, + "funding": { + "url": "https://github.com/sponsors/antfu" + } + }, + "node_modules/@vueuse/integrations": { + "version": "12.8.2", + "resolved": "https://registry.npmjs.org/@vueuse/integrations/-/integrations-12.8.2.tgz", + "integrity": "sha512-fbGYivgK5uBTRt7p5F3zy6VrETlV9RtZjBqd1/HxGdjdckBgBM4ugP8LHpjolqTj14TXTxSK1ZfgPbHYyGuH7g==", + "dev": true, + "dependencies": { + "@vueuse/core": "12.8.2", + "@vueuse/shared": "12.8.2", + "vue": "^3.5.13" + }, + "funding": { + "url": "https://github.com/sponsors/antfu" + }, + "peerDependencies": { + "async-validator": "^4", + "axios": "^1", + "change-case": "^5", + "drauu": "^0.4", + "focus-trap": "^7", + "fuse.js": "^7", + "idb-keyval": "^6", + "jwt-decode": "^4", + "nprogress": "^0.2", + "qrcode": "^1.5", + "sortablejs": "^1", + "universal-cookie": "^7" + }, + "peerDependenciesMeta": { + "async-validator": { + "optional": true + }, + "axios": { + "optional": true + }, + "change-case": { + "optional": true + }, + "drauu": { + "optional": true + }, + "focus-trap": { + "optional": true + }, + "fuse.js": { + "optional": true + }, + "idb-keyval": { + "optional": true + }, + "jwt-decode": { + "optional": true + }, + "nprogress": { + "optional": true + }, + "qrcode": { + "optional": true + }, + "sortablejs": { + "optional": true + }, + "universal-cookie": { + "optional": true + } + } + }, + "node_modules/@vueuse/metadata": { + "version": "12.8.2", + "resolved": "https://registry.npmjs.org/@vueuse/metadata/-/metadata-12.8.2.tgz", + "integrity": "sha512-rAyLGEuoBJ/Il5AmFHiziCPdQzRt88VxR+Y/A/QhJ1EWtWqPBBAxTAFaSkviwEuOEZNtW8pvkPgoCZQ+HxqW1A==", + "dev": true, + "funding": { + "url": "https://github.com/sponsors/antfu" + } + }, + "node_modules/@vueuse/shared": { + "version": "12.8.2", + "resolved": "https://registry.npmjs.org/@vueuse/shared/-/shared-12.8.2.tgz", + "integrity": "sha512-dznP38YzxZoNloI0qpEfpkms8knDtaoQ6Y/sfS0L7Yki4zh40LFHEhur0odJC6xTHG5dxWVPiUWBXn+wCG2s5w==", + "dev": true, + "dependencies": { + "vue": "^3.5.13" + }, + "funding": { + "url": "https://github.com/sponsors/antfu" + } + }, + "node_modules/acorn": { + "version": "8.16.0", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.16.0.tgz", + "integrity": "sha512-UVJyE9MttOsBQIDKw1skb9nAwQuR5wuGD3+82K6JgJlm/Y+KI92oNsMNGZCYdDsVtRHSak0pcV5Dno5+4jh9sw==", + "dev": true, + "bin": { + "acorn": "bin/acorn" + }, + "engines": { + "node": ">=0.4.0" + } + }, + "node_modules/algoliasearch": { + "version": "5.52.0", + "resolved": "https://registry.npmjs.org/algoliasearch/-/algoliasearch-5.52.0.tgz", + "integrity": "sha512-0ZzY9mjqV7gop/AH8pIBiAS8giXP7WcSiUfoFYIzYAK9QC5c37E4SIVtJVBMwlURc0/uNt2o4RcNRvdHa4CJ5w==", + "dev": true, + "dependencies": { + "@algolia/abtesting": "1.18.0", + "@algolia/client-abtesting": "5.52.0", + "@algolia/client-analytics": "5.52.0", + "@algolia/client-common": "5.52.0", + "@algolia/client-insights": "5.52.0", + "@algolia/client-personalization": "5.52.0", + "@algolia/client-query-suggestions": "5.52.0", + "@algolia/client-search": "5.52.0", + "@algolia/ingestion": "1.52.0", + "@algolia/monitoring": "1.52.0", + "@algolia/recommend": "5.52.0", + "@algolia/requester-browser-xhr": "5.52.0", + "@algolia/requester-fetch": "5.52.0", + "@algolia/requester-node-http": "5.52.0" + }, + "engines": { + "node": ">= 14.0.0" + } + }, + "node_modules/birpc": { + "version": "2.9.0", + "resolved": "https://registry.npmjs.org/birpc/-/birpc-2.9.0.tgz", + "integrity": "sha512-KrayHS5pBi69Xi9JmvoqrIgYGDkD6mcSe/i6YKi3w5kekCLzrX4+nawcXqrj2tIp50Kw/mT/s3p+GVK0A0sKxw==", + "dev": true, + "funding": { + "url": "https://github.com/sponsors/antfu" + } + }, + "node_modules/ccount": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/ccount/-/ccount-2.0.1.tgz", + "integrity": "sha512-eyrF0jiFpY+3drT6383f1qhkbGsLSifNAjA61IUjZjmLCWjItY6LB9ft9YhoDgwfmclB2zhu51Lc7+95b8NRAg==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/character-entities-html4": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/character-entities-html4/-/character-entities-html4-2.1.0.tgz", + "integrity": "sha512-1v7fgQRj6hnSwFpq1Eu0ynr/CDEw0rXo2B61qXrLNdHZmPKgb7fqS1a2JwF0rISo9q77jDI8VMEHoApn8qDoZA==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/character-entities-legacy": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/character-entities-legacy/-/character-entities-legacy-3.0.0.tgz", + "integrity": "sha512-RpPp0asT/6ufRm//AJVwpViZbGM/MkjQFxJccQRHmISF/22NBtsHqAWmL+/pmkPWoIUJdWyeVleTl1wydHATVQ==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/chevrotain": { + "version": "12.0.0", + "resolved": "https://registry.npmjs.org/chevrotain/-/chevrotain-12.0.0.tgz", + "integrity": "sha512-csJvb+6kEiQaqo1woTdSAuOWdN0WTLIydkKrBnS+V5gZz0oqBrp4kQ35519QgK6TpBThiG3V1vNSHlIkv4AglQ==", + "dev": true, + "dependencies": { + "@chevrotain/cst-dts-gen": "12.0.0", + "@chevrotain/gast": "12.0.0", + "@chevrotain/regexp-to-ast": "12.0.0", + "@chevrotain/types": "12.0.0", + "@chevrotain/utils": "12.0.0" + }, + "engines": { + "node": ">=22.0.0" + } + }, + "node_modules/chevrotain-allstar": { + "version": "0.4.3", + "resolved": "https://registry.npmjs.org/chevrotain-allstar/-/chevrotain-allstar-0.4.3.tgz", + "integrity": "sha512-2X4mkroolSMKqW+H22pyPMUVDqYZzPhephTmg/NODKb1IGYPHfxfhcW0EjS7wcPJNbze2i4vBWT7zT5FKF2lrQ==", + "dev": true, + "dependencies": { + "lodash-es": "^4.18.1" + }, + "peerDependencies": { + "chevrotain": "^12.0.0" + } + }, + "node_modules/comma-separated-tokens": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/comma-separated-tokens/-/comma-separated-tokens-2.0.3.tgz", + "integrity": "sha512-Fu4hJdvzeylCfQPp9SGWidpzrMs7tTrlu6Vb8XGaRGck8QSNZJJp538Wrb60Lax4fPwR64ViY468OIUTbRlGZg==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/commander": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/commander/-/commander-7.2.0.tgz", + "integrity": "sha512-QrWXB+ZQSVPmIWIhtEO9H+gwHaMGYiF5ChvoJ+K9ZGHG/sVsa6yiesAD1GC/x46sET00Xlwo1u49RVVVzvcSkw==", + "dev": true, + "engines": { + "node": ">= 10" + } + }, + "node_modules/confbox": { + "version": "0.1.8", + "resolved": "https://registry.npmjs.org/confbox/-/confbox-0.1.8.tgz", + "integrity": "sha512-RMtmw0iFkeR4YV+fUOSucriAQNb9g8zFR52MWCtl+cCZOFRNL6zeB395vPzFhEjjn4fMxXudmELnl/KF/WrK6w==", + "dev": true + }, + "node_modules/copy-anything": { + "version": "4.0.5", + "resolved": "https://registry.npmjs.org/copy-anything/-/copy-anything-4.0.5.tgz", + "integrity": "sha512-7Vv6asjS4gMOuILabD3l739tsaxFQmC+a7pLZm02zyvs8p977bL3zEgq3yDk5rn9B0PbYgIv++jmHcuUab4RhA==", + "dev": true, + "dependencies": { + "is-what": "^5.2.0" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/mesqueeb" + } + }, + "node_modules/cose-base": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/cose-base/-/cose-base-1.0.3.tgz", + "integrity": "sha512-s9whTXInMSgAp/NVXVNuVxVKzGH2qck3aQlVHxDCdAEPgtMKwc4Wq6/QKhgdEdgbLSi9rBTAcPoRa6JpiG4ksg==", + "dev": true, + "dependencies": { + "layout-base": "^1.0.0" + } + }, + "node_modules/csstype": { + "version": "3.2.3", + "resolved": "https://registry.npmjs.org/csstype/-/csstype-3.2.3.tgz", + "integrity": "sha512-z1HGKcYy2xA8AGQfwrn0PAy+PB7X/GSj3UVJW9qKyn43xWa+gl5nXmU4qqLMRzWVLFC8KusUX8T/0kCiOYpAIQ==", + "dev": true + }, + "node_modules/cytoscape": { + "version": "3.33.3", + "resolved": "https://registry.npmjs.org/cytoscape/-/cytoscape-3.33.3.tgz", + "integrity": "sha512-Gej7U+OKR+LZ8kvX7rb2HhCYJ0IhvEFsnkud4SB1PR+BUY/TsSO0dmOW59WEVLu51b1Rm+gQRKoz4bLYxGSZ2g==", + "dev": true, + "engines": { + "node": ">=0.10" + } + }, + "node_modules/cytoscape-cose-bilkent": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/cytoscape-cose-bilkent/-/cytoscape-cose-bilkent-4.1.0.tgz", + "integrity": "sha512-wgQlVIUJF13Quxiv5e1gstZ08rnZj2XaLHGoFMYXz7SkNfCDOOteKBE6SYRfA9WxxI/iBc3ajfDoc6hb/MRAHQ==", + "dev": true, + "dependencies": { + "cose-base": "^1.0.0" + }, + "peerDependencies": { + "cytoscape": "^3.2.0" + } + }, + "node_modules/cytoscape-fcose": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/cytoscape-fcose/-/cytoscape-fcose-2.2.0.tgz", + "integrity": "sha512-ki1/VuRIHFCzxWNrsshHYPs6L7TvLu3DL+TyIGEsRcvVERmxokbf5Gdk7mFxZnTdiGtnA4cfSmjZJMviqSuZrQ==", + "dev": true, + "dependencies": { + "cose-base": "^2.2.0" + }, + "peerDependencies": { + "cytoscape": "^3.2.0" + } + }, + "node_modules/cytoscape-fcose/node_modules/cose-base": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/cose-base/-/cose-base-2.2.0.tgz", + "integrity": "sha512-AzlgcsCbUMymkADOJtQm3wO9S3ltPfYOFD5033keQn9NJzIbtnZj+UdBJe7DYml/8TdbtHJW3j58SOnKhWY/5g==", + "dev": true, + "dependencies": { + "layout-base": "^2.0.0" + } + }, + "node_modules/cytoscape-fcose/node_modules/layout-base": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/layout-base/-/layout-base-2.0.1.tgz", + "integrity": "sha512-dp3s92+uNI1hWIpPGH3jK2kxE2lMjdXdr+DH8ynZHpd6PUlH6x6cbuXnoMmiNumznqaNO31xu9e79F0uuZ0JFg==", + "dev": true + }, + "node_modules/d3": { + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/d3/-/d3-7.9.0.tgz", + "integrity": "sha512-e1U46jVP+w7Iut8Jt8ri1YsPOvFpg46k+K8TpCb0P+zjCkjkPnV7WzfDJzMHy1LnA+wj5pLT1wjO901gLXeEhA==", + "dev": true, + "dependencies": { + "d3-array": "3", + "d3-axis": "3", + "d3-brush": "3", + "d3-chord": "3", + "d3-color": "3", + "d3-contour": "4", + "d3-delaunay": "6", + "d3-dispatch": "3", + "d3-drag": "3", + "d3-dsv": "3", + "d3-ease": "3", + "d3-fetch": "3", + "d3-force": "3", + "d3-format": "3", + "d3-geo": "3", + "d3-hierarchy": "3", + "d3-interpolate": "3", + "d3-path": "3", + "d3-polygon": "3", + "d3-quadtree": "3", + "d3-random": "3", + "d3-scale": "4", + "d3-scale-chromatic": "3", + "d3-selection": "3", + "d3-shape": "3", + "d3-time": "3", + "d3-time-format": "4", + "d3-timer": "3", + "d3-transition": "3", + "d3-zoom": "3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-array": { + "version": "3.2.4", + "resolved": "https://registry.npmjs.org/d3-array/-/d3-array-3.2.4.tgz", + "integrity": "sha512-tdQAmyA18i4J7wprpYq8ClcxZy3SC31QMeByyCFyRt7BVHdREQZ5lpzoe5mFEYZUWe+oq8HBvk9JjpibyEV4Jg==", + "dev": true, + "dependencies": { + "internmap": "1 - 2" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-axis": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/d3-axis/-/d3-axis-3.0.0.tgz", + "integrity": "sha512-IH5tgjV4jE/GhHkRV0HiVYPDtvfjHQlQfJHs0usq7M30XcSBvOotpmH1IgkcXsO/5gEQZD43B//fc7SRT5S+xw==", + "dev": true, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-brush": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/d3-brush/-/d3-brush-3.0.0.tgz", + "integrity": "sha512-ALnjWlVYkXsVIGlOsuWH1+3udkYFI48Ljihfnh8FZPF2QS9o+PzGLBslO0PjzVoHLZ2KCVgAM8NVkXPJB2aNnQ==", + "dev": true, + "dependencies": { + "d3-dispatch": "1 - 3", + "d3-drag": "2 - 3", + "d3-interpolate": "1 - 3", + "d3-selection": "3", + "d3-transition": "3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-chord": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-chord/-/d3-chord-3.0.1.tgz", + "integrity": "sha512-VE5S6TNa+j8msksl7HwjxMHDM2yNK3XCkusIlpX5kwauBfXuyLAtNg9jCp/iHH61tgI4sb6R/EIMWCqEIdjT/g==", + "dev": true, + "dependencies": { + "d3-path": "1 - 3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-color": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/d3-color/-/d3-color-3.1.0.tgz", + "integrity": "sha512-zg/chbXyeBtMQ1LbD/WSoW2DpC3I0mpmPdW+ynRTj/x2DAWYrIY7qeZIHidozwV24m4iavr15lNwIwLxRmOxhA==", + "dev": true, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-contour": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/d3-contour/-/d3-contour-4.0.2.tgz", + "integrity": "sha512-4EzFTRIikzs47RGmdxbeUvLWtGedDUNkTcmzoeyg4sP/dvCexO47AaQL7VKy/gul85TOxw+IBgA8US2xwbToNA==", + "dev": true, + "dependencies": { + "d3-array": "^3.2.0" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-delaunay": { + "version": "6.0.4", + "resolved": "https://registry.npmjs.org/d3-delaunay/-/d3-delaunay-6.0.4.tgz", + "integrity": "sha512-mdjtIZ1XLAM8bm/hx3WwjfHt6Sggek7qH043O8KEjDXN40xi3vx/6pYSVTwLjEgiXQTbvaouWKynLBiUZ6SK6A==", + "dev": true, + "dependencies": { + "delaunator": "5" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-dispatch": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-dispatch/-/d3-dispatch-3.0.1.tgz", + "integrity": "sha512-rzUyPU/S7rwUflMyLc1ETDeBj0NRuHKKAcvukozwhshr6g6c5d8zh4c2gQjY2bZ0dXeGLWc1PF174P2tVvKhfg==", + "dev": true, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-drag": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/d3-drag/-/d3-drag-3.0.0.tgz", + "integrity": "sha512-pWbUJLdETVA8lQNJecMxoXfH6x+mO2UQo8rSmZ+QqxcbyA3hfeprFgIT//HW2nlHChWeIIMwS2Fq+gEARkhTkg==", + "dev": true, + "dependencies": { + "d3-dispatch": "1 - 3", + "d3-selection": "3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-dsv": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-dsv/-/d3-dsv-3.0.1.tgz", + "integrity": "sha512-UG6OvdI5afDIFP9w4G0mNq50dSOsXHJaRE8arAS5o9ApWnIElp8GZw1Dun8vP8OyHOZ/QJUKUJwxiiCCnUwm+Q==", + "dev": true, + "dependencies": { + "commander": "7", + "iconv-lite": "0.6", + "rw": "1" + }, + "bin": { + "csv2json": "bin/dsv2json.js", + "csv2tsv": "bin/dsv2dsv.js", + "dsv2dsv": "bin/dsv2dsv.js", + "dsv2json": "bin/dsv2json.js", + "json2csv": "bin/json2dsv.js", + "json2dsv": "bin/json2dsv.js", + "json2tsv": "bin/json2dsv.js", + "tsv2csv": "bin/dsv2dsv.js", + "tsv2json": "bin/dsv2json.js" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-ease": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-ease/-/d3-ease-3.0.1.tgz", + "integrity": "sha512-wR/XK3D3XcLIZwpbvQwQ5fK+8Ykds1ip7A2Txe0yxncXSdq1L9skcG7blcedkOX+ZcgxGAmLX1FrRGbADwzi0w==", + "dev": true, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-fetch": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-fetch/-/d3-fetch-3.0.1.tgz", + "integrity": "sha512-kpkQIM20n3oLVBKGg6oHrUchHM3xODkTzjMoj7aWQFq5QEM+R6E4WkzT5+tojDY7yjez8KgCBRoj4aEr99Fdqw==", + "dev": true, + "dependencies": { + "d3-dsv": "1 - 3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-force": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/d3-force/-/d3-force-3.0.0.tgz", + "integrity": "sha512-zxV/SsA+U4yte8051P4ECydjD/S+qeYtnaIyAs9tgHCqfguma/aAQDjo85A9Z6EKhBirHRJHXIgJUlffT4wdLg==", + "dev": true, + "dependencies": { + "d3-dispatch": "1 - 3", + "d3-quadtree": "1 - 3", + "d3-timer": "1 - 3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-format": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/d3-format/-/d3-format-3.1.2.tgz", + "integrity": "sha512-AJDdYOdnyRDV5b6ArilzCPPwc1ejkHcoyFarqlPqT7zRYjhavcT3uSrqcMvsgh2CgoPbK3RCwyHaVyxYcP2Arg==", + "dev": true, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-geo": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/d3-geo/-/d3-geo-3.1.1.tgz", + "integrity": "sha512-637ln3gXKXOwhalDzinUgY83KzNWZRKbYubaG+fGVuc/dxO64RRljtCTnf5ecMyE1RIdtqpkVcq0IbtU2S8j2Q==", + "dev": true, + "dependencies": { + "d3-array": "2.5.0 - 3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-hierarchy": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/d3-hierarchy/-/d3-hierarchy-3.1.2.tgz", + "integrity": "sha512-FX/9frcub54beBdugHjDCdikxThEqjnR93Qt7PvQTOHxyiNCAlvMrHhclk3cD5VeAaq9fxmfRp+CnWw9rEMBuA==", + "dev": true, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-interpolate": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-interpolate/-/d3-interpolate-3.0.1.tgz", + "integrity": "sha512-3bYs1rOD33uo8aqJfKP3JWPAibgw8Zm2+L9vBKEHJ2Rg+viTR7o5Mmv5mZcieN+FRYaAOWX5SJATX6k1PWz72g==", + "dev": true, + "dependencies": { + "d3-color": "1 - 3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-path": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/d3-path/-/d3-path-3.1.0.tgz", + "integrity": "sha512-p3KP5HCf/bvjBSSKuXid6Zqijx7wIfNW+J/maPs+iwR35at5JCbLUT0LzF1cnjbCHWhqzQTIN2Jpe8pRebIEFQ==", + "dev": true, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-polygon": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-polygon/-/d3-polygon-3.0.1.tgz", + "integrity": "sha512-3vbA7vXYwfe1SYhED++fPUQlWSYTTGmFmQiany/gdbiWgU/iEyQzyymwL9SkJjFFuCS4902BSzewVGsHHmHtXg==", + "dev": true, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-quadtree": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-quadtree/-/d3-quadtree-3.0.1.tgz", + "integrity": "sha512-04xDrxQTDTCFwP5H6hRhsRcb9xxv2RzkcsygFzmkSIOJy3PeRJP7sNk3VRIbKXcog561P9oU0/rVH6vDROAgUw==", + "dev": true, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-random": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-random/-/d3-random-3.0.1.tgz", + "integrity": "sha512-FXMe9GfxTxqd5D6jFsQ+DJ8BJS4E/fT5mqqdjovykEB2oFbTMDVdg1MGFxfQW+FBOGoB++k8swBrgwSHT1cUXQ==", + "dev": true, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-sankey": { + "version": "0.12.3", + "resolved": "https://registry.npmjs.org/d3-sankey/-/d3-sankey-0.12.3.tgz", + "integrity": "sha512-nQhsBRmM19Ax5xEIPLMY9ZmJ/cDvd1BG3UVvt5h3WRxKg5zGRbvnteTyWAbzeSvlh3tW7ZEmq4VwR5mB3tutmQ==", + "dev": true, + "dependencies": { + "d3-array": "1 - 2", + "d3-shape": "^1.2.0" + } + }, + "node_modules/d3-sankey/node_modules/d3-array": { + "version": "2.12.1", + "resolved": "https://registry.npmjs.org/d3-array/-/d3-array-2.12.1.tgz", + "integrity": "sha512-B0ErZK/66mHtEsR1TkPEEkwdy+WDesimkM5gpZr5Dsg54BiTA5RXtYW5qTLIAcekaS9xfZrzBLF/OAkB3Qn1YQ==", + "dev": true, + "dependencies": { + "internmap": "^1.0.0" + } + }, + "node_modules/d3-sankey/node_modules/d3-path": { + "version": "1.0.9", + "resolved": "https://registry.npmjs.org/d3-path/-/d3-path-1.0.9.tgz", + "integrity": "sha512-VLaYcn81dtHVTjEHd8B+pbe9yHWpXKZUC87PzoFmsFrJqgFwDe/qxfp5MlfsfM1V5E/iVt0MmEbWQ7FVIXh/bg==", + "dev": true + }, + "node_modules/d3-sankey/node_modules/d3-shape": { + "version": "1.3.7", + "resolved": "https://registry.npmjs.org/d3-shape/-/d3-shape-1.3.7.tgz", + "integrity": "sha512-EUkvKjqPFUAZyOlhY5gzCxCeI0Aep04LwIRpsZ/mLFelJiUfnK56jo5JMDSE7yyP2kLSb6LtF+S5chMk7uqPqw==", + "dev": true, + "dependencies": { + "d3-path": "1" + } + }, + "node_modules/d3-sankey/node_modules/internmap": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/internmap/-/internmap-1.0.1.tgz", + "integrity": "sha512-lDB5YccMydFBtasVtxnZ3MRBHuaoE8GKsppq+EchKL2U4nK/DmEpPHNH8MZe5HkMtpSiTSOZwfN0tzYjO/lJEw==", + "dev": true + }, + "node_modules/d3-scale": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/d3-scale/-/d3-scale-4.0.2.tgz", + "integrity": "sha512-GZW464g1SH7ag3Y7hXjf8RoUuAFIqklOAq3MRl4OaWabTFJY9PN/E1YklhXLh+OQ3fM9yS2nOkCoS+WLZ6kvxQ==", + "dev": true, + "dependencies": { + "d3-array": "2.10.0 - 3", + "d3-format": "1 - 3", + "d3-interpolate": "1.2.0 - 3", + "d3-time": "2.1.1 - 3", + "d3-time-format": "2 - 4" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-scale-chromatic": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/d3-scale-chromatic/-/d3-scale-chromatic-3.1.0.tgz", + "integrity": "sha512-A3s5PWiZ9YCXFye1o246KoscMWqf8BsD9eRiJ3He7C9OBaxKhAd5TFCdEx/7VbKtxxTsu//1mMJFrEt572cEyQ==", + "dev": true, + "dependencies": { + "d3-color": "1 - 3", + "d3-interpolate": "1 - 3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-selection": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/d3-selection/-/d3-selection-3.0.0.tgz", + "integrity": "sha512-fmTRWbNMmsmWq6xJV8D19U/gw/bwrHfNXxrIN+HfZgnzqTHp9jOmKMhsTUjXOJnZOdZY9Q28y4yebKzqDKlxlQ==", + "dev": true, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-shape": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/d3-shape/-/d3-shape-3.2.0.tgz", + "integrity": "sha512-SaLBuwGm3MOViRq2ABk3eLoxwZELpH6zhl3FbAoJ7Vm1gofKx6El1Ib5z23NUEhF9AsGl7y+dzLe5Cw2AArGTA==", + "dev": true, + "dependencies": { + "d3-path": "^3.1.0" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-time": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/d3-time/-/d3-time-3.1.0.tgz", + "integrity": "sha512-VqKjzBLejbSMT4IgbmVgDjpkYrNWUYJnbCGo874u7MMKIWsILRX+OpX/gTk8MqjpT1A/c6HY2dCA77ZN0lkQ2Q==", + "dev": true, + "dependencies": { + "d3-array": "2 - 3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-time-format": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/d3-time-format/-/d3-time-format-4.1.0.tgz", + "integrity": "sha512-dJxPBlzC7NugB2PDLwo9Q8JiTR3M3e4/XANkreKSUxF8vvXKqm1Yfq4Q5dl8budlunRVlUUaDUgFt7eA8D6NLg==", + "dev": true, + "dependencies": { + "d3-time": "1 - 3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-timer": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-timer/-/d3-timer-3.0.1.tgz", + "integrity": "sha512-ndfJ/JxxMd3nw31uyKoY2naivF+r29V+Lc0svZxe1JvvIRmi8hUsrMvdOwgS1o6uBHmiz91geQ0ylPP0aj1VUA==", + "dev": true, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-transition": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-transition/-/d3-transition-3.0.1.tgz", + "integrity": "sha512-ApKvfjsSR6tg06xrL434C0WydLr7JewBB3V+/39RMHsaXTOG0zmt/OAXeng5M5LBm0ojmxJrpomQVZ1aPvBL4w==", + "dev": true, + "dependencies": { + "d3-color": "1 - 3", + "d3-dispatch": "1 - 3", + "d3-ease": "1 - 3", + "d3-interpolate": "1 - 3", + "d3-timer": "1 - 3" + }, + "engines": { + "node": ">=12" + }, + "peerDependencies": { + "d3-selection": "2 - 3" + } + }, + "node_modules/d3-zoom": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/d3-zoom/-/d3-zoom-3.0.0.tgz", + "integrity": "sha512-b8AmV3kfQaqWAuacbPuNbL6vahnOJflOhexLzMMNLga62+/nh0JzvJ0aO/5a5MVgUFGS7Hu1P9P03o3fJkDCyw==", + "dev": true, + "dependencies": { + "d3-dispatch": "1 - 3", + "d3-drag": "2 - 3", + "d3-interpolate": "1 - 3", + "d3-selection": "2 - 3", + "d3-transition": "2 - 3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/dagre-d3-es": { + "version": "7.0.14", + "resolved": "https://registry.npmjs.org/dagre-d3-es/-/dagre-d3-es-7.0.14.tgz", + "integrity": "sha512-P4rFMVq9ESWqmOgK+dlXvOtLwYg0i7u0HBGJER0LZDJT2VHIPAMZ/riPxqJceWMStH5+E61QxFra9kIS3AqdMg==", + "dev": true, + "dependencies": { + "d3": "^7.9.0", + "lodash-es": "^4.17.21" + } + }, + "node_modules/dayjs": { + "version": "1.11.20", + "resolved": "https://registry.npmjs.org/dayjs/-/dayjs-1.11.20.tgz", + "integrity": "sha512-YbwwqR/uYpeoP4pu043q+LTDLFBLApUP6VxRihdfNTqu4ubqMlGDLd6ErXhEgsyvY0K6nCs7nggYumAN+9uEuQ==", + "dev": true + }, + "node_modules/delaunator": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/delaunator/-/delaunator-5.1.0.tgz", + "integrity": "sha512-AGrQ4QSgssa1NGmWmLPqN5NY2KajF5MqxetNEO+o0n3ZwZZeTmt7bBnvzHWrmkZFxGgr4HdyFgelzgi06otLuQ==", + "dev": true, + "dependencies": { + "robust-predicates": "^3.0.2" + } + }, + "node_modules/dequal": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/dequal/-/dequal-2.0.3.tgz", + "integrity": "sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/devlop": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/devlop/-/devlop-1.1.0.tgz", + "integrity": "sha512-RWmIqhcFf1lRYBvNmr7qTNuyCt/7/ns2jbpp1+PalgE/rDQcBT0fioSMUpJ93irlUhC5hrg4cYqe6U+0ImW0rA==", + "dev": true, + "dependencies": { + "dequal": "^2.0.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/dompurify": { + "version": "3.4.2", + "resolved": "https://registry.npmjs.org/dompurify/-/dompurify-3.4.2.tgz", + "integrity": "sha512-lHeS9SA/IKeIFFyYciHBr2n0v1VMPlSj843HdLOwjb2OxNwdq9Xykxqhk+FE42MzAdHvInbAolSE4mhahPpjXA==", + "dev": true, + "optionalDependencies": { + "@types/trusted-types": "^2.0.7" + } + }, + "node_modules/emoji-regex-xs": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/emoji-regex-xs/-/emoji-regex-xs-1.0.0.tgz", + "integrity": "sha512-LRlerrMYoIDrT6jgpeZ2YYl/L8EulRTt5hQcYjy5AInh7HWXKimpqx68aknBFpGL2+/IcogTcaydJEgaTmOpDg==", + "dev": true + }, + "node_modules/entities": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/entities/-/entities-7.0.1.tgz", + "integrity": "sha512-TWrgLOFUQTH994YUyl1yT4uyavY5nNB5muff+RtWaqNVCAK408b5ZnnbNAUEWLTCpum9w6arT70i1XdQ4UeOPA==", + "dev": true, + "engines": { + "node": ">=0.12" + }, + "funding": { + "url": "https://github.com/fb55/entities?sponsor=1" + } + }, + "node_modules/esbuild": { + "version": "0.21.5", + "resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.21.5.tgz", + "integrity": "sha512-mg3OPMV4hXywwpoDxu3Qda5xCKQi+vCTZq8S9J/EpkhB2HzKXq4SNFZE3+NK93JYxc8VMSep+lOUSC/RVKaBqw==", + "dev": true, + "hasInstallScript": true, + "bin": { + "esbuild": "bin/esbuild" + }, + "engines": { + "node": ">=12" + }, + "optionalDependencies": { + "@esbuild/aix-ppc64": "0.21.5", + "@esbuild/android-arm": "0.21.5", + "@esbuild/android-arm64": "0.21.5", + "@esbuild/android-x64": "0.21.5", + "@esbuild/darwin-arm64": "0.21.5", + "@esbuild/darwin-x64": "0.21.5", + "@esbuild/freebsd-arm64": "0.21.5", + "@esbuild/freebsd-x64": "0.21.5", + "@esbuild/linux-arm": "0.21.5", + "@esbuild/linux-arm64": "0.21.5", + "@esbuild/linux-ia32": "0.21.5", + "@esbuild/linux-loong64": "0.21.5", + "@esbuild/linux-mips64el": "0.21.5", + "@esbuild/linux-ppc64": "0.21.5", + "@esbuild/linux-riscv64": "0.21.5", + "@esbuild/linux-s390x": "0.21.5", + "@esbuild/linux-x64": "0.21.5", + "@esbuild/netbsd-x64": "0.21.5", + "@esbuild/openbsd-x64": "0.21.5", + "@esbuild/sunos-x64": "0.21.5", + "@esbuild/win32-arm64": "0.21.5", + "@esbuild/win32-ia32": "0.21.5", + "@esbuild/win32-x64": "0.21.5" + } + }, + "node_modules/estree-walker": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/estree-walker/-/estree-walker-2.0.2.tgz", + "integrity": "sha512-Rfkk/Mp/DL7JVje3u18FxFujQlTNR2q6QfMSMB7AvCBx91NGj/ba3kCfza0f6dVDbw7YlRf/nDrn7pQrCCyQ/w==", + "dev": true + }, + "node_modules/focus-trap": { + "version": "7.8.0", + "resolved": "https://registry.npmjs.org/focus-trap/-/focus-trap-7.8.0.tgz", + "integrity": "sha512-/yNdlIkpWbM0ptxno3ONTuf+2g318kh2ez3KSeZN5dZ8YC6AAmgeWz+GasYYiBJPFaYcSAPeu4GfhUaChzIJXA==", + "dev": true, + "dependencies": { + "tabbable": "^6.4.0" + } + }, + "node_modules/fsevents": { + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.3.tgz", + "integrity": "sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==", + "dev": true, + "hasInstallScript": true, + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": "^8.16.0 || ^10.6.0 || >=11.0.0" + } + }, + "node_modules/hachure-fill": { + "version": "0.5.2", + "resolved": "https://registry.npmjs.org/hachure-fill/-/hachure-fill-0.5.2.tgz", + "integrity": "sha512-3GKBOn+m2LX9iq+JC1064cSFprJY4jL1jCXTcpnfER5HYE2l/4EfWSGzkPa/ZDBmYI0ZOEj5VHV/eKnPGkHuOg==", + "dev": true + }, + "node_modules/hast-util-to-html": { + "version": "9.0.5", + "resolved": "https://registry.npmjs.org/hast-util-to-html/-/hast-util-to-html-9.0.5.tgz", + "integrity": "sha512-OguPdidb+fbHQSU4Q4ZiLKnzWo8Wwsf5bZfbvu7//a9oTYoqD/fWpe96NuHkoS9h0ccGOTe0C4NGXdtS0iObOw==", + "dev": true, + "dependencies": { + "@types/hast": "^3.0.0", + "@types/unist": "^3.0.0", + "ccount": "^2.0.0", + "comma-separated-tokens": "^2.0.0", + "hast-util-whitespace": "^3.0.0", + "html-void-elements": "^3.0.0", + "mdast-util-to-hast": "^13.0.0", + "property-information": "^7.0.0", + "space-separated-tokens": "^2.0.0", + "stringify-entities": "^4.0.0", + "zwitch": "^2.0.4" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/hast-util-whitespace": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/hast-util-whitespace/-/hast-util-whitespace-3.0.0.tgz", + "integrity": "sha512-88JUN06ipLwsnv+dVn+OIYOvAuvBMy/Qoi6O7mQHxdPXpjy+Cd6xRkWwux7DKO+4sYILtLBRIKgsdpS2gQc7qw==", + "dev": true, + "dependencies": { + "@types/hast": "^3.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/hookable": { + "version": "5.5.3", + "resolved": "https://registry.npmjs.org/hookable/-/hookable-5.5.3.tgz", + "integrity": "sha512-Yc+BQe8SvoXH1643Qez1zqLRmbA5rCL+sSmk6TVos0LWVfNIB7PGncdlId77WzLGSIB5KaWgTaNTs2lNVEI6VQ==", + "dev": true + }, + "node_modules/html-void-elements": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/html-void-elements/-/html-void-elements-3.0.0.tgz", + "integrity": "sha512-bEqo66MRXsUGxWHV5IP0PUiAWwoEjba4VCzg0LjFJBpchPaTfyfCKTG6bc5F8ucKec3q5y6qOdGyYTSBEvhCrg==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/iconv-lite": { + "version": "0.6.3", + "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.6.3.tgz", + "integrity": "sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==", + "dev": true, + "dependencies": { + "safer-buffer": ">= 2.1.2 < 3.0.0" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/internmap": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/internmap/-/internmap-2.0.3.tgz", + "integrity": "sha512-5Hh7Y1wQbvY5ooGgPbDaL5iYLAPzMTUrjMulskHLH6wnv/A+1q5rgEaiuqEjB+oxGXIVZs1FF+R/KPN3ZSQYYg==", + "dev": true, + "engines": { + "node": ">=12" + } + }, + "node_modules/is-what": { + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/is-what/-/is-what-5.5.0.tgz", + "integrity": "sha512-oG7cgbmg5kLYae2N5IVd3jm2s+vldjxJzK1pcu9LfpGuQ93MQSzo0okvRna+7y5ifrD+20FE8FvjusyGaz14fw==", + "dev": true, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/mesqueeb" + } + }, + "node_modules/katex": { + "version": "0.16.45", + "resolved": "https://registry.npmjs.org/katex/-/katex-0.16.45.tgz", + "integrity": "sha512-pQpZbdBu7wCTmQUh7ufPmLr0pFoObnGUoL/yhtwJDgmmQpbkg/0HSVti25Fu4rmd1oCR6NGWe9vqTWuWv3GcNA==", + "dev": true, + "funding": [ + "https://opencollective.com/katex", + "https://github.com/sponsors/katex" + ], + "dependencies": { + "commander": "^8.3.0" + }, + "bin": { + "katex": "cli.js" + } + }, + "node_modules/katex/node_modules/commander": { + "version": "8.3.0", + "resolved": "https://registry.npmjs.org/commander/-/commander-8.3.0.tgz", + "integrity": "sha512-OkTL9umf+He2DZkUq8f8J9of7yL6RJKI24dVITBmNfZBmri9zYZQrKkuXiKhyfPSu8tUhnVBB1iKXevvnlR4Ww==", + "dev": true, + "engines": { + "node": ">= 12" + } + }, + "node_modules/khroma": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/khroma/-/khroma-2.1.0.tgz", + "integrity": "sha512-Ls993zuzfayK269Svk9hzpeGUKob/sIgZzyHYdjQoAdQetRKpOLj+k/QQQ/6Qi0Yz65mlROrfd+Ev+1+7dz9Kw==", + "dev": true + }, + "node_modules/langium": { + "version": "4.2.3", + "resolved": "https://registry.npmjs.org/langium/-/langium-4.2.3.tgz", + "integrity": "sha512-sOPIi4hISFnY7twwV97ca1TsxpBtXq0URu/LL1AvxwccPG/RIBBlKS7a/f/EL6w8lTNaS0EFs/F+IdSOaqYpng==", + "dev": true, + "dependencies": { + "@chevrotain/regexp-to-ast": "~12.0.0", + "chevrotain": "~12.0.0", + "chevrotain-allstar": "~0.4.3", + "vscode-languageserver": "~9.0.1", + "vscode-languageserver-textdocument": "~1.0.11", + "vscode-uri": "~3.1.0" + }, + "engines": { + "node": ">=20.10.0", + "npm": ">=10.2.3" + } + }, + "node_modules/layout-base": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/layout-base/-/layout-base-1.0.2.tgz", + "integrity": "sha512-8h2oVEZNktL4BH2JCOI90iD1yXwL6iNW7KcCKT2QZgQJR2vbqDsldCTPRU9NifTCqHZci57XvQQ15YTu+sTYPg==", + "dev": true + }, + "node_modules/lodash-es": { + "version": "4.18.1", + "resolved": "https://registry.npmjs.org/lodash-es/-/lodash-es-4.18.1.tgz", + "integrity": "sha512-J8xewKD/Gk22OZbhpOVSwcs60zhd95ESDwezOFuA3/099925PdHJ7OFHNTGtajL3AlZkykD32HykiMo+BIBI8A==", + "dev": true + }, + "node_modules/magic-string": { + "version": "0.30.21", + "resolved": "https://registry.npmjs.org/magic-string/-/magic-string-0.30.21.tgz", + "integrity": "sha512-vd2F4YUyEXKGcLHoq+TEyCjxueSeHnFxyyjNp80yg0XV4vUhnDer/lvvlqM/arB5bXQN5K2/3oinyCRyx8T2CQ==", + "dev": true, + "dependencies": { + "@jridgewell/sourcemap-codec": "^1.5.5" + } + }, + "node_modules/mark.js": { + "version": "8.11.1", + "resolved": "https://registry.npmjs.org/mark.js/-/mark.js-8.11.1.tgz", + "integrity": "sha512-1I+1qpDt4idfgLQG+BNWmrqku+7/2bi5nLf4YwF8y8zXvmfiTBY3PV3ZibfrjBueCByROpuBjLLFCajqkgYoLQ==", + "dev": true + }, + "node_modules/marked": { + "version": "16.4.2", + "resolved": "https://registry.npmjs.org/marked/-/marked-16.4.2.tgz", + "integrity": "sha512-TI3V8YYWvkVf3KJe1dRkpnjs68JUPyEa5vjKrp1XEEJUAOaQc+Qj+L1qWbPd0SJuAdQkFU0h73sXXqwDYxsiDA==", + "dev": true, + "bin": { + "marked": "bin/marked.js" + }, + "engines": { + "node": ">= 20" + } + }, + "node_modules/mdast-util-to-hast": { + "version": "13.2.1", + "resolved": "https://registry.npmjs.org/mdast-util-to-hast/-/mdast-util-to-hast-13.2.1.tgz", + "integrity": "sha512-cctsq2wp5vTsLIcaymblUriiTcZd0CwWtCbLvrOzYCDZoWyMNV8sZ7krj09FSnsiJi3WVsHLM4k6Dq/yaPyCXA==", + "dev": true, + "dependencies": { + "@types/hast": "^3.0.0", + "@types/mdast": "^4.0.0", + "@ungap/structured-clone": "^1.0.0", + "devlop": "^1.0.0", + "micromark-util-sanitize-uri": "^2.0.0", + "trim-lines": "^3.0.0", + "unist-util-position": "^5.0.0", + "unist-util-visit": "^5.0.0", + "vfile": "^6.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mermaid": { + "version": "11.14.0", + "resolved": "https://registry.npmjs.org/mermaid/-/mermaid-11.14.0.tgz", + "integrity": "sha512-GSGloRsBs+JINmmhl0JDwjpuezCsHB4WGI4NASHxL3fHo3o/BRXTxhDLKnln8/Q0lRFRyDdEjmk1/d5Sn1Xz8g==", + "dev": true, + "dependencies": { + "@braintree/sanitize-url": "^7.1.1", + "@iconify/utils": "^3.0.2", + "@mermaid-js/parser": "^1.1.0", + "@types/d3": "^7.4.3", + "@upsetjs/venn.js": "^2.0.0", + "cytoscape": "^3.33.1", + "cytoscape-cose-bilkent": "^4.1.0", + "cytoscape-fcose": "^2.2.0", + "d3": "^7.9.0", + "d3-sankey": "^0.12.3", + "dagre-d3-es": "7.0.14", + "dayjs": "^1.11.19", + "dompurify": "^3.3.1", + "katex": "^0.16.25", + "khroma": "^2.1.0", + "lodash-es": "^4.17.23", + "marked": "^16.3.0", + "roughjs": "^4.6.6", + "stylis": "^4.3.6", + "ts-dedent": "^2.2.0", + "uuid": "^11.1.0" + } + }, + "node_modules/micromark-util-character": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.1.tgz", + "integrity": "sha512-wv8tdUTJ3thSFFFJKtpYKOYiGP2+v96Hvk4Tu8KpCAsTMs6yi+nVmGh1syvSCsaxz45J6Jbw+9DD6g97+NV67Q==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "micromark-util-symbol": "^2.0.0", + "micromark-util-types": "^2.0.0" + } + }, + "node_modules/micromark-util-encode": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-encode/-/micromark-util-encode-2.0.1.tgz", + "integrity": "sha512-c3cVx2y4KqUnwopcO9b/SCdo2O67LwJJ/UyqGfbigahfegL9myoEFoDYZgkT7f36T0bLrM9hZTAaAyH+PCAXjw==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ] + }, + "node_modules/micromark-util-sanitize-uri": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-sanitize-uri/-/micromark-util-sanitize-uri-2.0.1.tgz", + "integrity": "sha512-9N9IomZ/YuGGZZmQec1MbgxtlgougxTodVwDzzEouPKo3qFWvymFHWcnDi2vzV1ff6kas9ucW+o3yzJK9YB1AQ==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "micromark-util-character": "^2.0.0", + "micromark-util-encode": "^2.0.0", + "micromark-util-symbol": "^2.0.0" + } + }, + "node_modules/micromark-util-symbol": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.1.tgz", + "integrity": "sha512-vs5t8Apaud9N28kgCrRUdEed4UJ+wWNvicHLPxCa9ENlYuAY31M0ETy5y1vA33YoNPDFTghEbnh6efaE8h4x0Q==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ] + }, + "node_modules/micromark-util-types": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/micromark-util-types/-/micromark-util-types-2.0.2.tgz", + "integrity": "sha512-Yw0ECSpJoViF1qTU4DC6NwtC4aWGt1EkzaQB8KPPyCRR8z9TWeV0HbEFGTO+ZY1wB22zmxnJqhPyTpOVCpeHTA==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ] + }, + "node_modules/minisearch": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/minisearch/-/minisearch-7.2.0.tgz", + "integrity": "sha512-dqT2XBYUOZOiC5t2HRnwADjhNS2cecp9u+TJRiJ1Qp/f5qjkeT5APcGPjHw+bz89Ms8Jp+cG4AlE+QZ/QnDglg==", + "dev": true + }, + "node_modules/mitt": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/mitt/-/mitt-3.0.1.tgz", + "integrity": "sha512-vKivATfr97l2/QBCYAkXYDbrIWPM2IIKEl7YPhjCvKlG3kE2gm+uBo6nEXK3M5/Ffh/FLpKExzOQ3JJoJGFKBw==", + "dev": true + }, + "node_modules/mlly": { + "version": "1.8.2", + "resolved": "https://registry.npmjs.org/mlly/-/mlly-1.8.2.tgz", + "integrity": "sha512-d+ObxMQFmbt10sretNDytwt85VrbkhhUA/JBGm1MPaWJ65Cl4wOgLaB1NYvJSZ0Ef03MMEU/0xpPMXUIQ29UfA==", + "dev": true, + "dependencies": { + "acorn": "^8.16.0", + "pathe": "^2.0.3", + "pkg-types": "^1.3.1", + "ufo": "^1.6.3" + } + }, + "node_modules/nanoid": { + "version": "3.3.12", + "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.12.tgz", + "integrity": "sha512-ZB9RH/39qpq5Vu6Y+NmUaFhQR6pp+M2Xt76XBnEwDaGcVAqhlvxrl3B2bKS5D3NH3QR76v3aSrKaF/Kiy7lEtQ==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/ai" + } + ], + "bin": { + "nanoid": "bin/nanoid.cjs" + }, + "engines": { + "node": "^10 || ^12 || ^13.7 || ^14 || >=15.0.1" + } + }, + "node_modules/non-layered-tidy-tree-layout": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/non-layered-tidy-tree-layout/-/non-layered-tidy-tree-layout-2.0.2.tgz", + "integrity": "sha512-gkXMxRzUH+PB0ax9dUN0yYF0S25BqeAYqhgMaLUFmpXLEk7Fcu8f4emJuOAY0V8kjDICxROIKsTAKsV/v355xw==", + "dev": true, + "optional": true + }, + "node_modules/oniguruma-to-es": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/oniguruma-to-es/-/oniguruma-to-es-3.1.1.tgz", + "integrity": "sha512-bUH8SDvPkH3ho3dvwJwfonjlQ4R80vjyvrU8YpxuROddv55vAEJrTuCuCVUhhsHbtlD9tGGbaNApGQckXhS8iQ==", + "dev": true, + "dependencies": { + "emoji-regex-xs": "^1.0.0", + "regex": "^6.0.1", + "regex-recursion": "^6.0.2" + } + }, + "node_modules/package-manager-detector": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/package-manager-detector/-/package-manager-detector-1.6.0.tgz", + "integrity": "sha512-61A5ThoTiDG/C8s8UMZwSorAGwMJ0ERVGj2OjoW5pAalsNOg15+iQiPzrLJ4jhZ1HJzmC2PIHT2oEiH3R5fzNA==", + "dev": true + }, + "node_modules/path-data-parser": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/path-data-parser/-/path-data-parser-0.1.0.tgz", + "integrity": "sha512-NOnmBpt5Y2RWbuv0LMzsayp3lVylAHLPUTut412ZA3l+C4uw4ZVkQbjShYCQ8TCpUMdPapr4YjUqLYD6v68j+w==", + "dev": true + }, + "node_modules/pathe": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/pathe/-/pathe-2.0.3.tgz", + "integrity": "sha512-WUjGcAqP1gQacoQe+OBJsFA7Ld4DyXuUIjZ5cc75cLHvJ7dtNsTugphxIADwspS+AraAUePCKrSVtPLFj/F88w==", + "dev": true + }, + "node_modules/perfect-debounce": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/perfect-debounce/-/perfect-debounce-1.0.0.tgz", + "integrity": "sha512-xCy9V055GLEqoFaHoC1SoLIaLmWctgCUaBaWxDZ7/Zx4CTyX7cJQLJOok/orfjZAh9kEYpjJa4d0KcJmCbctZA==", + "dev": true + }, + "node_modules/picocolors": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.1.1.tgz", + "integrity": "sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA==", + "dev": true + }, + "node_modules/pkg-types": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/pkg-types/-/pkg-types-1.3.1.tgz", + "integrity": "sha512-/Jm5M4RvtBFVkKWRu2BLUTNP8/M2a+UwuAX+ae4770q1qVGtfjG+WTCupoZixokjmHiry8uI+dlY8KXYV5HVVQ==", + "dev": true, + "dependencies": { + "confbox": "^0.1.8", + "mlly": "^1.7.4", + "pathe": "^2.0.1" + } + }, + "node_modules/points-on-curve": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/points-on-curve/-/points-on-curve-0.2.0.tgz", + "integrity": "sha512-0mYKnYYe9ZcqMCWhUjItv/oHjvgEsfKvnUTg8sAtnHr3GVy7rGkXCb6d5cSyqrWqL4k81b9CPg3urd+T7aop3A==", + "dev": true + }, + "node_modules/points-on-path": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/points-on-path/-/points-on-path-0.2.1.tgz", + "integrity": "sha512-25ClnWWuw7JbWZcgqY/gJ4FQWadKxGWk+3kR/7kD0tCaDtPPMj7oHu2ToLaVhfpnHrZzYby2w6tUA0eOIuUg8g==", + "dev": true, + "dependencies": { + "path-data-parser": "0.1.0", + "points-on-curve": "0.2.0" + } + }, + "node_modules/postcss": { + "version": "8.5.13", + "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.5.13.tgz", + "integrity": "sha512-qif0+jGGZoLWdHey3UFHHWP0H7Gbmsk8T5VEqyYFbWqPr1XqvLGBbk/sl8V5exGmcYJklJOhOQq1pV9IcsiFag==", + "dev": true, + "funding": [ + { + "type": "opencollective", + "url": "https://opencollective.com/postcss/" + }, + { + "type": "tidelift", + "url": "https://tidelift.com/funding/github/npm/postcss" + }, + { + "type": "github", + "url": "https://github.com/sponsors/ai" + } + ], + "dependencies": { + "nanoid": "^3.3.11", + "picocolors": "^1.1.1", + "source-map-js": "^1.2.1" + }, + "engines": { + "node": "^10 || ^12 || >=14" + } + }, + "node_modules/preact": { + "version": "10.29.1", + "resolved": "https://registry.npmjs.org/preact/-/preact-10.29.1.tgz", + "integrity": "sha512-gQCLc/vWroE8lIpleXtdJhTFDogTdZG9AjMUpVkDf2iTCNwYNWA+u16dL41TqUDJO4gm2IgrcMv3uTpjd4Pwmg==", + "dev": true, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/preact" + } + }, + "node_modules/property-information": { + "version": "7.1.0", + "resolved": "https://registry.npmjs.org/property-information/-/property-information-7.1.0.tgz", + "integrity": "sha512-TwEZ+X+yCJmYfL7TPUOcvBZ4QfoT5YenQiJuX//0th53DE6w0xxLEtfK3iyryQFddXuvkIk51EEgrJQ0WJkOmQ==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/regex": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/regex/-/regex-6.1.0.tgz", + "integrity": "sha512-6VwtthbV4o/7+OaAF9I5L5V3llLEsoPyq9P1JVXkedTP33c7MfCG0/5NOPcSJn0TzXcG9YUrR0gQSWioew3LDg==", + "dev": true, + "dependencies": { + "regex-utilities": "^2.3.0" + } + }, + "node_modules/regex-recursion": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/regex-recursion/-/regex-recursion-6.0.2.tgz", + "integrity": "sha512-0YCaSCq2VRIebiaUviZNs0cBz1kg5kVS2UKUfNIx8YVs1cN3AV7NTctO5FOKBA+UT2BPJIWZauYHPqJODG50cg==", + "dev": true, + "dependencies": { + "regex-utilities": "^2.3.0" + } + }, + "node_modules/regex-utilities": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/regex-utilities/-/regex-utilities-2.3.0.tgz", + "integrity": "sha512-8VhliFJAWRaUiVvREIiW2NXXTmHs4vMNnSzuJVhscgmGav3g9VDxLrQndI3dZZVVdp0ZO/5v0xmX516/7M9cng==", + "dev": true + }, + "node_modules/rfdc": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/rfdc/-/rfdc-1.4.1.tgz", + "integrity": "sha512-q1b3N5QkRUWUl7iyylaaj3kOpIT0N2i9MqIEQXP73GVsN9cw3fdx8X63cEmWhJGi2PPCF23Ijp7ktmd39rawIA==", + "dev": true + }, + "node_modules/robust-predicates": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/robust-predicates/-/robust-predicates-3.0.3.tgz", + "integrity": "sha512-NS3levdsRIUOmiJ8FZWCP7LG3QpJyrs/TE0Zpf1yvZu8cAJJ6QMW92H1c7kWpdIHo8RvmLxN/o2JXTKHp74lUA==", + "dev": true + }, + "node_modules/rollup": { + "version": "4.60.2", + "resolved": "https://registry.npmjs.org/rollup/-/rollup-4.60.2.tgz", + "integrity": "sha512-J9qZyW++QK/09NyN/zeO0dG/1GdGfyp9lV8ajHnRVLfo/uFsbji5mHnDgn/qYdUHyCkM2N+8VyspgZclfAh0eQ==", + "dev": true, + "dependencies": { + "@types/estree": "1.0.8" + }, + "bin": { + "rollup": "dist/bin/rollup" + }, + "engines": { + "node": ">=18.0.0", + "npm": ">=8.0.0" + }, + "optionalDependencies": { + "@rollup/rollup-android-arm-eabi": "4.60.2", + "@rollup/rollup-android-arm64": "4.60.2", + "@rollup/rollup-darwin-arm64": "4.60.2", + "@rollup/rollup-darwin-x64": "4.60.2", + "@rollup/rollup-freebsd-arm64": "4.60.2", + "@rollup/rollup-freebsd-x64": "4.60.2", + "@rollup/rollup-linux-arm-gnueabihf": "4.60.2", + "@rollup/rollup-linux-arm-musleabihf": "4.60.2", + "@rollup/rollup-linux-arm64-gnu": "4.60.2", + "@rollup/rollup-linux-arm64-musl": "4.60.2", + "@rollup/rollup-linux-loong64-gnu": "4.60.2", + "@rollup/rollup-linux-loong64-musl": "4.60.2", + "@rollup/rollup-linux-ppc64-gnu": "4.60.2", + "@rollup/rollup-linux-ppc64-musl": "4.60.2", + "@rollup/rollup-linux-riscv64-gnu": "4.60.2", + "@rollup/rollup-linux-riscv64-musl": "4.60.2", + "@rollup/rollup-linux-s390x-gnu": "4.60.2", + "@rollup/rollup-linux-x64-gnu": "4.60.2", + "@rollup/rollup-linux-x64-musl": "4.60.2", + "@rollup/rollup-openbsd-x64": "4.60.2", + "@rollup/rollup-openharmony-arm64": "4.60.2", + "@rollup/rollup-win32-arm64-msvc": "4.60.2", + "@rollup/rollup-win32-ia32-msvc": "4.60.2", + "@rollup/rollup-win32-x64-gnu": "4.60.2", + "@rollup/rollup-win32-x64-msvc": "4.60.2", + "fsevents": "~2.3.2" + } + }, + "node_modules/roughjs": { + "version": "4.6.6", + "resolved": "https://registry.npmjs.org/roughjs/-/roughjs-4.6.6.tgz", + "integrity": "sha512-ZUz/69+SYpFN/g/lUlo2FXcIjRkSu3nDarreVdGGndHEBJ6cXPdKguS8JGxwj5HA5xIbVKSmLgr5b3AWxtRfvQ==", + "dev": true, + "dependencies": { + "hachure-fill": "^0.5.2", + "path-data-parser": "^0.1.0", + "points-on-curve": "^0.2.0", + "points-on-path": "^0.2.1" + } + }, + "node_modules/rw": { + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/rw/-/rw-1.3.3.tgz", + "integrity": "sha512-PdhdWy89SiZogBLaw42zdeqtRJ//zFd2PgQavcICDUgJT5oW10QCRKbJ6bg4r0/UY2M6BWd5tkxuGFRvCkgfHQ==", + "dev": true + }, + "node_modules/safer-buffer": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", + "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==", + "dev": true + }, + "node_modules/search-insights": { + "version": "2.17.3", + "resolved": "https://registry.npmjs.org/search-insights/-/search-insights-2.17.3.tgz", + "integrity": "sha512-RQPdCYTa8A68uM2jwxoY842xDhvx3E5LFL1LxvxCNMev4o5mLuokczhzjAgGwUZBAmOKZknArSxLKmXtIi2AxQ==", + "dev": true, + "peer": true + }, + "node_modules/shiki": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/shiki/-/shiki-2.5.0.tgz", + "integrity": "sha512-mI//trrsaiCIPsja5CNfsyNOqgAZUb6VpJA+340toL42UpzQlXpwRV9nch69X6gaUxrr9kaOOa6e3y3uAkGFxQ==", + "dev": true, + "dependencies": { + "@shikijs/core": "2.5.0", + "@shikijs/engine-javascript": "2.5.0", + "@shikijs/engine-oniguruma": "2.5.0", + "@shikijs/langs": "2.5.0", + "@shikijs/themes": "2.5.0", + "@shikijs/types": "2.5.0", + "@shikijs/vscode-textmate": "^10.0.2", + "@types/hast": "^3.0.4" + } + }, + "node_modules/source-map-js": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/source-map-js/-/source-map-js-1.2.1.tgz", + "integrity": "sha512-UXWMKhLOwVKb728IUtQPXxfYU+usdybtUrK/8uGE8CQMvrhOpwvzDBwj0QhSL7MQc7vIsISBG8VQ8+IDQxpfQA==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/space-separated-tokens": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/space-separated-tokens/-/space-separated-tokens-2.0.2.tgz", + "integrity": "sha512-PEGlAwrG8yXGXRjW32fGbg66JAlOAwbObuqVoJpv/mRgoWDQfgH1wDPvtzWyUSNAXBGSk8h755YDbbcEy3SH2Q==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/speakingurl": { + "version": "14.0.1", + "resolved": "https://registry.npmjs.org/speakingurl/-/speakingurl-14.0.1.tgz", + "integrity": "sha512-1POYv7uv2gXoyGFpBCmpDVSNV74IfsWlDW216UPjbWufNf+bSU6GdbDsxdcxtfwb4xlI3yxzOTKClUosxARYrQ==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/stringify-entities": { + "version": "4.0.4", + "resolved": "https://registry.npmjs.org/stringify-entities/-/stringify-entities-4.0.4.tgz", + "integrity": "sha512-IwfBptatlO+QCJUo19AqvrPNqlVMpW9YEL2LIVY+Rpv2qsjCGxaDLNRgeGsQWJhfItebuJhsGSLjaBbNSQ+ieg==", + "dev": true, + "dependencies": { + "character-entities-html4": "^2.0.0", + "character-entities-legacy": "^3.0.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/stylis": { + "version": "4.4.0", + "resolved": "https://registry.npmjs.org/stylis/-/stylis-4.4.0.tgz", + "integrity": "sha512-5Z9ZpRzfuH6l/UAvCPAPUo3665Nk2wLaZU3x+TLHKVzIz33+sbJqbtrYoC3KD4/uVOr2Zp+L0LySezP9OHV9yA==", + "dev": true + }, + "node_modules/superjson": { + "version": "2.2.6", + "resolved": "https://registry.npmjs.org/superjson/-/superjson-2.2.6.tgz", + "integrity": "sha512-H+ue8Zo4vJmV2nRjpx86P35lzwDT3nItnIsocgumgr0hHMQ+ZGq5vrERg9kJBo5AWGmxZDhzDo+WVIJqkB0cGA==", + "dev": true, + "dependencies": { + "copy-anything": "^4" + }, + "engines": { + "node": ">=16" + } + }, + "node_modules/tabbable": { + "version": "6.4.0", + "resolved": "https://registry.npmjs.org/tabbable/-/tabbable-6.4.0.tgz", + "integrity": "sha512-05PUHKSNE8ou2dwIxTngl4EzcnsCDZGJ/iCLtDflR/SHB/ny14rXc+qU5P4mG9JkusiV7EivzY9Mhm55AzAvCg==", + "dev": true + }, + "node_modules/tinyexec": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/tinyexec/-/tinyexec-1.1.2.tgz", + "integrity": "sha512-dAqSqE/RabpBKI8+h26GfLq6Vb3JVXs30XYQjdMjaj/c2tS8IYYMbIzP599KtRj7c57/wYApb3QjgRgXmrCukA==", + "dev": true, + "engines": { + "node": ">=18" + } + }, + "node_modules/trim-lines": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/trim-lines/-/trim-lines-3.0.1.tgz", + "integrity": "sha512-kRj8B+YHZCc9kQYdWfJB2/oUl9rA99qbowYYBtr4ui4mZyAQ2JpvVBd/6U2YloATfqBhBTSMhTpgBHtU0Mf3Rg==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/ts-dedent": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/ts-dedent/-/ts-dedent-2.2.0.tgz", + "integrity": "sha512-q5W7tVM71e2xjHZTlgfTDoPF/SmqKG5hddq9SzR49CH2hayqRKJtQ4mtRlSxKaJlR/+9rEM+mnBHf7I2/BQcpQ==", + "dev": true, + "engines": { + "node": ">=6.10" + } + }, + "node_modules/ufo": { + "version": "1.6.4", + "resolved": "https://registry.npmjs.org/ufo/-/ufo-1.6.4.tgz", + "integrity": "sha512-JFNbkD1Svwe0KvGi8GOeLcP4kAWQ609twvCdcHxq1oSL8svv39ZuSvajcD8B+5D0eL4+s1Is2D/O6KN3qcTeRA==", + "dev": true + }, + "node_modules/unist-util-is": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/unist-util-is/-/unist-util-is-6.0.1.tgz", + "integrity": "sha512-LsiILbtBETkDz8I9p1dQ0uyRUWuaQzd/cuEeS1hoRSyW5E5XGmTzlwY1OrNzzakGowI9Dr/I8HVaw4hTtnxy8g==", + "dev": true, + "dependencies": { + "@types/unist": "^3.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/unist-util-position": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/unist-util-position/-/unist-util-position-5.0.0.tgz", + "integrity": "sha512-fucsC7HjXvkB5R3kTCO7kUjRdrS0BJt3M/FPxmHMBOm8JQi2BsHAHFsy27E0EolP8rp0NzXsJ+jNPyDWvOJZPA==", + "dev": true, + "dependencies": { + "@types/unist": "^3.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/unist-util-stringify-position": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-4.0.0.tgz", + "integrity": "sha512-0ASV06AAoKCDkS2+xw5RXJywruurpbC4JZSm7nr7MOt1ojAzvyyaO+UxZf18j8FCF6kmzCZKcAgN/yu2gm2XgQ==", + "dev": true, + "dependencies": { + "@types/unist": "^3.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/unist-util-visit": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/unist-util-visit/-/unist-util-visit-5.1.0.tgz", + "integrity": "sha512-m+vIdyeCOpdr/QeQCu2EzxX/ohgS8KbnPDgFni4dQsfSCtpz8UqDyY5GjRru8PDKuYn7Fq19j1CQ+nJSsGKOzg==", + "dev": true, + "dependencies": { + "@types/unist": "^3.0.0", + "unist-util-is": "^6.0.0", + "unist-util-visit-parents": "^6.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/unist-util-visit-parents": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/unist-util-visit-parents/-/unist-util-visit-parents-6.0.2.tgz", + "integrity": "sha512-goh1s1TBrqSqukSc8wrjwWhL0hiJxgA8m4kFxGlQ+8FYQ3C/m11FcTs4YYem7V664AhHVvgoQLk890Ssdsr2IQ==", + "dev": true, + "dependencies": { + "@types/unist": "^3.0.0", + "unist-util-is": "^6.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/uuid": { + "version": "11.1.1", + "resolved": "https://registry.npmjs.org/uuid/-/uuid-11.1.1.tgz", + "integrity": "sha512-vIYxrBCC/N/K+Js3qSN88go7kIfNPssr/hHCesKCQNAjmgvYS2oqr69kIufEG+O4+PfezOH4EbIeHCfFov8ZgQ==", + "dev": true, + "funding": [ + "https://github.com/sponsors/broofa", + "https://github.com/sponsors/ctavan" + ], + "bin": { + "uuid": "dist/esm/bin/uuid" + } + }, + "node_modules/vfile": { + "version": "6.0.3", + "resolved": "https://registry.npmjs.org/vfile/-/vfile-6.0.3.tgz", + "integrity": "sha512-KzIbH/9tXat2u30jf+smMwFCsno4wHVdNmzFyL+T/L3UGqqk6JKfVqOFOZEpZSHADH1k40ab6NUIXZq422ov3Q==", + "dev": true, + "dependencies": { + "@types/unist": "^3.0.0", + "vfile-message": "^4.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/vfile-message": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/vfile-message/-/vfile-message-4.0.3.tgz", + "integrity": "sha512-QTHzsGd1EhbZs4AsQ20JX1rC3cOlt/IWJruk893DfLRr57lcnOeMaWG4K0JrRta4mIJZKth2Au3mM3u03/JWKw==", + "dev": true, + "dependencies": { + "@types/unist": "^3.0.0", + "unist-util-stringify-position": "^4.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/vite": { + "version": "5.4.21", + "resolved": "https://registry.npmjs.org/vite/-/vite-5.4.21.tgz", + "integrity": "sha512-o5a9xKjbtuhY6Bi5S3+HvbRERmouabWbyUcpXXUA1u+GNUKoROi9byOJ8M0nHbHYHkYICiMlqxkg1KkYmm25Sw==", + "dev": true, + "dependencies": { + "esbuild": "^0.21.3", + "postcss": "^8.4.43", + "rollup": "^4.20.0" + }, + "bin": { + "vite": "bin/vite.js" + }, + "engines": { + "node": "^18.0.0 || >=20.0.0" + }, + "funding": { + "url": "https://github.com/vitejs/vite?sponsor=1" + }, + "optionalDependencies": { + "fsevents": "~2.3.3" + }, + "peerDependencies": { + "@types/node": "^18.0.0 || >=20.0.0", + "less": "*", + "lightningcss": "^1.21.0", + "sass": "*", + "sass-embedded": "*", + "stylus": "*", + "sugarss": "*", + "terser": "^5.4.0" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + }, + "less": { + "optional": true + }, + "lightningcss": { + "optional": true + }, + "sass": { + "optional": true + }, + "sass-embedded": { + "optional": true + }, + "stylus": { + "optional": true + }, + "sugarss": { + "optional": true + }, + "terser": { + "optional": true + } + } + }, + "node_modules/vitepress": { + "version": "1.6.4", + "resolved": "https://registry.npmjs.org/vitepress/-/vitepress-1.6.4.tgz", + "integrity": "sha512-+2ym1/+0VVrbhNyRoFFesVvBvHAVMZMK0rw60E3X/5349M1GuVdKeazuksqopEdvkKwKGs21Q729jX81/bkBJg==", + "dev": true, + "dependencies": { + "@docsearch/css": "3.8.2", + "@docsearch/js": "3.8.2", + "@iconify-json/simple-icons": "^1.2.21", + "@shikijs/core": "^2.1.0", + "@shikijs/transformers": "^2.1.0", + "@shikijs/types": "^2.1.0", + "@types/markdown-it": "^14.1.2", + "@vitejs/plugin-vue": "^5.2.1", + "@vue/devtools-api": "^7.7.0", + "@vue/shared": "^3.5.13", + "@vueuse/core": "^12.4.0", + "@vueuse/integrations": "^12.4.0", + "focus-trap": "^7.6.4", + "mark.js": "8.11.1", + "minisearch": "^7.1.1", + "shiki": "^2.1.0", + "vite": "^5.4.14", + "vue": "^3.5.13" + }, + "bin": { + "vitepress": "bin/vitepress.js" + }, + "peerDependencies": { + "markdown-it-mathjax3": "^4", + "postcss": "^8" + }, + "peerDependenciesMeta": { + "markdown-it-mathjax3": { + "optional": true + }, + "postcss": { + "optional": true + } + } + }, + "node_modules/vitepress-plugin-mermaid": { + "version": "2.0.17", + "resolved": "https://registry.npmjs.org/vitepress-plugin-mermaid/-/vitepress-plugin-mermaid-2.0.17.tgz", + "integrity": "sha512-IUzYpwf61GC6k0XzfmAmNrLvMi9TRrVRMsUyCA8KNXhg/mQ1VqWnO0/tBVPiX5UoKF1mDUwqn5QV4qAJl6JnUg==", + "dev": true, + "optionalDependencies": { + "@mermaid-js/mermaid-mindmap": "^9.3.0" + }, + "peerDependencies": { + "mermaid": "10 || 11", + "vitepress": "^1.0.0 || ^1.0.0-alpha" + } + }, + "node_modules/vscode-jsonrpc": { + "version": "8.2.0", + "resolved": "https://registry.npmjs.org/vscode-jsonrpc/-/vscode-jsonrpc-8.2.0.tgz", + "integrity": "sha512-C+r0eKJUIfiDIfwJhria30+TYWPtuHJXHtI7J0YlOmKAo7ogxP20T0zxB7HZQIFhIyvoBPwWskjxrvAtfjyZfA==", + "dev": true, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/vscode-languageserver": { + "version": "9.0.1", + "resolved": "https://registry.npmjs.org/vscode-languageserver/-/vscode-languageserver-9.0.1.tgz", + "integrity": "sha512-woByF3PDpkHFUreUa7Hos7+pUWdeWMXRd26+ZX2A8cFx6v/JPTtd4/uN0/jB6XQHYaOlHbio03NTHCqrgG5n7g==", + "dev": true, + "dependencies": { + "vscode-languageserver-protocol": "3.17.5" + }, + "bin": { + "installServerIntoExtension": "bin/installServerIntoExtension" + } + }, + "node_modules/vscode-languageserver-protocol": { + "version": "3.17.5", + "resolved": "https://registry.npmjs.org/vscode-languageserver-protocol/-/vscode-languageserver-protocol-3.17.5.tgz", + "integrity": "sha512-mb1bvRJN8SVznADSGWM9u/b07H7Ecg0I3OgXDuLdn307rl/J3A9YD6/eYOssqhecL27hK1IPZAsaqh00i/Jljg==", + "dev": true, + "dependencies": { + "vscode-jsonrpc": "8.2.0", + "vscode-languageserver-types": "3.17.5" + } + }, + "node_modules/vscode-languageserver-textdocument": { + "version": "1.0.12", + "resolved": "https://registry.npmjs.org/vscode-languageserver-textdocument/-/vscode-languageserver-textdocument-1.0.12.tgz", + "integrity": "sha512-cxWNPesCnQCcMPeenjKKsOCKQZ/L6Tv19DTRIGuLWe32lyzWhihGVJ/rcckZXJxfdKCFvRLS3fpBIsV/ZGX4zA==", + "dev": true + }, + "node_modules/vscode-languageserver-types": { + "version": "3.17.5", + "resolved": "https://registry.npmjs.org/vscode-languageserver-types/-/vscode-languageserver-types-3.17.5.tgz", + "integrity": "sha512-Ld1VelNuX9pdF39h2Hgaeb5hEZM2Z3jUrrMgWQAu82jMtZp7p3vJT3BzToKtZI7NgQssZje5o0zryOrhQvzQAg==", + "dev": true + }, + "node_modules/vscode-uri": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/vscode-uri/-/vscode-uri-3.1.0.tgz", + "integrity": "sha512-/BpdSx+yCQGnCvecbyXdxHDkuk55/G3xwnC0GqY4gmQ3j+A+g8kzzgB4Nk/SINjqn6+waqw3EgbVF2QKExkRxQ==", + "dev": true + }, + "node_modules/vue": { + "version": "3.5.33", + "resolved": "https://registry.npmjs.org/vue/-/vue-3.5.33.tgz", + "integrity": "sha512-1AgChhx5w3ALgT4oK3acm2Es/7jyZhWSVUfs3rOBlGQC0rjEDkS7G4lWlJJGGNQD+BV3reCwbQrOe1mPNwKHBQ==", + "dev": true, + "dependencies": { + "@vue/compiler-dom": "3.5.33", + "@vue/compiler-sfc": "3.5.33", + "@vue/runtime-dom": "3.5.33", + "@vue/server-renderer": "3.5.33", + "@vue/shared": "3.5.33" + }, + "peerDependencies": { + "typescript": "*" + }, + "peerDependenciesMeta": { + "typescript": { + "optional": true + } + } + }, + "node_modules/zwitch": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/zwitch/-/zwitch-2.0.4.tgz", + "integrity": "sha512-bXE4cR/kVZhKZX/RjPEflHaKVhUVl85noU3v6b8apfQEc1x4A+zBxjZ4lN8LqGd6WZ3dl98pY4o717VFmoPp+A==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + } + } +} diff --git a/docs/package.json b/docs/package.json new file mode 100644 index 000000000..ed517df33 --- /dev/null +++ b/docs/package.json @@ -0,0 +1,17 @@ +{ + "name": "mtconnect.net-docs", + "version": "0.1.0", + "description": "VitePress documentation site for MTConnect.NET", + "private": true, + "type": "module", + "scripts": { + "dev": "vitepress dev", + "build": "vitepress build", + "preview": "vitepress preview" + }, + "devDependencies": { + "mermaid": "^11.0.0", + "vitepress": "^1.5.0", + "vitepress-plugin-mermaid": "^2.0.17" + } +} diff --git a/docs/reference/cli.md b/docs/reference/cli.md new file mode 100644 index 000000000..77ddd2945 --- /dev/null +++ b/docs/reference/cli.md @@ -0,0 +1,120 @@ + + +# CLI reference + +Every command-line tool the repository exposes — including the shipped `mtconnect.net-agent` + `mtconnect.net-adapter` binaries and the contributor scripts under `tools/` plus the .NET tools under `build/`. The list is built by walking the source tree at docs-build time, so a new flag added to any tool surfaces here on the next regeneration. + +## Shipped CLIs + +### `mtconnect.net-adapter` + +- **Source**: [`adapter/MTConnect.NET-Applications-Adapter/MTConnectAdapterApplication.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/adapter/MTConnect.NET-Applications-Adapter/MTConnectAdapterApplication.cs) + +Standalone adapter host. Pumps observations from a data source (SHDR socket, MQTT topic, or a custom `DataSource` implementation) into a downstream agent. Reads `adapter.config.yaml` at startup. The CLI surface is defined by `MTConnectAdapterApplication.Run(args)`. + +**Commands** + +| Command | Description | +| --- | --- | +| `help` | Prints usage information | +| `install` | Install as a Service | +| `install-start` | Install as a Service and Start the Service | +| `start` | Start the Service | +| `stop` | Stop the Service | +| `remove` | Remove the Service | +| `debug` | Runs the Agent in the terminal (with verbose logging) | +| `run` | Runs the Agent in the terminal | +| `run-service` | Runs the Agent as a Service | + +**Positional arguments** + +| Name | Description | +| --- | --- | +| `configuration_file` | Path to the adapter configuration file. Defaults to `adapter.config.yaml` next to the executable when omitted. | + +### `mtconnect.net-agent` + +- **Source**: [`agent/MTConnect.NET-Applications-Agents/MTConnectAgentApplication.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/agent/MTConnect.NET-Applications-Agents/MTConnectAgentApplication.cs) + +Standalone HTTP agent host. Loads `agent.config.yaml` (or `agent.config.json`), builds an `MTConnectAgentBroker`, instantiates every configured agent module, and runs them inside a single process. The CLI surface is defined by `MTConnectAgentApplication.Run(args)`. + +**Commands** + +| Command | Description | +| --- | --- | +| `help` | Prints usage information | +| `install` | Install as a Service | +| `install-start` | Install as a Service and Start the Service | +| `start` | Start the Service | +| `stop` | Stop the Service | +| `remove` | Remove the Service | +| `debug` | Runs the Agent in the terminal (with verbose logging) | +| `run` | Runs the Agent in the terminal | +| `run-service` | Runs the Agent as a Service | + +**Positional arguments** + +| Name | Description | +| --- | --- | +| `configuration_file` | Path to the agent configuration file. Absolute or relative to the executable's directory. If omitted, the agent looks for `agent.config.json`, then `agent.config.yaml`, and copies `agent.config.default.yaml` into place if neither exists. | + +## Contributor CLIs + +### `MTConnect.NET-DocsGen` + +- **Source**: [`build/MTConnect.NET-DocsGen/Program.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/build/MTConnect.NET-DocsGen/Program.cs) + +Walks the repository source tree with Roslyn and emits the auto-generated VitePress reference pages under `docs/reference/`. The same inventory routines are exposed as public static methods so the validation test can re-run them independently. + +**Flags** + +| Flag | Short | Argument | Description | +| --- | --- | --- | --- | +| `--check` | | | Verify pages are in sync; exit 1 on drift | +| `--help` | | | | +| `--out` | | `` | Docs root (defaults to <repo>/docs) | +| `--repo` | | `` | Repository root (required) | + +### `MTConnect.NET-SysML-Import` + +- **Source**: [`build/MTConnect.NET-SysML-Import/Program.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/build/MTConnect.NET-SysML-Import/Program.cs) + +Parses an `MTConnectSysMLModel.xml` (the XMI export of the standard's SysML model) and regenerates the `*.g.cs` source files under `libraries/MTConnect.NET-Common/`, `libraries/MTConnect.NET-XML/`, and `libraries/MTConnect.NET-JSON-cppagent/`. Run by maintainers when a new spec version lands. + +**Flags** + +| Flag | Short | Argument | Description | +| --- | --- | --- | --- | +| `--help` | | | | +| `--json-dump` | | `` | Optional. Writes the parsed MTConnectModel as JSON for debugging. | +| `--output` | | `` | Repository root. Each subgenerator writes into its own libraries/<LibraryName>/ subtree under this root. Required. | +| `--xmi` | | `` | SysML XMI file to consume. Required. | + +### `dotnet.sh` + +- **Source**: [`tools/dotnet.sh`](https://github.com/TrakHound/MTConnect.NET/blob/master/tools/dotnet.sh) + +Wrapper around `dotnet` that runs either against the dotnet on PATH (default) or inside an official Microsoft .NET SDK container when `--docker` (or `MTCONNECT_DOTNET_USE_DOCKER=1`) is set. Lets a contributor without a local SDK install build and test the repo, and pins the SDK version so two contributors don't drif... + +**Flags** + +| Flag | Short | Argument | Description | +| --- | --- | --- | --- | +| `--docker` | `-d` | | Run dotnet inside a pinned mcr.microsoft.com/dotnet/sdk container (also honored via MTCONNECT_DOTNET_USE_DOCKER=1). Everything after the flag is forwarded to the `dotnet` CLI verbatim. | + +### `test.sh` + +- **Source**: [`tools/test.sh`](https://github.com/TrakHound/MTConnect.NET/blob/master/tools/test.sh) + +Local test + coverage entry point for MTConnect.NET. Discovers every test project under tests/**/*.csproj — adding a new test project requires no edits to this script. The compliance harness under tests/Compliance/** and the Docker-gated end-to-end suites are skipped by default so the common loop stays fast; flags b... + +**Flags** + +| Flag | Short | Argument | Description | +| --- | --- | --- | --- | +| `--docker` | `-d` | | Run every dotnet invocation through tools/dotnet.sh --docker (also honored via MTCONNECT_DOTNET_USE_DOCKER=1). | +| `--compliance` | `-c` | | Include the MTConnect compliance harness under tests/Compliance/** (XSD validation, OCL checks, cppagent parity). Skipped by default because it is the slowest tier and many of its tests are gated behind Docker / [Category] tags. NOTE: runs every test in the project including `XsdLoadStrict`, expected to surface ~54 failures until the XSD-1.1 validator lands. | +| `--e2e` | `-e` | | Force the Docker-gated end-to-end suites (implies MTCONNECT_E2E_DOCKER=true; Testcontainers spins up mosquitto + cppagent containers per test class). | +| `--only` | `-o` | `PATTERN` | Run only the test projects whose path matches PATTERN (grep -E). Example: --only 'XML\|SHDR' runs only those two projects. | +| `--help` | `-h` | | Print this help and exit. | + diff --git a/docs/reference/configuration.md b/docs/reference/configuration.md new file mode 100644 index 000000000..40e14edd0 --- /dev/null +++ b/docs/reference/configuration.md @@ -0,0 +1,353 @@ + + +# Configuration schema + +The agent and adapter accept YAML or JSON configuration. The schema below is derived from the source declarations of every option class — the `JsonPropertyName` / `YamlMember.Alias` value gives the on-the-wire key, and the `///` summary above each property is reproduced verbatim. + +## Worked example + +A minimal `agent.config.yaml` for an HTTP agent on port 5000: + +```yaml +observationBufferSize: 150000 +assetBufferSize: 1000 +defaultVersion: "2.5" +enableAgentDevice: true +enableMetrics: true + +modules: + - http: + port: 5000 + documentFormat: xml +``` + +## Option classes + +### `AdapterApplicationConfiguration` + +- **Namespace**: `MTConnect.Configurations` +- **Source**: [`libraries/MTConnect.NET-Common/Configurations/AdapterApplicationConfiguration.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-Common/Configurations/AdapterApplicationConfiguration.cs) + +Configuration for an MTConnect Http Agent Application + +| Key | C# property | Type | Description | +| --- | --- | --- | --- | +| `changeToken` | `ChangeToken` | `string` | An opaque token regenerated each time the configuration is saved, allowing consumers to detect that the configuration has changed. | +| `configurationFileRestartInterval` | `ConfigurationFileRestartInterval` | `int` | Gets or Sets the minimum time (in seconds) between Adapter restarts when MonitorConfigurationFiles is enabled | +| `deviceKey` | `DeviceKey` | `string` | The Name or UUID of the Device to create a connection for | +| `enableBuffer` | `EnableBuffer` | `bool` | Determines whether to send all changes to data or only most recent at the specified Interval | +| `engine` | `Engine` | `Dictionary` | Free-form key/value settings consumed by the adapter engine; keys correspond to engine property names with loosely typed values. | +| `filterDuplicates` | `FilterDuplicates` | `bool` | Determines whether to filter out duplicate data | +| `id` | `Id` | `string` | Get a unique identifier for the Adapter | +| `modules` | `Modules` | `IEnumerable` | The raw, untyped module configuration sections declared for the adapter, each later resolved to a strongly typed configuration on demand. | +| `monitorConfigurationFiles` | `MonitorConfigurationFiles` | `bool` | Gets or Sets whether Configuration files are monitored. If enabled and a configuration file is changed, the Adapter will restart | +| `outputTimestamps` | `OutputTimestamps` | `bool` | Determines whether to output Timestamps for each SHDR line | +| `readInterval` | `ReadInterval` | `int` | The interval (in milliseconds) at which new data is read from the Data Source | +| `serviceAutoStart` | `ServiceAutoStart` | `bool` | Sets the Service Start Type. True = Auto \| False = Manual | +| `serviceName` | `ServiceName` | `string` | Changes the service name when installing or removing the service. This allows multiple Adapters to run as services on the same machine. | +| `writeInterval` | `WriteInterval` | `int` | The interval (in milliseconds) at which new data is sent to the Agent | + +### `AgentApplicationConfiguration` + +- **Namespace**: `MTConnect.Configurations` +- **Source**: [`libraries/MTConnect.NET-Common/Configurations/AgentApplicationConfiguration.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-Common/Configurations/AgentApplicationConfiguration.cs) + +Configuration for an MTConnect Http Agent Application + +| Key | C# property | Type | Description | +| --- | --- | --- | --- | +| `configurationFileRestartInterval` | `ConfigurationFileRestartInterval` | `int` | Gets or Sets the minimum time (in seconds) between Agent restarts when MonitorConfigurationFiles is enabled | +| `devices` | `Devices` | `string` | The Path to look for the file(s) that represent the Device Information Models to load into the Agent. The path can either be a single file or a directory. The path can be absolute or relative to the executable's directory | +| `durable` | `Durable` | `bool` | Gets or Sets whether the Agent buffers are durable and retain state after restart | +| `durableBufferPath` | `DurableBufferPath` | `string` | The base path to the directory to write the File Buffers when 'durable = true' | +| `modules` | `Modules` | `IEnumerable` | The raw, untyped module configuration sections declared for the agent, each later resolved to a strongly typed configuration on demand. | +| `monitorConfigurationFiles` | `MonitorConfigurationFiles` | `bool` | Gets or Sets whether Configuration files are monitored. If enabled and a configuration file is changed, the Agent will restart | +| `processors` | `Processors` | `IEnumerable` | The raw, untyped processor configuration sections declared for the agent's observation/asset processing pipeline. | +| `serviceAutoStart` | `ServiceAutoStart` | `bool` | Sets the Service Start Type. True = Auto \| False = Manual | +| `serviceDisplayName` | `ServiceDisplayName` | `string` | Changes the display name of the service. This helps with identification when multiple agents on run as services on the same machine. | +| `serviceDisplayName` | `ServiceDescription` | `string` | Changes the description of the service. This helps with identification when multiple agents on run as services on the same machine. | +| `serviceName` | `ServiceName` | `string` | Changes the service name when installing or removing the service. This allows multiple agents to run as services on the same machine. | +| `useBufferCompression` | `UseBufferCompression` | `bool` | Gets or Sets whether the durable Agent buffers use Compression | + +### `AgentConfiguration` + +- **Namespace**: `MTConnect.Configurations` +- **Source**: [`libraries/MTConnect.NET-Common/Configurations/AgentConfiguration.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-Common/Configurations/AgentConfiguration.cs) + +Configuration for an MTConnect Agent + +| Key | C# property | Type | Description | +| --- | --- | --- | --- | +| `assetBufferSize` | `AssetBufferSize` | `uint` | The maximum number of assets the agent can hold in its buffer | +| `changeToken` | `ChangeToken` | `string` | An opaque token regenerated each time the configuration is saved, allowing consumers to detect that the configuration has changed. | +| `convertUnits` | `ConvertUnits` | `bool` | Gets or Sets the default for Converting Units when adding Observations | +| `defaultVersion` | `DefaultVersionValue` | `string` | The string form of used for serialization; assigning a parseable version string updates . | +| `enableAgentDevice` | `EnableAgentDevice` | `bool` | Gets or Sets whether the Agent Device is output | +| `enableMetrics` | `EnableMetrics` | `bool` | Gets or Sets whether Metrics are captured (ex. ObserationUpdateRate, AssetUpdateRate) | +| `enableValidation` | `EnableValidation` | `bool` | Gets or Sets whether validation information is output | +| `ignoreObservationCase` | `IgnoreObservationCase` | `bool` | Gets or Sets the default for Ignoring the case of Observation values | +| `ignoreTimestamps` | `IgnoreTimestamps` | `bool` | Overwrite timestamps with the agent time. This will correct clock drift but will not give as accurate relative time since it will not take into consideration network latencies. This can be overridden on a per adapter basis. | +| `inputValidationLevel` | `InputValidationLevel` | `InputValidationLevel` | Gets or Sets the default Input (Observation or Asset) validation level. 0 = Ignore, 1 = Warning, 2 = Remove, 3 = Strict | +| `observationBufferSize` | `ObservationBufferSize` | `uint` | The maximum number of Observations the agent can hold in its buffer | +| `timezoneOutput` | `TimeZoneOutput` | `string` | Sets the TimeZone to use when timestamps are output from the Agent | + +### `DataSourceConfiguration` + +- **Namespace**: `MTConnect.Configurations` +- **Source**: [`libraries/MTConnect.NET-Common/Configurations/DataSourceConfiguration.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-Common/Configurations/DataSourceConfiguration.cs) + +Configuration for an MTConnect Data Source + +| Key | C# property | Type | Description | +| --- | --- | --- | --- | +| `readInterval` | `ReadInterval` | `int` | The interval (in milliseconds) at which new data is read from the Data Source | + +### `FileConfiguration` + +- **Namespace**: `MTConnect.Configurations` +- **Source**: [`libraries/MTConnect.NET-HTTP/Configurations/FileConfiguration.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP/Configurations/FileConfiguration.cs) + +Configuration for Static Files that can served from an Http Server + +| Key | C# property | Type | Description | +| --- | --- | --- | --- | +| `location` | `Location` | `string` | The path to match in the requested URL | +| `path` | `Path` | `string` | The location of the files on the server (where the Agent is running) | + +### `HttpClientConfiguration` + +- **Namespace**: `MTConnect.Configurations` +- **Source**: [`libraries/MTConnect.NET-HTTP/Configurations/HttpClientConfiguration.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP/Configurations/HttpClientConfiguration.cs) + +Configuration for a MTConnect Http Client + +| Key | C# property | Type | Description | +| --- | --- | --- | --- | +| `address` | `Address` | `string` | The URL address the client MTConnect Agent is located at. | +| `currentOnly` | `CurrentOnly` | `bool` | Gets or Sets whether the stream requests a Current (true) or a Sample (false) | +| `deviceKey` | `DeviceKey` | `string` | The Name or UUID of the MTConnect Device | +| `heartbeat` | `Heartbeat` | `int` | The streaming heartbeat in milliseconds passed to the agent as the heartbeat query parameter on sample long-poll requests. The agent emits an empty document each heartbeat to keep the HTTP connection alive when no observations are produced. | +| `interval` | `Interval` | `int` | The polling/streaming interval in milliseconds. For polling clients this is the wait between successive current/sample requests; for streaming clients it is the interval query parameter sent to the agent's sample long-poll. | +| `outputConnectionInformation` | `OutputConnectionInformation` | `bool` | Gets or Sets whether the Connection Information (Host / Port) is output to the Agent to be collected by a client | +| `port` | `Port` | `int` | The port to connect to the client MTConnect Agent. | +| `useSSL` | `UseSSL` | `bool` | When true, the client connects to the agent over https://; when false, over http://. Any explicit scheme already present in is rewritten to match this flag. | +| `useStreaming` | `UseStreaming` | `bool` | Gets or Sets whether the client should use Streaming (true) or Polling (false) | + +### `IAdapterApplicationConfiguration` + +- **Namespace**: `MTConnect.Configurations` +- **Source**: [`libraries/MTConnect.NET-Common/Configurations/IAdapterApplicationConfiguration.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-Common/Configurations/IAdapterApplicationConfiguration.cs) + +Configuration for an MTConnect Adapter + +| Key | C# property | Type | Description | +| --- | --- | --- | --- | +| `changeToken` | `ChangeToken` | `string` | An opaque token that changes whenever the underlying configuration source is reloaded, allowing consumers to detect that the configuration has been replaced. | +| `configurationFileRestartInterval` | `ConfigurationFileRestartInterval` | `int` | Gets or Sets the minimum time (in seconds) between Adapter restarts when MonitorConfigurationFiles is enabled | +| `deviceKey` | `DeviceKey` | `string` | The Name or UUID of the Device to create a connection for | +| `enableBuffer` | `EnableBuffer` | `bool` | Determines whether to send all changes to data or only most recent at the specified Interval | +| `engine` | `Engine` | `Dictionary` | Free-form key/value settings consumed by the adapter engine; keys correspond to engine property names with loosely typed values. | +| `filterDuplicates` | `FilterDuplicates` | `bool` | Determines whether to filter out duplicate data | +| `id` | `Id` | `string` | Get a unique identifier for the Adapter | +| `modules` | `Modules` | `IEnumerable` | The raw, untyped module configuration sections declared for the adapter, each later resolved to a strongly typed configuration on demand. | +| `monitorConfigurationFiles` | `MonitorConfigurationFiles` | `bool` | Gets or Sets whether Configuration files are monitored. If enabled and a configuration file is changed, the Adapter will restart | +| `outputTimestamps` | `OutputTimestamps` | `bool` | Determines whether to output Timestamps for each SHDR line | +| `path` | `Path` | `string` | The file system path the configuration was loaded from, used as the default target when the configuration is saved back to disk. | +| `serviceAutoStart` | `ServiceAutoStart` | `bool` | Sets the Service Start Type. True = Auto \| False = Manual | +| `serviceName` | `ServiceName` | `string` | Changes the service name when installing or removing the service. This allows multiple Adapters to run as services on the same machine. | +| `writeInterval` | `WriteInterval` | `int` | The interval (in milliseconds) at which new data is sent to the Agent | + +### `IAgentApplicationConfiguration` + +- **Namespace**: `MTConnect.Configurations` +- **Source**: [`libraries/MTConnect.NET-Common/Configurations/IAgentApplicationConfiguration.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-Common/Configurations/IAgentApplicationConfiguration.cs) + +Configuration for an MTConnect Shdr > Http Agent + +| Key | C# property | Type | Description | +| --- | --- | --- | --- | +| `configurationFileRestartInterval` | `ConfigurationFileRestartInterval` | `int` | Gets or Sets the minimum time (in seconds) between Agent restarts when MonitorConfigurationFiles is enabled | +| `devices` | `Devices` | `string` | The Path to look for the file(s) that represent the Device Information Models to load into the Agent. The path can either be a single file or a directory. The path can be absolute or relative to the executable's directory | +| `durable` | `Durable` | `bool` | Gets or Sets whether the Agent buffers are durable and retain state after restart | +| `durableBufferPath` | `DurableBufferPath` | `string` | The base path to the directory to write the File Buffers when 'durable = true' | +| `modules` | `Modules` | `IEnumerable` | The raw, untyped module configuration sections declared for the agent, each later resolved to a strongly typed configuration on demand. | +| `monitorConfigurationFiles` | `MonitorConfigurationFiles` | `bool` | Gets or Sets whether Configuration files are monitored. If enabled and a configuration file is changed, the Agent will restart | +| `processors` | `Processors` | `IEnumerable` | The raw, untyped processor configuration sections declared for the agent's observation/asset processing pipeline. | +| `serviceAutoStart` | `ServiceAutoStart` | `bool` | Sets the Service Start Type. True = Auto \| False = Manual | +| `serviceDescription` | `ServiceDescription` | `string` | Changes the description of the service. This helps with identification when multiple agents on run as services on the same machine. | +| `serviceDisplayName` | `ServiceDisplayName` | `string` | Changes the display name of the service. This helps with identification when multiple agents on run as services on the same machine. | +| `serviceName` | `ServiceName` | `string` | Changes the service name when installing or removing the service. This allows multiple agents to run as services on the same machine. | +| `useBufferCompression` | `UseBufferCompression` | `bool` | Gets or Sets whether the durable Agent buffers use Compression | + +### `IAgentConfiguration` + +- **Namespace**: `MTConnect.Configurations` +- **Source**: [`libraries/MTConnect.NET-Common/Configurations/IAgentConfiguration.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-Common/Configurations/IAgentConfiguration.cs) + +Configuration for an MTConnect Agent + +| Key | C# property | Type | Description | +| --- | --- | --- | --- | +| `assetBufferSize` | `AssetBufferSize` | `uint` | The maximum number of assets the agent can hold in its buffer | +| `changeToken` | `ChangeToken` | `string` | An opaque token that changes whenever the underlying configuration source is reloaded, allowing consumers to detect that the configuration has been replaced. | +| `convertUnits` | `ConvertUnits` | `bool` | Gets the default for Converting Units when adding Observations | +| `defaultVersion` | `DefaultVersion` | `Version` | Gets the default MTConnect version to output response documents for. | +| `enableAgentDevice` | `EnableAgentDevice` | `bool` | Gets or Sets whether the Agent Device is output | +| `enableMetrics` | `EnableMetrics` | `bool` | Gets whether Metrics are captured (ex. ObserationUpdateRate, AssetUpdateRate) | +| `enableValidation` | `EnableValidation` | `bool` | Gets or Sets whether validation information is output | +| `ignoreObservationCase` | `IgnoreObservationCase` | `bool` | Gets the default for Ignoring the case of Observation values | +| `ignoreTimestamps` | `IgnoreTimestamps` | `bool` | Overwrite timestamps with the agent time. This will correct clock drift but will not give as accurate relative time since it will not take into consideration network latencies. This can be overridden on a per adapter basis. | +| `inputValidationLevel` | `InputValidationLevel` | `InputValidationLevel` | Gets the default Input (Observation or Asset) validation level. 0 = Ignore, 1 = Warning, 2 = Remove, 3 = Strict | +| `observationBufferSize` | `ObservationBufferSize` | `uint` | The maximum number of Observations the agent can hold in its buffer | +| `path` | `Path` | `string` | The file system path the configuration was loaded from, used as the default target when the configuration is saved back to disk. | +| `timeZoneOutput` | `TimeZoneOutput` | `string` | Sets the TimeZone to use when timestamps are output from the Agent | + +### `IDataSourceConfiguration` + +- **Namespace**: `MTConnect.Configurations` +- **Source**: [`libraries/MTConnect.NET-Common/Configurations/IDataSourceConfiguration.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-Common/Configurations/IDataSourceConfiguration.cs) + +Configuration for an MTConnect Data Source + +| Key | C# property | Type | Description | +| --- | --- | --- | --- | +| `readInterval` | `ReadInterval` | `int` | The interval (in milliseconds) at which new data is read from the Data Source | + +### `IFileConfiguration` + +- **Namespace**: `MTConnect.Configurations` +- **Source**: [`libraries/MTConnect.NET-HTTP/Configurations/IFileConfiguration.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP/Configurations/IFileConfiguration.cs) + +Configuration for Static Files that can served from an Http Server + +| Key | C# property | Type | Description | +| --- | --- | --- | --- | +| `location` | `Location` | `string` | The path to match in the requested URL | +| `path` | `Path` | `string` | The location of the files on the server (where the Agent is running) | + +### `IHttpClientConfiguration` + +- **Namespace**: `MTConnect.Configurations` +- **Source**: [`libraries/MTConnect.NET-HTTP/Configurations/IHttpClientConfiguration.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP/Configurations/IHttpClientConfiguration.cs) + +Configuration for a MTConnect Http Client + +| Key | C# property | Type | Description | +| --- | --- | --- | --- | +| `address` | `Address` | `string` | The URL address the client MTConnect Agent is located at. | +| `currentOnly` | `CurrentOnly` | `bool` | Gets or Sets whether the stream requests a Current (true) or a Sample (false) | +| `deviceKey` | `DeviceKey` | `string` | The Name or UUID of the MTConnect Device | +| `heartbeat` | `Heartbeat` | `int` | | +| `id` | `Id` | `string` | The unique identifier for the Adapter | +| `interval` | `Interval` | `int` | | +| `outputConnectionInformation` | `OutputConnectionInformation` | `bool` | Gets or Sets whether the Connection Information (Host / Port) is output to the Agent to be collected by a client | +| `port` | `Port` | `int` | The port to connect to the client MTConnect Agent. | +| `useSSL` | `UseSSL` | `bool` | | +| `useStreaming` | `UseStreaming` | `bool` | Gets or Sets whether the client should use Streaming (true) or Polling (false) | + +### `IShdrAdapterClientConfiguration` + +- **Namespace**: `MTConnect.Configurations` +- **Source**: [`libraries/MTConnect.NET-SHDR/Configurations/IShdrAdapterClientConfiguration.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-SHDR/Configurations/IShdrAdapterClientConfiguration.cs) + +Configuration for an MTConnect SHDR Adapter + +| Key | C# property | Type | Description | +| --- | --- | --- | --- | +| `availableOnConnection` | `AvailableOnConnection` | `bool` | For devices that do not have the ability to provide available events, if yes, this sets the Availability to AVAILABLE upon connection. | +| `convertUnits` | `ConvertUnits` | `bool` | Adapter setting for data item units conversion in the agent. Assumes the adapter has already done unit conversion. Defaults to global. | +| `ignoreHeartbeatOnChange` | `IgnoreHeartbeatOnChange` | `bool` | Gets or Sets whether Heartbeat PING requests are not sent if data has been received within the Heartbeat period | +| `ignoreObservationCase` | `IgnoreObservationCase` | `bool` | Gets or Sets the default for Ignoring the case of Observation values | +| `ignoreTimestamps` | `IgnoreTimestamps` | `bool` | Overwrite timestamps with the agent time. This will correct clock drift but will not give as accurate relative time since it will not take into consideration network latencies. This can be overridden on a per adapter basis. | +| `outputConnectionInformation` | `OutputConnectionInformation` | `bool` | Gets or Sets whether the Connection Information (Host / Port) is output to the Agent to be collected by a client | + +### `IShdrClientConfiguration` + +- **Namespace**: `MTConnect.Configurations` +- **Source**: [`libraries/MTConnect.NET-SHDR/Configurations/IShdrClientConfiguration.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-SHDR/Configurations/IShdrClientConfiguration.cs) + +Configuration for an MTConnect SHDR Client + +| Key | C# property | Type | Description | +| --- | --- | --- | --- | +| `connectionTimeout` | `ConnectionTimeout` | `int` | The amount of time (in milliseconds) an adapter can be silent before it is disconnected. This is only for legacy adapters that do not support heartbeats. If heartbeats are present, this will be ignored. | +| `deviceKey` | `DeviceKey` | `string` | The UUID or Name of the device that corresponds to the name of the device in the Devices file. | +| `heartbeat` | `Heartbeat` | `int` | The Heartbeat interval (in milliseconds) that the TCP Connection will use to maintain a connection when no new data has been sent | +| `hostname` | `Hostname` | `string` | The host the adapter is located on. | +| `id` | `Id` | `string` | The unique identifier for the Adapter | +| `port` | `Port` | `int` | The port to connect to the adapter. | +| `reconnectInterval` | `ReconnectInterval` | `int` | The amount of time (in milliseconds) between adapter reconnection attempts. This is useful for implementation of high performance adapters where availability needs to be tracked in near-real-time. | + +### `ShdrAdapterClientConfiguration` + +- **Namespace**: `MTConnect.Configurations` +- **Source**: [`libraries/MTConnect.NET-SHDR/Configurations/ShdrAdapterClientConfiguration.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-SHDR/Configurations/ShdrAdapterClientConfiguration.cs) + +Configuration for an MTConnect SHDR Adapter + +| Key | C# property | Type | Description | +| --- | --- | --- | --- | +| `availableOnConnection` | `AvailableOnConnection` | `bool` | For devices that do not have the ability to provide available events, if TRUE, this sets the Availability to AVAILABLE upon connection. | +| `convertUnits` | `ConvertUnits` | `bool` | Adapter setting for data item units conversion in the agent. Assumes the adapter has already done unit conversion. Defaults to global. | +| `ignoreHeartbeatOnChange` | `IgnoreHeartbeatOnChange` | `bool` | Gets or Sets whether Heartbeat PING requests are not sent if data has been received within the Heartbeat period | +| `ignoreObservationCase` | `IgnoreObservationCase` | `bool` | Gets or Sets the default for Ignoring the case of Observation values | +| `ignoreTimestamps` | `IgnoreTimestamps` | `bool` | Overwrite timestamps with the agent time. This will correct clock drift but will not give as accurate relative time since it will not take into consideration network latencies. This can be overridden on a per adapter basis. | +| `outputConnectionInformation` | `OutputConnectionInformation` | `bool` | Gets or Sets whether the Connection Information (Host / Port) is output to the Agent to be collected by a client | + +### `ShdrClientConfiguration` + +- **Namespace**: `MTConnect.Configurations` +- **Source**: [`libraries/MTConnect.NET-SHDR/Configurations/ShdrClientConfiguration.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-SHDR/Configurations/ShdrClientConfiguration.cs) + +Configuration for an MTConnect SHDR Client + +| Key | C# property | Type | Description | +| --- | --- | --- | --- | +| `connectionTimeout` | `ConnectionTimeout` | `int` | The amount of time (in milliseconds) an adapter can be silent before it is disconnected. This is only for legacy adapters that do not support heartbeats. If heartbeats are present, this will be ignored. | +| `deviceKey` | `DeviceKey` | `string` | The UUID or Name of the device that corresponds to the name of the device in the Devices file. | +| `heartbeat` | `Heartbeat` | `int` | The Heartbeat interval (in milliseconds) that the TCP Connection will use to maintain a connection when no new data has been sent | +| `hostname` | `Hostname` | `string` | The host the adapter is located on. | +| `id` | `Id` | `string` | The unique identifier for the Adapter | +| `port` | `Port` | `int` | The port to connect to the adapter. | +| `reconnectInterval` | `ReconnectInterval` | `int` | The amount of time (in milliseconds) between adapter reconnection attempts. This is useful for implementation of high performance adapters where availability needs to be tracked in near-real-time. | + +### `PemCertificateConfiguration` + +- **Namespace**: `MTConnect.Tls` +- **Source**: [`libraries/MTConnect.NET-TLS/PemCertificateConfiguration.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-TLS/PemCertificateConfiguration.cs) + +Configures a TLS certificate loaded from PEM-encoded files. + +| Key | C# property | Type | Description | +| --- | --- | --- | --- | +| `certificateAuthority` | `CertificateAuthority` | `string` | The path to the PEM file containing the trusted certificate authority chain. | +| `certificatePath` | `CertificatePath` | `string` | The path to the PEM file containing the server or client certificate. | +| `privateKeyPassword` | `PrivateKeyPassword` | `string` | The password protecting the private key, when it is encrypted. | +| `privateKeyPath` | `PrivateKeyPath` | `string` | The path to the PEM file containing the certificate's private key. | + +### `PfxCertificateConfiguration` + +- **Namespace**: `MTConnect.Tls` +- **Source**: [`libraries/MTConnect.NET-TLS/PfxCertificateConfiguration.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-TLS/PfxCertificateConfiguration.cs) + +Configures a TLS certificate loaded from a PKCS#12 (PFX) file. + +| Key | C# property | Type | Description | +| --- | --- | --- | --- | +| `certificatePassword` | `CertificatePassword` | `string` | The password protecting the PFX file, when it is encrypted. | +| `certificatePath` | `CertificatePath` | `string` | The path to the PFX file containing the certificate and its private key. | + +### `TlsConfiguration` + +- **Namespace**: `MTConnect.Tls` +- **Source**: [`libraries/MTConnect.NET-TLS/TlsConfiguration.cs`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-TLS/TlsConfiguration.cs) + +Configures TLS for an MTConnect endpoint, selecting either a PFX or PEM certificate and its validation options. + +| Key | C# property | Type | Description | +| --- | --- | --- | --- | +| `omitCAValidation` | `OmitCAValidation` | `bool` | Whether certificate-authority chain validation is skipped. | +| `pem` | `Pem` | `PemCertificateConfiguration` | The PEM certificate configuration, used when is not set. | +| `pfx` | `Pfx` | `PfxCertificateConfiguration` | The PFX certificate configuration; takes precedence over when set. | +| `verifyClientCertificate` | `VerifyClientCertificate` | `bool` | Whether the endpoint requires and verifies a client certificate. | + diff --git a/docs/reference/environment-variables.md b/docs/reference/environment-variables.md new file mode 100644 index 000000000..f08004721 --- /dev/null +++ b/docs/reference/environment-variables.md @@ -0,0 +1,90 @@ + + +# Environment variables + +Every environment-variable reference discovered in the source tree. Both the C# `Environment.GetEnvironmentVariable("…")` read sites and the contributor scripts under `tools/` (`*.sh` and `*.ps1`) are scanned. Variables are grouped by name, so reads, writes, and defaults that all target the same variable appear together. + +## Summary + +| Variable | Kinds | Default(s) | +| --- | --- | --- | +| `MTCONNECT_DOTNET_E2E_DIND` | powershell-read, shell-read | `0` | +| `MTCONNECT_DOTNET_IMAGE` | powershell-read, shell-read | `${IMAGE_DEFAULT}` | +| `MTCONNECT_DOTNET_SDK_TAG` | powershell-read, shell-read | `8.0` | +| `MTCONNECT_DOTNET_TOOLS_VOLUME` | powershell-read, shell-read | `mtconnect-net-dotnet-tools` | +| `MTCONNECT_DOTNET_USE_DOCKER` | powershell-read, powershell-write, shell-read, shell-write | `'1'`, `0`, `1` | +| `MTCONNECT_E2E_DOCKER` | docker-env, powershell-read, powershell-write, shell-read, shell-write | `true`, `'true'`, `false` | +| `MTCONNECT_E2E_HOST_REPO_ROOT` | docker-env | `${REPO_ROOT}` | +| `MTCONNECT_NUGET_VOLUME` | powershell-read, shell-read | `mtconnect-net-nuget` | +| `MTCONNECT_PARITY_FIXTURE_DIR` | csharp-read | | + +## Per-variable detail + +### `MTCONNECT_DOTNET_E2E_DIND` + +| Kind | Source | Default / value | Context | +| --- | --- | --- | --- | +| `powershell-read` | [`tools/dotnet.ps1:52`](https://github.com/TrakHound/MTConnect.NET/blob/master/tools/dotnet.ps1#L52) | | $e2eMode = ($env:MTCONNECT_DOTNET_E2E_DIND -eq '1') | +| `shell-read` | [`tools/dotnet.sh:73`](https://github.com/TrakHound/MTConnect.NET/blob/master/tools/dotnet.sh#L73) | `0` | if [[ "${MTCONNECT_DOTNET_E2E_DIND:-0}" == "1" ]]; then | + +### `MTCONNECT_DOTNET_IMAGE` + +| Kind | Source | Default / value | Context | +| --- | --- | --- | --- | +| `powershell-read` | [`tools/dotnet.ps1:45`](https://github.com/TrakHound/MTConnect.NET/blob/master/tools/dotnet.ps1#L45) | | $image = if ($env:MTCONNECT_DOTNET_IMAGE) { $env:MTCONNECT_DOTNET_IMAGE } else { "mcr.microsoft.com/dotnet/sdk:${sdkTag}" } | +| `shell-read` | [`tools/dotnet.sh:63`](https://github.com/TrakHound/MTConnect.NET/blob/master/tools/dotnet.sh#L63) | `${IMAGE_DEFAULT}` | IMAGE="${MTCONNECT_DOTNET_IMAGE:-${IMAGE_DEFAULT}}" | + +### `MTCONNECT_DOTNET_SDK_TAG` + +| Kind | Source | Default / value | Context | +| --- | --- | --- | --- | +| `powershell-read` | [`tools/dotnet.ps1:42`](https://github.com/TrakHound/MTConnect.NET/blob/master/tools/dotnet.ps1#L42) | | $sdkTag = if ($env:MTCONNECT_DOTNET_SDK_TAG) { $env:MTCONNECT_DOTNET_SDK_TAG } else { '8.0' } | +| `shell-read` | [`tools/dotnet.sh:59`](https://github.com/TrakHound/MTConnect.NET/blob/master/tools/dotnet.sh#L59) | `8.0` | SDK_TAG_DEFAULT="${MTCONNECT_DOTNET_SDK_TAG:-8.0}" | + +### `MTCONNECT_DOTNET_TOOLS_VOLUME` + +| Kind | Source | Default / value | Context | +| --- | --- | --- | --- | +| `powershell-read` | [`tools/dotnet.ps1:47`](https://github.com/TrakHound/MTConnect.NET/blob/master/tools/dotnet.ps1#L47) | | $toolsVol = if ($env:MTCONNECT_DOTNET_TOOLS_VOLUME) { $env:MTCONNECT_DOTNET_TOOLS_VOLUME } else { 'mtconnect-net-dotnet-tools' } | +| `shell-read` | [`tools/dotnet.sh:65`](https://github.com/TrakHound/MTConnect.NET/blob/master/tools/dotnet.sh#L65) | `mtconnect-net-dotnet-tools` | TOOLS_VOL="${MTCONNECT_DOTNET_TOOLS_VOLUME:-mtconnect-net-dotnet-tools}" | + +### `MTCONNECT_DOTNET_USE_DOCKER` + +| Kind | Source | Default / value | Context | +| --- | --- | --- | --- | +| `powershell-read` | [`tools/dotnet.ps1:40`](https://github.com/TrakHound/MTConnect.NET/blob/master/tools/dotnet.ps1#L40) | | $useDocker = $Docker -or ($env:MTCONNECT_DOTNET_USE_DOCKER -eq '1') | +| `powershell-write` | [`tools/test.ps1:51`](https://github.com/TrakHound/MTConnect.NET/blob/master/tools/test.ps1#L51) | `'1'` | if ($Docker) { $env:MTCONNECT_DOTNET_USE_DOCKER = '1' } | +| `shell-read` | [`tools/dotnet.sh:49`](https://github.com/TrakHound/MTConnect.NET/blob/master/tools/dotnet.sh#L49) | `0` | USE_DOCKER="${MTCONNECT_DOTNET_USE_DOCKER:-0}" | +| `shell-write` | [`tools/test.sh:106`](https://github.com/TrakHound/MTConnect.NET/blob/master/tools/test.sh#L106) | `1` | export MTCONNECT_DOTNET_USE_DOCKER=1 | + +### `MTCONNECT_E2E_DOCKER` + +| Kind | Source | Default / value | Context | +| --- | --- | --- | --- | +| `docker-env` | [`tools/dotnet.sh:88`](https://github.com/TrakHound/MTConnect.NET/blob/master/tools/dotnet.sh#L88) | `true` | -e MTCONNECT_E2E_DOCKER=true | +| `powershell-read` | [`tools/test.ps1:67`](https://github.com/TrakHound/MTConnect.NET/blob/master/tools/test.ps1#L67) | | $raw = [string]$env:MTCONNECT_E2E_DOCKER | +| `powershell-write` | [`tools/test.ps1:52`](https://github.com/TrakHound/MTConnect.NET/blob/master/tools/test.ps1#L52) | `'true'` | if ($E2E) { $env:MTCONNECT_E2E_DOCKER = 'true' } | +| `shell-read` | [`tools/test.sh:140`](https://github.com/TrakHound/MTConnect.NET/blob/master/tools/test.sh#L140) | `false` | local raw="${MTCONNECT_E2E_DOCKER:-false}" | +| `shell-write` | [`tools/test.sh:110`](https://github.com/TrakHound/MTConnect.NET/blob/master/tools/test.sh#L110) | `true` | export MTCONNECT_E2E_DOCKER=true | + +### `MTCONNECT_E2E_HOST_REPO_ROOT` + +| Kind | Source | Default / value | Context | +| --- | --- | --- | --- | +| `docker-env` | [`tools/dotnet.sh:90`](https://github.com/TrakHound/MTConnect.NET/blob/master/tools/dotnet.sh#L90) | `${REPO_ROOT}` | -e "MTCONNECT_E2E_HOST_REPO_ROOT=${REPO_ROOT}" | + +### `MTCONNECT_NUGET_VOLUME` + +| Kind | Source | Default / value | Context | +| --- | --- | --- | --- | +| `powershell-read` | [`tools/dotnet.ps1:46`](https://github.com/TrakHound/MTConnect.NET/blob/master/tools/dotnet.ps1#L46) | | $nugetVol = if ($env:MTCONNECT_NUGET_VOLUME) { $env:MTCONNECT_NUGET_VOLUME } else { 'mtconnect-net-nuget' } | +| `shell-read` | [`tools/dotnet.sh:64`](https://github.com/TrakHound/MTConnect.NET/blob/master/tools/dotnet.sh#L64) | `mtconnect-net-nuget` | NUGET_VOL="${MTCONNECT_NUGET_VOLUME:-mtconnect-net-nuget}" | + +### `MTCONNECT_PARITY_FIXTURE_DIR` + +| Kind | Source | Default / value | Context | +| --- | --- | --- | --- | +| `csharp-read` | [`tests/Compliance/MTConnect-Compliance-Tests/L2_CrossImpl/CppAgentParityWorkflowTests.cs:473`](https://github.com/TrakHound/MTConnect.NET/blob/master/tests/Compliance/MTConnect-Compliance-Tests/L2_CrossImpl/CppAgentParityWorkflowTests.cs#L473) | | = Environment.GetEnvironmentVariable(FixtureDirEnv) | + +Adding a new `Environment.GetEnvironmentVariable("…")` call, a new `${MTCONNECT_…}` read in a contributor script, or a new `$env:MTCONNECT_…` reference in a PowerShell script without regenerating this page fails the validation test in CI. + diff --git a/docs/reference/http-api.md b/docs/reference/http-api.md new file mode 100644 index 000000000..2fffd3fa5 --- /dev/null +++ b/docs/reference/http-api.md @@ -0,0 +1,581 @@ + + +# HTTP API reference + +This page lists every HTTP endpoint exposed by an MTConnect.NET agent, separated by the underlying transport implementation. The list is generated by walking the source tree with Roslyn and does not require any project to compile — including `MTConnect.NET-HTTP-AspNetCore`, which currently fails to build on `net8.0` (see `extra-files.user/spec/` for the porting issue) and is documented here statically. + +## Surface taxonomy + +- **Agent API** — the MTConnect-Standard request types (`/probe`, `/current`, `/sample`, `/assets`, `/asset/{id}`, and the per-device variants of the same). Every endpoint listed below currently belongs to this surface. +- **Admin / diagnostic** — none. No administrative endpoint is currently exposed by either transport. A search for `/admin`, `/diagnostics`, `/metrics`, or `/health` across the source tree returns no hits. + +## Ceen transport (`MTConnect.NET-HTTP`) + +Routes are registered inside `MTConnectHttpServer.ConfigureServer` and dispatched by the bundled Ceen router. + +| Method | Path | Handler | Source | +| --- | --- | --- | --- | +| `GET` | `(any)` | `probeHandler` | `libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:321` | +| `GET` | `/` | `probeHandler` | `libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:333` | +| `GET` | `/*/assets` | `assetsHandler` | `libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:341` | +| `GET` | `/*/current` | `currentHandler` | `libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:337` | +| `GET` | `/*/probe` | `probeHandler` | `libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:335` | +| `GET` | `/*/sample` | `sampleHandler` | `libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:339` | +| `GET` | `/asset/*` | `assetHandler` | `libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:342` | +| `GET` | `/assets` | `assetsHandler` | `libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:340` | +| `GET` | `/current` | `currentHandler` | `libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:336` | +| `GET` | `/probe` | `probeHandler` | `libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:334` | +| `GET` | `/sample` | `sampleHandler` | `libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:338` | +| `POST` | `(any)` | `postHandler` | `libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:329` | +| `PUT` | `(any)` | `putHandler` | `libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:325` | + +## AspNetCore transport (`MTConnect.NET-HTTP-AspNetCore`) + +Routes are declared on `[ApiController]` types under `Http/Controllers/`. The project does not currently build on `net8.0`, so this section is generated by static Roslyn inspection and will track any future controller changes regardless of build state. + +| Method | Path | Handler | Source | +| --- | --- | --- | --- | +| `GET` | `/` | `GlobalController.GetProbe` | `libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/GlobalController.cs:42` | +| `GET` | `/asset/{assetIds}` | `AssetController.GetAsset` | `libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/AssetController.cs:42` | +| `GET` | `/assets` | `AssetsController.GetAssets` | `libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/AssetsController.cs:46` | +| `GET` | `/current` | `GlobalController.GetCurrent` | `libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/GlobalController.cs:88` | +| `GET` | `/probe` | `GlobalController.GetProbe` | `libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/GlobalController.cs:43` | +| `GET` | `/sample` | `GlobalController.GetSample` | `libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/GlobalController.cs:212` | +| `GET` | `/{deviceKey}` | `DeviceController.GetDeviceProbe` | `libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/DeviceController.cs:43` | +| `GET` | `/{deviceKey}/assets` | `DeviceController.GetAssets` | `libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/DeviceController.cs:340` | +| `GET` | `/{deviceKey}/current` | `DeviceController.GetDeviceCurrent` | `libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/DeviceController.cs:90` | +| `GET` | `/{deviceKey}/probe` | `DeviceController.GetDeviceProbe` | `libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/DeviceController.cs:44` | +| `GET` | `/{deviceKey}/sample` | `DeviceController.GetDeviceSample` | `libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/DeviceController.cs:214` | +| `POST` | `/asset/{assetId}` | `AssetController.PostAsset` | `libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/AssetController.cs:80` | +| `PUT` | `/` | `GlobalController.PutDataItems` | `libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/GlobalController.cs:325` | +| `PUT` | `/asset/{assetId}` | `AssetController.PostAsset` | `libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/AssetController.cs:81` | +| `PUT` | `/{deviceKey}` | `DeviceController.PutDataItems` | `libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/DeviceController.cs:375` | + +## Per-endpoint detail + +### `GET /` — AspNetCore + +- **Handler**: `GlobalController.GetProbe` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/GlobalController.cs:42`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/GlobalController.cs#L42) +- **Response status codes**: 200, 400, 404, 405, 406, 431, 500 + +An Agent responds to a Probe Request with an MTConnectDevices Response Document that contains the Equipment Metadata for pieces of equipment that are requested and currently represented in the Agent. + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `deviceType` | Query | `string` | null | | +| `version` | Query | `Version` | null | The MTConnect Version of the response document | +| `documentFormat` | Query | `string` | DocumentFormat.XML | The format of the response document | +| `indentOutput` | Query | `bool?` | null | A boolean flag to indent the response document (pretty) | +| `outputComments` | Query | `bool?` | null | | + +### `GET /asset/{assetIds}` — AspNetCore + +- **Handler**: `AssetController.GetAsset` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/AssetController.cs:42`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/AssetController.cs#L42) +- **Response status codes**: 200, 400, 404, 500 + +An Agent responds to an Asset Request with an MTConnectAssets Response Document that contains information for MTConnect Assets from the Agent, subject to any filtering defined in the Request. + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `assetIds` | Route | `string` | | Identifies the IDs of the MTConnect Assets to be provided by an Agent. | +| `version` | Query | `Version` | null | The MTConnect Version of the response document | +| `documentFormat` | Query | `string` | DocumentFormat.XML | The format of the response document | +| `indentOutput` | Query | `bool?` | null | A boolean flag to indent the response document (pretty) | +| `outputComments` | Query | `bool?` | null | | + +### `GET /assets` — AspNetCore + +- **Handler**: `AssetsController.GetAssets` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/AssetsController.cs:46`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/AssetsController.cs#L46) +- **Response status codes**: 200, 400, 404, 500 + +An Agent responds to an Asset Request with an MTConnectAssets Response Document that contains information for MTConnect Assets from the Agent, subject to any filtering defined in the Request. + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `type` | Query | `string` | null | Defines the type of MTConnect Asset to be returned in the MTConnectAssets Response Document. | +| `removed` | Query | `bool` | false | An attribute that indicates whether the Asset has been removed from a piece of equipment. If the value of the removed parameter in the query is true, then Asset Documents for Assets that have been marked as removed from a piece of equipment will be included in the Response Document. If the value of the removed parameter in the query is false, then Asset Documents for Assets that have been marked as removed from a piece of equipment will not be included in the Response Document. | +| `count` | Query | `int` | 100 | Defines the maximum number of Asset Documents to return in an MTConnectAssets Response Document. | +| `version` | Query | `Version` | null | The MTConnect Version of the response document | +| `documentFormat` | Query | `string` | DocumentFormat.XML | The format of the response document | +| `indentOutput` | Query | `bool?` | null | A boolean flag to indent the response document (pretty) | +| `outputComments` | Query | `bool?` | null | | + +### `GET /current` — AspNetCore + +- **Handler**: `GlobalController.GetCurrent` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/GlobalController.cs:88`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/GlobalController.cs#L88) +- **Response status codes**: 200, 400, 404, 405, 406, 431, 500 + +An Agent responds to a Current Request with an MTConnectStreams Response Document that contains the current value of Data Entities associated with each piece of Streaming Data available from the Agent, subject to any filtering defined in the Request. + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `deviceType` | Query | `string` | null | | +| `path` | Query | `string` | null | An XPath that defines specific information or a set of information to be included in an MTConnectStreams Response Document. | +| `at` | Query | `long` | 0 | Requests that the MTConnect Response Documents MUST include the current value for all Data Entities relative to the time that a specific sequence number was recorded. | +| `interval` | Query | `int` | -1 | The Agent MUST continuously publish Response Documents when the query parameters include interval using the value as the minimum period between adjacent publications. | +| `heartbeat` | Query | `int` | 1000 | | +| `version` | Query | `Version` | null | The MTConnect Version of the response document | +| `documentFormat` | Query | `string` | DocumentFormat.XML | The format of the response document | +| `indentOutput` | Query | `bool?` | null | A boolean flag to indent the response document (pretty) | +| `outputComments` | Query | `bool?` | null | | + +### `GET /probe` — AspNetCore + +- **Handler**: `GlobalController.GetProbe` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/GlobalController.cs:43`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/GlobalController.cs#L43) +- **Response status codes**: 200, 400, 404, 405, 406, 431, 500 + +An Agent responds to a Probe Request with an MTConnectDevices Response Document that contains the Equipment Metadata for pieces of equipment that are requested and currently represented in the Agent. + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `deviceType` | Query | `string` | null | | +| `version` | Query | `Version` | null | The MTConnect Version of the response document | +| `documentFormat` | Query | `string` | DocumentFormat.XML | The format of the response document | +| `indentOutput` | Query | `bool?` | null | A boolean flag to indent the response document (pretty) | +| `outputComments` | Query | `bool?` | null | | + +### `GET /sample` — AspNetCore + +- **Handler**: `GlobalController.GetSample` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/GlobalController.cs:212`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/GlobalController.cs#L212) +- **Response status codes**: 200, 400, 404, 405, 406, 431, 500 + +An Agent responds to a Sample Request with an MTConnectStreams Response Document that contains a set of values for Data Entities currently available for Streaming Data from the Agent, subject to any filtering defined in the Request. + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `deviceType` | Query | `string` | null | | +| `path` | Query | `string` | null | An XPath that defines specific information or a set of information to be included in an MTConnectStreams Response Document. | +| `from` | Query | `long` | 0 | The from parameter designates the sequence number of the first observation in the buffer the Agent MUST consider publishing in the Response Document. | +| `to` | Query | `long` | 0 | The to parameter specifies the sequence number of the observation in the buffer that will be the upper bound of the observations in the Response Document. | +| `count` | Query | `int` | 100 | The count parameter designates the maximum number of observations the Agent MUST publish in the Response Document. | +| `interval` | Query | `int` | -1 | The Agent MUST continuously publish Response Documents when the query parameters include interval using the value as the minimum period between adjacent publications. | +| `heartbeat` | Query | `int` | 1000 | Sets the time period for the heartbeat function in an Agent. | +| `version` | Query | `Version` | null | The MTConnect Version of the response document | +| `documentFormat` | Query | `string` | DocumentFormat.XML | The format of the response document | +| `indentOutput` | Query | `bool?` | null | A boolean flag to indent the response document (pretty) | +| `outputComments` | Query | `bool?` | null | | + +### `GET /{deviceKey}` — AspNetCore + +- **Handler**: `DeviceController.GetDeviceProbe` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/DeviceController.cs:43`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/DeviceController.cs#L43) +- **Response status codes**: 200, 400, 404, 405, 406, 431, 500 + +An Agent responds to a Probe Request with an MTConnectDevices Response Document that contains the Equipment Metadata for pieces of equipment that are requested and currently represented in the Agent. + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `deviceKey` | Route | `string` | | A specific Path portion (name or uuid) | +| `version` | Query | `Version` | null | The MTConnect Version of the response document | +| `documentFormat` | Query | `string` | DocumentFormat.XML | The format of the response document | +| `indentOutput` | Query | `bool?` | null | A boolean flag to indent the response document (pretty) | +| `outputComments` | Query | `bool?` | null | | + +### `GET /{deviceKey}/assets` — AspNetCore + +- **Handler**: `DeviceController.GetAssets` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/DeviceController.cs:340`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/DeviceController.cs#L340) +- **Response status codes**: 200, 400, 404, 500 + +An Agent responds to an Asset Request with an MTConnectAssets Response Document that contains information for MTConnect Assets from the Agent, subject to any filtering defined in the Request. + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `deviceKey` | Route | `string` | | | +| `type` | Query | `string` | null | Defines the type of MTConnect Asset to be returned in the MTConnectAssets Response Document. | +| `removed` | Query | `bool` | false | An attribute that indicates whether the Asset has been removed from a piece of equipment. If the value of the removed parameter in the query is true, then Asset Documents for Assets that have been marked as removed from a piece of equipment will be included in the Response Document. If the value of the removed parameter in the query is false, then Asset Documents for Assets that have been marked as removed from a piece of equipment will not be included in the Response Document. | +| `count` | Query | `int` | 100 | Defines the maximum number of Asset Documents to return in an MTConnectAssets Response Document. | +| `version` | Query | `Version` | null | The MTConnect Version of the response document | +| `documentFormat` | Query | `string` | DocumentFormat.XML | The format of the response document | +| `indentOutput` | Query | `bool?` | null | A boolean flag to indent the response document (pretty) | +| `outputComments` | Query | `bool?` | null | | + +### `GET /{deviceKey}/current` — AspNetCore + +- **Handler**: `DeviceController.GetDeviceCurrent` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/DeviceController.cs:90`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/DeviceController.cs#L90) +- **Response status codes**: 200, 400, 404, 405, 406, 431, 500 + +An Agent responds to a Current Request with an MTConnectStreams Response Document that contains the current value of Data Entities associated with each piece of Streaming Data available from the Agent, subject to any filtering defined in the Request. + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `deviceKey` | Route | `string` | | The (name or uuid) of the requested Device | +| `path` | Query | `string` | null | An XPath that defines specific information or a set of information to be included in an MTConnectStreams Response Document. | +| `at` | Query | `long` | 0 | Requests that the MTConnect Response Documents MUST include the current value for all Data Entities relative to the time that a specific sequence number was recorded. | +| `interval` | Query | `int` | 0 | The Agent MUST continuously publish Response Documents when the query parameters include interval using the value as the minimum period between adjacent publications. | +| `heartbeat` | Query | `int` | 1000 | | +| `version` | Query | `Version` | null | The MTConnect Version of the response document | +| `documentFormat` | Query | `string` | DocumentFormat.XML | The format of the response document | +| `indentOutput` | Query | `bool?` | null | A boolean flag to indent the response document (pretty) | +| `outputComments` | Query | `bool?` | null | | + +### `GET /{deviceKey}/probe` — AspNetCore + +- **Handler**: `DeviceController.GetDeviceProbe` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/DeviceController.cs:44`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/DeviceController.cs#L44) +- **Response status codes**: 200, 400, 404, 405, 406, 431, 500 + +An Agent responds to a Probe Request with an MTConnectDevices Response Document that contains the Equipment Metadata for pieces of equipment that are requested and currently represented in the Agent. + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `deviceKey` | Route | `string` | | A specific Path portion (name or uuid) | +| `version` | Query | `Version` | null | The MTConnect Version of the response document | +| `documentFormat` | Query | `string` | DocumentFormat.XML | The format of the response document | +| `indentOutput` | Query | `bool?` | null | A boolean flag to indent the response document (pretty) | +| `outputComments` | Query | `bool?` | null | | + +### `GET /{deviceKey}/sample` — AspNetCore + +- **Handler**: `DeviceController.GetDeviceSample` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/DeviceController.cs:214`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/DeviceController.cs#L214) +- **Response status codes**: 200, 400, 404, 405, 406, 431, 500 + +An Agent responds to a Sample Request with an MTConnectStreams Response Document that contains a set of values for Data Entities currently available for Streaming Data from the Agent, subject to any filtering defined in the Request. + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `deviceKey` | Route | `string` | | The (name or uuid) of the requested Device | +| `path` | Query | `string` | null | An XPath that defines specific information or a set of information to be included in an MTConnectStreams Response Document. | +| `from` | Query | `long` | 0 | The from parameter designates the sequence number of the first observation in the buffer the Agent MUST consider publishing in the Response Document. | +| `to` | Query | `long` | 0 | The to parameter specifies the sequence number of the observation in the buffer that will be the upper bound of the observations in the Response Document. | +| `count` | Query | `int` | 100 | The count parameter designates the maximum number of observations the Agent MUST publish in the Response Document. | +| `interval` | Query | `int` | -1 | The Agent MUST continuously publish Response Documents when the query parameters include interval using the value as the minimum period between adjacent publications. | +| `heartbeat` | Query | `int` | 1000 | Sets the time period for the heartbeat function in an Agent. | +| `version` | Query | `Version` | null | The MTConnect Version of the response document | +| `documentFormat` | Query | `string` | DocumentFormat.XML | The format of the response document | +| `indentOutput` | Query | `bool?` | null | A boolean flag to indent the response document (pretty) | +| `outputComments` | Query | `bool?` | null | | + +### `POST /asset/{assetId}` — AspNetCore + +- **Handler**: `AssetController.PostAsset` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/AssetController.cs:80`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/AssetController.cs#L80) +- **Response status codes**: 200 + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `assetId` | Route | `string` | | | +| `device` | Query | `string` | | | +| `type` | Query | `string` | | | + +### `PUT /` — AspNetCore + +- **Handler**: `GlobalController.PutDataItems` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/GlobalController.cs:325`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/GlobalController.cs#L325) +- **Response status codes**: 200, 400, 500 + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `deviceName` | Route | `string` | | | +| `items` | Query | `Dictionary` | | | + +### `PUT /asset/{assetId}` — AspNetCore + +- **Handler**: `AssetController.PostAsset` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/AssetController.cs:81`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/AssetController.cs#L81) +- **Response status codes**: 200 + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `assetId` | Route | `string` | | | +| `device` | Query | `string` | | | +| `type` | Query | `string` | | | + +### `PUT /{deviceKey}` — AspNetCore + +- **Handler**: `DeviceController.PutDataItems` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/DeviceController.cs:375`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP-AspNetCore/Http/Controllers/DeviceController.cs#L375) +- **Response status codes**: 200, 400, 500 + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `deviceName` | Route | `string` | | | +| `items` | Query | `Dictionary` | | | + +### `GET (any)` — Ceen + +- **Handler**: `probeHandler` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:321`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs#L321) + +Method-gated dispatcher; routes the request to the handler matching the request method. + +### `GET /` — Ceen + +- **Handler**: `probeHandler` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:333`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs#L333) +- **Response status codes**: 200, 400, 404, 406, 500 + +Ceen request handler for the MTConnect Probe endpoint (GET /probe and GET /{deviceKey}/probe, plus the bare GET / alias). Returns an MTConnectDevices Response Document describing the device metadata visible to the agent. The optional leading path segment selects a single device by name or UUID. The response document format is negotiated via the documentFormat query parameter (xml | json | json-cppagent) and defaults to XML; deviceType, version, validationLevel, indentOutput, and outputComments further shape the payload. + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `deviceType` | Query | `string` | | Optional device-type filter. | +| `version` | Query | `string` | | Target MTConnect Standard version of the response document. | +| `documentFormat` | Query | `string` | xml | Response document format (xml \| json \| json-cppagent). | +| `validationLevel` | Query | `int` | | 0=ignore, 1=warning, 2=remove, 3=strict. | +| `indentOutput` | Query | `bool` | | Pretty-print the response document. | +| `outputComments` | Query | `bool` | | Emit comments / annotations in the response document. | + +### `GET /*/assets` — Ceen + +- **Handler**: `assetsHandler` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:341`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs#L341) +- **Response status codes**: 200, 400, 404, 406, 500 + +Ceen request handler for the MTConnect Assets endpoint (GET /assets and GET /{deviceKey}/assets). Returns an MTConnectAssets Response Document containing the asset records known to the agent. The optional leading path segment scopes the response to assets owned by a specific device; the type, removed, and count query parameters filter the asset set; documentFormat (xml | json | json-cppagent, default XML) and indentOutput negotiate the rendered representation. + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `type` | Query | `string` | | Asset type filter (e.g. CuttingTool). | +| `removed` | Query | `bool` | | Include removed assets when true. | +| `count` | Query | `int` | | Maximum number of assets. | +| `documentFormat` | Query | `string` | xml | Response document format. | +| `indentOutput` | Query | `bool` | | Pretty-print the response document. | + +### `GET /*/current` — Ceen + +- **Handler**: `currentHandler` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:337`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs#L337) +- **Response status codes**: 200, 400, 404, 406, 500 + +Ceen request handler for the MTConnect Current endpoint (GET /current and GET /{deviceKey}/current). Returns an MTConnectStreams Response Document containing the current observation snapshot for every data item visible to the agent, optionally filtered by an XPath in the path query parameter and anchored to a sequence number via at. When interval is supplied, the handler upgrades the response to a multipart x-mixed-replace stream and emits a fresh snapshot every interval milliseconds, interleaved with heartbeats. The response document format is negotiated via documentFormat (xml | json | json-cppagent), defaulting to XML; deviceType, version, indentOutput, and outputComments further shape the payload. + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `path` | Query | `string` | | XPath that filters the data items included in the response. | +| `at` | Query | `ulong` | | Sequence number anchoring the snapshot. | +| `interval` | Query | `int` | | Streaming interval in milliseconds; switches to multipart streaming when > 0. | +| `heartbeat` | Query | `int` | 10000 | Heartbeat interval for the streaming response. | +| `deviceType` | Query | `string` | | Optional device-type filter. | +| `version` | Query | `string` | | Target MTConnect Standard version of the response document. | +| `documentFormat` | Query | `string` | xml | Response document format. | +| `indentOutput` | Query | `bool` | | Pretty-print the response document. | +| `outputComments` | Query | `bool` | | Emit comments / annotations in the response document. | + +### `GET /*/probe` — Ceen + +- **Handler**: `probeHandler` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:335`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs#L335) +- **Response status codes**: 200, 400, 404, 406, 500 + +Ceen request handler for the MTConnect Probe endpoint (GET /probe and GET /{deviceKey}/probe, plus the bare GET / alias). Returns an MTConnectDevices Response Document describing the device metadata visible to the agent. The optional leading path segment selects a single device by name or UUID. The response document format is negotiated via the documentFormat query parameter (xml | json | json-cppagent) and defaults to XML; deviceType, version, validationLevel, indentOutput, and outputComments further shape the payload. + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `deviceType` | Query | `string` | | Optional device-type filter. | +| `version` | Query | `string` | | Target MTConnect Standard version of the response document. | +| `documentFormat` | Query | `string` | xml | Response document format (xml \| json \| json-cppagent). | +| `validationLevel` | Query | `int` | | 0=ignore, 1=warning, 2=remove, 3=strict. | +| `indentOutput` | Query | `bool` | | Pretty-print the response document. | +| `outputComments` | Query | `bool` | | Emit comments / annotations in the response document. | + +### `GET /*/sample` — Ceen + +- **Handler**: `sampleHandler` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:339`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs#L339) +- **Response status codes**: 200, 400, 404, 406, 500 + +Ceen request handler for the MTConnect Sample endpoint (GET /sample and GET /{deviceKey}/sample). Returns an MTConnectStreams Response Document containing a slice of historical observations bounded by the from / to / count query parameters, optionally filtered by an XPath in path. When interval is supplied, the handler upgrades the response to a multipart x-mixed-replace stream and emits successive sample windows every interval milliseconds, interleaved with heartbeats. The response document format is negotiated via documentFormat (xml | json | json-cppagent), defaulting to XML; deviceType, version, indentOutput, and outputComments further shape the payload. + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `path` | Query | `string` | | XPath that filters the data items included in the response. | +| `from` | Query | `ulong` | | Sequence number lower bound. | +| `to` | Query | `ulong` | | Sequence number upper bound. | +| `count` | Query | `int` | 100 | Maximum number of observations. | +| `interval` | Query | `int` | | Streaming interval in milliseconds; switches to multipart streaming when > 0. | +| `heartbeat` | Query | `int` | 10000 | Heartbeat interval for the streaming response. | +| `deviceType` | Query | `string` | | Optional device-type filter. | +| `version` | Query | `string` | | Target MTConnect Standard version of the response document. | +| `documentFormat` | Query | `string` | xml | Response document format. | +| `indentOutput` | Query | `bool` | | Pretty-print the response document. | +| `outputComments` | Query | `bool` | | Emit comments / annotations in the response document. | + +### `GET /asset/*` — Ceen + +- **Handler**: `assetHandler` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:342`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs#L342) +- **Response status codes**: 200, 400, 404, 406, 500 + +Ceen request handler for the single-asset MTConnect endpoint (GET /asset/{assetId}). Returns an MTConnectAssets Response Document containing the asset identified by the trailing path segment, or an MTConnectError document with status 404 when no such asset exists. The response document format is negotiated via the documentFormat query parameter (xml | json | json-cppagent) and defaults to XML. + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `assetId` | Route | `string` | | Asset identifier captured from the trailing path segment. | +| `documentFormat` | Query | `string` | xml | Response document format. | + +### `GET /assets` — Ceen + +- **Handler**: `assetsHandler` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:340`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs#L340) +- **Response status codes**: 200, 400, 404, 406, 500 + +Ceen request handler for the MTConnect Assets endpoint (GET /assets and GET /{deviceKey}/assets). Returns an MTConnectAssets Response Document containing the asset records known to the agent. The optional leading path segment scopes the response to assets owned by a specific device; the type, removed, and count query parameters filter the asset set; documentFormat (xml | json | json-cppagent, default XML) and indentOutput negotiate the rendered representation. + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `type` | Query | `string` | | Asset type filter (e.g. CuttingTool). | +| `removed` | Query | `bool` | | Include removed assets when true. | +| `count` | Query | `int` | | Maximum number of assets. | +| `documentFormat` | Query | `string` | xml | Response document format. | +| `indentOutput` | Query | `bool` | | Pretty-print the response document. | + +### `GET /current` — Ceen + +- **Handler**: `currentHandler` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:336`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs#L336) +- **Response status codes**: 200, 400, 404, 406, 500 + +Ceen request handler for the MTConnect Current endpoint (GET /current and GET /{deviceKey}/current). Returns an MTConnectStreams Response Document containing the current observation snapshot for every data item visible to the agent, optionally filtered by an XPath in the path query parameter and anchored to a sequence number via at. When interval is supplied, the handler upgrades the response to a multipart x-mixed-replace stream and emits a fresh snapshot every interval milliseconds, interleaved with heartbeats. The response document format is negotiated via documentFormat (xml | json | json-cppagent), defaulting to XML; deviceType, version, indentOutput, and outputComments further shape the payload. + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `path` | Query | `string` | | XPath that filters the data items included in the response. | +| `at` | Query | `ulong` | | Sequence number anchoring the snapshot. | +| `interval` | Query | `int` | | Streaming interval in milliseconds; switches to multipart streaming when > 0. | +| `heartbeat` | Query | `int` | 10000 | Heartbeat interval for the streaming response. | +| `deviceType` | Query | `string` | | Optional device-type filter. | +| `version` | Query | `string` | | Target MTConnect Standard version of the response document. | +| `documentFormat` | Query | `string` | xml | Response document format. | +| `indentOutput` | Query | `bool` | | Pretty-print the response document. | +| `outputComments` | Query | `bool` | | Emit comments / annotations in the response document. | + +### `GET /probe` — Ceen + +- **Handler**: `probeHandler` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:334`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs#L334) +- **Response status codes**: 200, 400, 404, 406, 500 + +Ceen request handler for the MTConnect Probe endpoint (GET /probe and GET /{deviceKey}/probe, plus the bare GET / alias). Returns an MTConnectDevices Response Document describing the device metadata visible to the agent. The optional leading path segment selects a single device by name or UUID. The response document format is negotiated via the documentFormat query parameter (xml | json | json-cppagent) and defaults to XML; deviceType, version, validationLevel, indentOutput, and outputComments further shape the payload. + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `deviceType` | Query | `string` | | Optional device-type filter. | +| `version` | Query | `string` | | Target MTConnect Standard version of the response document. | +| `documentFormat` | Query | `string` | xml | Response document format (xml \| json \| json-cppagent). | +| `validationLevel` | Query | `int` | | 0=ignore, 1=warning, 2=remove, 3=strict. | +| `indentOutput` | Query | `bool` | | Pretty-print the response document. | +| `outputComments` | Query | `bool` | | Emit comments / annotations in the response document. | + +### `GET /sample` — Ceen + +- **Handler**: `sampleHandler` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:338`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs#L338) +- **Response status codes**: 200, 400, 404, 406, 500 + +Ceen request handler for the MTConnect Sample endpoint (GET /sample and GET /{deviceKey}/sample). Returns an MTConnectStreams Response Document containing a slice of historical observations bounded by the from / to / count query parameters, optionally filtered by an XPath in path. When interval is supplied, the handler upgrades the response to a multipart x-mixed-replace stream and emits successive sample windows every interval milliseconds, interleaved with heartbeats. The response document format is negotiated via documentFormat (xml | json | json-cppagent), defaulting to XML; deviceType, version, indentOutput, and outputComments further shape the payload. + +**Parameters** + +| Name | Kind | Type | Default | Description | +| --- | --- | --- | --- | --- | +| `path` | Query | `string` | | XPath that filters the data items included in the response. | +| `from` | Query | `ulong` | | Sequence number lower bound. | +| `to` | Query | `ulong` | | Sequence number upper bound. | +| `count` | Query | `int` | 100 | Maximum number of observations. | +| `interval` | Query | `int` | | Streaming interval in milliseconds; switches to multipart streaming when > 0. | +| `heartbeat` | Query | `int` | 10000 | Heartbeat interval for the streaming response. | +| `deviceType` | Query | `string` | | Optional device-type filter. | +| `version` | Query | `string` | | Target MTConnect Standard version of the response document. | +| `documentFormat` | Query | `string` | xml | Response document format. | +| `indentOutput` | Query | `bool` | | Pretty-print the response document. | +| `outputComments` | Query | `bool` | | Emit comments / annotations in the response document. | + +### `POST (any)` — Ceen + +- **Handler**: `postHandler` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:329`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs#L329) + +Method-gated dispatcher; routes the request to the handler matching the request method. + +### `PUT (any)` — Ceen + +- **Handler**: `putHandler` +- **Surface**: Agent +- **Source**: [`libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs:325`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs#L325) + +Method-gated dispatcher; routes the request to the handler matching the request method. + diff --git a/docs/reference/index.md b/docs/reference/index.md new file mode 100644 index 000000000..86e612988 --- /dev/null +++ b/docs/reference/index.md @@ -0,0 +1,21 @@ + + +# Auto-generated reference + +Every page in this section is produced by `build/MTConnect.NET-DocsGen` at docs-build time by inspecting the source tree with Roslyn. Editing these files by hand will be overwritten on the next regeneration; instead, edit the source and re-run: + +```bash +dotnet run --project build/MTConnect.NET-DocsGen -- --repo . +``` + +## Pages + +- [HTTP API endpoints](./http-api) +- [Environment variables](./environment-variables) +- [Configuration schema](./configuration) +- [CLI reference](./cli) + +## Validation + +`MTConnect.NET-Docs-Tests` includes a `DocsReferenceGenerationTests` fixture that re-runs the same Roslyn / shell inventories and asserts the on-disk markdown is in sync. Adding an HTTP route, a `Environment.GetEnvironmentVariable("…")` read, a `${MTCONNECT_…}` reference in a contributor script, or a configuration property without regenerating the reference therefore fails CI. + diff --git a/docs/scripts/generate-api-ref.sh b/docs/scripts/generate-api-ref.sh new file mode 100755 index 000000000..761d11bec --- /dev/null +++ b/docs/scripts/generate-api-ref.sh @@ -0,0 +1,97 @@ +#!/usr/bin/env bash +# Generate the API reference Markdown under docs/api/. +# +# Compiles every shipped MTConnect.NET library in Release / net8.0, +# then runs `docfx metadata` against the produced DLLs and XML doc +# files. The output is a flat tree of `Namespace.Type.md` pages +# alongside per-namespace landing pages. +# +# Usage: +# bash docs/scripts/generate-api-ref.sh # full regen +# bash docs/scripts/generate-api-ref.sh --fast # skip the build +# +# Requirements: +# - dotnet 8 SDK +# - docfx (installed once via: dotnet tool install -g docfx) + +set -euo pipefail + +repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)" +cd "${repo_root}" + +skip_build=false +for arg in "$@"; do + case "${arg}" in + --fast) skip_build=true ;; + -h|--help) + sed -n '2,15p' "${BASH_SOURCE[0]}" + exit 0 + ;; + *) + echo "unknown argument: ${arg}" >&2 + exit 1 + ;; + esac +done + +libraries=( + "MTConnect.NET-Common" + "MTConnect.NET-DeviceFinder" + "MTConnect.NET-HTTP" + "MTConnect.NET-JSON" + "MTConnect.NET-JSON-cppagent" + "MTConnect.NET-MQTT" + "MTConnect.NET-Protobuf" + "MTConnect.NET-Services" + "MTConnect.NET-SHDR" + "MTConnect.NET-SysML" + "MTConnect.NET-TLS" + "MTConnect.NET-XML" + "MTConnect.NET" +) + +if ! "${skip_build}"; then + echo "==> building libraries in Debug for net8.0" + # Debug is the multi-target config that compiles ONLY net8.0 on every + # project — Release multi-targets net4.6.1..net9.0 and fails on SDKs + # that lack the legacy reference assemblies. The reference is content, + # not packaged output, so a Debug build is fine. + for lib in "${libraries[@]}"; do + dotnet build "libraries/${lib}/${lib}.csproj" \ + -c Debug \ + -p:GenerateDocumentationFile=true \ + -p:NoWarn=CS1591 \ + --nologo \ + -v:quiet + done +fi + +echo "==> running docfx metadata" +docfx_bin="docfx" +if ! command -v "${docfx_bin}" >/dev/null 2>&1; then + docfx_bin="${HOME}/.dotnet/tools/docfx" +fi +if ! command -v "${docfx_bin}" >/dev/null 2>&1; then + echo "docfx not found on PATH and ~/.dotnet/tools/docfx is missing." >&2 + echo "install with: dotnet tool install -g docfx" >&2 + exit 1 +fi + +# Clean previous output so removed types do not linger. +find docs/api -mindepth 1 -maxdepth 1 -not -name 'index.md' -exec rm -rf {} + + +"${docfx_bin}" metadata docs/.docfx/docfx.json --logLevel warning + +# docfx renders … as raw … HTML in the emitted +# markdown. VitePress's underlying Vue template compiler then treats +# {{ … }} inside that element as a mustache interpolation — +# e.g. {{term(data set)}} from the SysML representation +# markers is parsed as the JavaScript expression `term(data set)` and +# rejects the unquoted space. Mark every emitted as v-pre so +# Vue treats its contents as literal text rather than a template +# fragment. Safe to re-run because the clean step above wipes the +# output tree before docfx writes fresh files. +find docs/api -name '*.md' -not -name 'index.md' -print0 \ + | xargs -0 sed -i -E 's#]*)?>##g' + +echo "==> done. $(find docs/api -name '*.md' -not -name 'index.md' | wc -l) pages generated." diff --git a/docs/scripts/generate-reference.sh b/docs/scripts/generate-reference.sh new file mode 100755 index 000000000..292de8393 --- /dev/null +++ b/docs/scripts/generate-reference.sh @@ -0,0 +1,49 @@ +#!/usr/bin/env bash +# Regenerate the auto-generated reference pages under docs/reference/. +# +# Walks the repo source tree with Roslyn (via MTConnect.NET-DocsGen) +# and writes: +# +# docs/reference/http-api.md +# docs/reference/environment-variables.md +# docs/reference/configuration.md +# docs/reference/index.md +# +# Usage: +# bash docs/scripts/generate-reference.sh # regenerate +# bash docs/scripts/generate-reference.sh --check # CI gate; non-zero on drift +# +# Requirements: +# - dotnet 8 SDK + +set -euo pipefail + +repo_root="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)" +cd "${repo_root}" + +mode="generate" +for arg in "$@"; do + case "${arg}" in + --check) mode="check" ;; + -h|--help) + sed -n '2,18p' "${BASH_SOURCE[0]}" + exit 0 + ;; + *) + echo "unknown argument: ${arg}" >&2 + exit 1 + ;; + esac +done + +# Build once so subsequent runs are fast. +dotnet build build/MTConnect.NET-DocsGen/MTConnect.NET-DocsGen.csproj \ + -c Debug --nologo -v:quiet + +if [ "${mode}" = "check" ]; then + dotnet run --project build/MTConnect.NET-DocsGen --no-build \ + -- --repo . --check +else + dotnet run --project build/MTConnect.NET-DocsGen --no-build \ + -- --repo . +fi diff --git a/docs/troubleshooting/common-error-modes.md b/docs/troubleshooting/common-error-modes.md new file mode 100644 index 000000000..95952a387 --- /dev/null +++ b/docs/troubleshooting/common-error-modes.md @@ -0,0 +1,134 @@ +# Common error modes + +A field guide to error scenarios that come up in production deployments of `MTConnect.NET`. Each entry covers the symptom, the cause, and the fix. The four scenarios with dedicated pages — [XSD validation failures](/troubleshooting/xsd-validation-failures), [Schema version mismatches](/troubleshooting/schema-version-mismatches), and [MQTT TLS handshake](/troubleshooting/mqtt-tls-handshake) — are linked from here; this page indexes the rest. + +## Empty `name` on Probe DataItems + +**Symptom**: `/probe` returns DataItems whose `name` attribute is empty: + +```xml + +``` + +**Cause**: the DataItem was constructed with an explicit empty `Name` value (rather than a null `Name`, which the XML codec would omit). The serializer emits an attribute when the property is non-null, and the empty string passes the non-null check. + +**Fix**: leave `Name` null when no name is needed. The library treats null Name as "no name attribute on the wire"; only set Name when the SHDR adapter or another lookup pathway uses it. + +```csharp +// Correct +var di = new PositionDataItem("ctrl") { SubType = "ACTUAL" }; + +// Wrong — emits name="" on the wire. +var di = new PositionDataItem("ctrl") { SubType = "ACTUAL", Name = "" }; +``` + +## ASSET_COUNT emitted as a scalar EVENT instead of a DATA_SET + +**Symptom**: a cppagent-compatible consumer expects `representation="DATA_SET"` on the `ASSET_COUNT` DataItem and rejects the response when the library emits it as a scalar. + +**Cause**: this is the documented divergence between the spec's normative sources (SysML XMI + XSD) and the cppagent reference. The library follows the normative sources; see [Compliance: Known divergences](/compliance/known-divergences) and [Redmine #3890](https://projects.mtconnect.org/issues/3890). + +**Fix**: author the `ASSET_COUNT` DataItem with `representation="DATA_SET"` explicitly: + +```xml + +``` + +The library serializes the explicit representation as authored. + +## Pallet measurement constructors not present + +**Symptom**: a consumer expects to construct `HeightMeasurement`, `WidthMeasurement`, or `LoadedHeightMeasurement` and gets a "type not found" compile error. + +**Cause**: the library version pre-dates the v2.4 rich-template Pallet measurements. Earlier versions used the free-form `Measurement` class for every pallet measurement. + +**Fix**: upgrade `MTConnect.NET-Common` to a version that ships the v2.4 typed measurements. Alternatively, construct a free-form `Measurement` with the appropriate `Code`: + +```csharp +var m = new Measurement +{ + Code = "HEIGHT", + Value = 200m, + Units = "MILLIMETER", +}; +``` + +## Devices.xml validation surprises after a v2.x bump + +**Symptom**: a `Devices.xml` that validated under v2.3 fails under v2.5, even though no edits were made to the model itself. + +**Cause**: the v2.5 XSD tightened or added constraints (typically around attribute occurrence) that the v2.3 model did not satisfy. The library re-validates on every startup against the namespace declared in the document. + +**Fix**: read the validation error (it identifies the failing element), consult the [Per-version compliance matrix](/compliance/per-version-matrix) for the introduction version of any new constraint, and fix the model. See [Troubleshooting: XSD validation failures](/troubleshooting/xsd-validation-failures) for the category-by-category fix flow. + +## SHDR adapter disconnects every few minutes + +**Symptom**: the agent's `shdr-adapter` module log shows repeated reconnect cycles with `[WRN] SHDR connection lost; reconnecting in 1000ms`. + +**Causes**: + +1. The adapter's heartbeat interval is shorter than the agent's `heartbeat:` configuration. The agent expects a PING at least every `heartbeat` ms; if the adapter sends them less often, the agent times out. +2. A network device (firewall, load balancer) drops the TCP connection after an idle timeout. Long-running SHDR connections are vulnerable to NAT timeouts on cellular and VPN paths. +3. The adapter process is being recycled (memory pressure, scheduled restart) more often than the reconnect loop accommodates. + +**Fix**: + +- Match the agent's `heartbeat:` to the adapter's emit interval (e.g. `heartbeat: 2000` if the adapter pings every 2 s). +- Set the keepalive TCP socket option on the adapter side, or shorten the agent's `heartbeat:` so the dead connection is detected and re-established faster than the NAT timeout. +- If the adapter is unstable, run it as a systemd unit with `Restart=always`. + +## Agent serves stale observations after a buffer wipe + +**Symptom**: the agent's `/current` returns observations whose `Timestamp` is older than the agent's `creationTime`. A consumer reads "stale data" warnings. + +**Cause**: a durable-buffer restore loaded historical observations from the on-disk buffer. The observations are not stale per se — they are the most-recent values the agent has — but they look stale to a consumer that compares `Timestamp` against `now`. + +**Fix**: this is the intended behavior. To force a fresh start, set `durable: false` in `agent.config.yaml` or delete the `buffer/` directory before restarting. + +## MQTT relay's `availability` topic shows UNAVAILABLE even when connected + +**Symptom**: a subscriber to `/Probe/Availability` reads `UNAVAILABLE` even after the agent has reconnected to the broker. + +**Cause**: the broker's retained-message replay sent the consumer the previous LWT (Last Will and Testament) message before the relay's reconnect handler pushed the new `AVAILABLE` value. The retained-message protocol means subscribers see whatever was last published as retained, and the publish of `AVAILABLE` happens slightly after the client connects. + +**Fix**: wait for the relay's connect handler to fire; the `AVAILABLE` retained message will replace the stale `UNAVAILABLE`. For consumers that depend on immediate accuracy, subscribe to the topic with `qos: 1` and the broker re-delivers the latest retained value after the agent's connect handler fires. + +## HTTP /probe response is 503 or hangs + +**Symptom**: a curl against `/probe` hangs or returns `503 Service Unavailable`. + +**Causes**: + +1. The agent has not yet finished startup — the HTTP server module starts before the device-load step completes, and requests during that window return 503. +2. A long-running compaction or buffer-write operation is blocking the response path. +3. The agent is paused waiting for an adapter connection that never arrives. + +**Fix**: + +- For startup-window 503s, wait for the agent's log to print the "Devices loaded" line before sending requests. +- For sustained 503s, check the agent's metrics (`/probe?path=//Agent` returns the Agent Device's introspection observations). Adapter health is visible there. + +## Observations missing the `sequence` attribute + +**Symptom**: an XML observation envelope omits the `sequence` attribute, and a consumer paginating on it fails. + +**Cause**: a custom serializer was used that did not write `sequence`. The library always sets `Sequence` on every observation as it enters the buffer. + +**Fix**: use the library's `XmlFormatter`, `JsonFormatter`, or `JsonCppAgentFormatter` rather than a hand-rolled serializer. Each shipped formatter writes `sequence` on every observation as required by the XSD. + +## JSON-CPPAGENT response missing the array-of-wrappers shape + +**Symptom**: a v2-pinned consumer rejects the response because the observations are not wrapped in `{"": {...}}` envelopes. + +**Cause**: the response is being serialized through the JSON v1 codec rather than the JSON-CPPAGENT codec. The v1 codec mirrors the XML object structure one-to-one; the v2 codec uses the array-of-wrappers shape cppagent established. + +**Fix**: set `documentFormat: "json-cppAgent"` on the HTTP server module, or pass `Accept: application/mtconnect+json` on the request. The HTTP module dispatches by `Accept` header when the configuration's `accept:` map declares it. + +## Where to next + +- [Troubleshooting: XSD validation failures](/troubleshooting/xsd-validation-failures) — model-validation specifics. +- [Troubleshooting: Schema version mismatches](/troubleshooting/schema-version-mismatches) — version-pin specifics. +- [Troubleshooting: MQTT TLS handshake](/troubleshooting/mqtt-tls-handshake) — TLS specifics. +- [Compliance: Known divergences](/compliance/known-divergences) — where the library and the spec disagree. +- [Configure an agent](/configure/agent-config) — the agent-wide configuration. diff --git a/docs/troubleshooting/index.md b/docs/troubleshooting/index.md new file mode 100644 index 000000000..132c18432 --- /dev/null +++ b/docs/troubleshooting/index.md @@ -0,0 +1,30 @@ +# Troubleshooting + +Common errors when running `MTConnect.NET` and the fixes that work. Each entry follows the same shape: **symptom** (what you see in the logs or on the wire), **cause**, **fix**, and the **prevention** that keeps it from coming back. + +## Categories + +- **XSD validation failures** — the .NET BCL ships an XSD-1.0 validator, but several MTConnect XSDs use XSD-1.1 assertions. Symptoms include validation errors on documents that pass against the cppagent reference. Fix: route validation through the agent's structural validator (the per-class checks in `MTConnect.NET-Common`) and treat the XSD validator as advisory for the 1.1-only constructs. +- **Schema-version mismatches between agent and consumer** — a consumer requesting `version=2.4` from an agent built against v2.7 receives a v2.4-shaped envelope, but a consumer pinned to a fixed namespace URL sees a mismatch. Fix: have the consumer follow the namespace URL the agent emits in the response root rather than hard-coding it. +- **MQTT TLS handshake failures** — usually a certificate-chain problem when running against AWS IoT, HiveMQ Cloud, or any broker that requires mutual TLS. Fix: regenerate the certificate chain with OpenSSL (see the [OpenSSL guide](/configure/integrations/openssl)), confirm the agent's TLS configuration block points at the right `.pfx` or `.pem` paths, and verify the broker's CA bundle is in the agent's trust store. +- **Empty `name` attributes on probe DataItems** — caused by a `Devices.xml` that omits the `name` attribute on a DataItem and relies on the agent to synthesize one. Fix: add an explicit `name` attribute to every DataItem in `Devices.xml`; the spec does not require it on every DataItem but consumers often do. +- **Asset count emitted as a scalar EVENT instead of a DATA_SET** — happens on agents built against very old spec versions where `AssetCountDataSet` did not yet exist. Fix: bump the target spec version in the agent config to v1.7 or later and re-emit the device. +- **`Devices.xml` validation surprises after a v2.x bump** — new spec versions add new controlled-vocabulary values and tighten existing ones. Fix: validate `Devices.xml` against the per-version XSDs the agent ships under `schemas/` and resolve each error against the spec's release notes for that version. +- **Pallet measurement constructors not present** — the rich-template Pallet measurement types are introduced in newer spec versions. Fix: confirm the library version supports the spec version you target, and consult the API page for `PalletMeasurement` (and its specializations) for the introduced-in badge. +- **HTTP server port already in use** — the default port `5000` is shared with several other .NET application templates. Fix: change `http-server.port` in `agent.config.yaml`, or stop the conflicting process. +- **Devices not appearing in `/probe`** — the most common cause is a `Devices.xml` parse error that the agent logs but does not crash on. Fix: check the agent log for the parse error, fix the malformed XML, restart. +- **Buffer-overflow log messages under load** — the agent's sequence buffer has a configurable size and drops the oldest observations when full. Fix: increase `buffer.maximumSize` in `agent.config.yaml`, or process the buffer faster via more responsive consumers. + +## Reading the agent logs + +The agent writes to `stdout` by default and to a configurable log file when running as a service. Log levels: `Debug`, `Info`, `Warning`, `Error`, `Fatal`. Most fixable issues surface at `Warning` and `Error`. To capture the most diagnostic information, set the global log level to `Debug` temporarily — the volume is high, so do not leave it on in production. + +## When the fix is not here + +- Check the [Cookbook](/cookbook/) for the recipe that matches your deployment pattern — the recipe may already work around the issue. +- Open an issue at with the agent version, the relevant log lines, and a minimal `agent.config.yaml` + `Devices.xml` that reproduces the symptom. + +## See also + +- [Configure & Use](/configure/) — the per-knob reference for every setting troubleshooting touches. +- [Compliance](/compliance/) — when the agent and the cppagent reference disagree, the compliance section names which one `MTConnect.NET` follows and why. diff --git a/docs/troubleshooting/mqtt-tls-handshake.md b/docs/troubleshooting/mqtt-tls-handshake.md new file mode 100644 index 000000000..de7fbb99e --- /dev/null +++ b/docs/troubleshooting/mqtt-tls-handshake.md @@ -0,0 +1,200 @@ +# MQTT TLS handshake failures + +The `mqtt-relay`, `mqtt-broker`, and `mqtt-adapter` modules each support TLS termination through the shared [`TlsConfiguration`](/api/MTConnect.Tls/TlsConfiguration) class. When the TLS handshake fails, the agent logs a structured error and refuses to publish or subscribe. This page documents the common handshake failures and the resolution path for each. + +## Symptoms + +A failed TLS handshake typically surfaces as: + +- The relay logs `[ERR] MQTT TLS handshake failed: `. +- The relay reconnect loop spins (every `reconnectInterval` ms the same failure repeats). +- A subscriber connecting through the same broker fails with the same error. +- A `mosquitto_sub -h -p 8883` from a known-good client fails too, confirming the broker side. + +The shipped relay surfaces enough detail in the log to map directly to the root cause; this page indexes the most common error messages. + +## Diagnostic flow + +```mermaid +flowchart TD + A[Handshake error logged] --> B{Error category} + B -->|certificate not trusted| C[CA chain issue] + B -->|hostname does not match| D[CN / SAN mismatch] + B -->|key not found| E[Private key file missing or unreadable] + B -->|expired| F[Certificate past notAfter] + B -->|protocol| G[TLS version negotiation] + B -->|cipher| H[Cipher suite mismatch] + C --> R[Resolution per category] + D --> R + E --> R + F --> R + G --> R + H --> R +``` + +## Category 1: certificate not trusted + +**Log**: + +```text +[ERR] MQTT TLS handshake failed: The remote certificate is invalid according to the validation procedure. +``` + +**Cause**: the agent's TLS client cannot validate the broker's certificate chain against any root CA it trusts. Either the broker is using a self-signed certificate the agent has not been told about, or the broker's certificate was issued by a private CA the agent does not have in its trust store. + +**Fix**: configure the `tls.pem.certificateAuthority` to point at the CA's PEM file: + +```yaml +modules: +- mqtt-relay: + server: broker.example.com + port: 8883 + useTls: true + tls: + pem: + certificateAuthority: /etc/mtconnect/ca.crt + certificatePath: /etc/mtconnect/agent.crt + privateKeyPath: /etc/mtconnect/agent.key + privateKeyPassword: +``` + +The `certificateAuthority` file is appended to the platform trust store for the duration of the relay's connection. For brokers using a public CA (Let's Encrypt, DigiCert, etc.), the platform trust store already trusts the root and the `certificateAuthority` key can be omitted entirely. + +## Category 2: hostname does not match + +**Log**: + +```text +[ERR] MQTT TLS handshake failed: The remote certificate is invalid because of errors in the certificate chain: PartialChain +``` + +or + +```text +[ERR] MQTT TLS handshake failed: The certificate's hostname does not match the requested server name. +``` + +**Cause**: the certificate's CN / SAN list does not include the hostname the relay is connecting to. A certificate issued for `broker.example.com` does not validate a connection to `192.168.1.50`. + +**Fix**: connect to the broker by the hostname listed in the certificate. If the broker has multiple addresses (IP + hostname), use the hostname: + +```yaml +- mqtt-relay: + server: broker.example.com # not 192.168.1.50 + port: 8883 +``` + +For development against a self-signed certificate that you trust, the [OpenSSL](/configure/integrations/openssl) integration page walks through re-issuing the certificate with the right SAN entries. + +## Category 3: private key file missing or unreadable + +**Log**: + +```text +[ERR] MQTT TLS handshake failed: Could not load private key from /etc/mtconnect/agent.key. +``` + +**Cause**: the agent's TLS client uses a client certificate (mutual TLS), and the corresponding private key file is either missing or not readable by the agent's process user. + +**Fix**: + +1. Confirm the file exists at the configured `privateKeyPath`. +2. Confirm the agent's process user has read permission on it: `ls -la /etc/mtconnect/agent.key`. The file is typically `0600` owned by the agent's user. +3. Confirm the `privateKeyPassword` is correct if the key is encrypted. + +## Category 4: certificate expired + +**Log**: + +```text +[ERR] MQTT TLS handshake failed: The remote certificate is invalid: certificate has expired. +``` + +**Cause**: the broker's certificate (or the agent's client certificate) is past its `notAfter` date. + +**Fix**: + +1. Inspect the certificate's validity window: `openssl x509 -in broker.crt -noout -dates`. +2. Renew the certificate. For Let's Encrypt-issued certs, the broker's renewal hook should run automatically; for private CAs, re-issue and re-deploy. +3. Restart the relay (or wait for the next `reconnectInterval` to elapse) so the new certificate is loaded. + +## Category 5: TLS version negotiation + +**Log**: + +```text +[ERR] MQTT TLS handshake failed: Authentication failed because the remote party has closed the transport stream. +``` + +**Cause**: the broker accepts only TLS 1.2+ and the agent's runtime defaults to a lower version, or vice versa. .NET 6+ defaults to TLS 1.2 / 1.3 negotiation; older runtimes may default to TLS 1.0 / 1.1. + +**Fix**: + +- If the agent runs on .NET Framework 4.6.1 / 4.7, set the `SecurityProtocol` early in startup: `System.Net.ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12 | SecurityProtocolType.Tls13;`. +- If the broker is the limiting party, configure it to accept TLS 1.2; on Mosquitto this is `tls_version tlsv1.2` in `mosquitto.conf`. + +The shipped library targets `SslProtocols.None` (let the runtime pick the highest mutually-supported version) by default, which works for any broker accepting TLS 1.2+ on .NET 6+. + +## Category 6: cipher suite mismatch + +**Log**: + +```text +[ERR] MQTT TLS handshake failed: A call to SSPI failed, see inner exception. The Local Security Authority cannot be contacted. +``` + +**Cause**: the broker advertises a cipher suite set that does not intersect with the agent's runtime's cipher suite set. This is most common on legacy Mosquitto deployments with `ciphers HIGH:!aNULL:!MD5` overrides. + +**Fix**: relax the broker's cipher restrictions, or configure the agent's runtime to enable a cipher the broker supports. The runtime-side fix is .NET-version-specific; consult the [.NET TLS configuration docs](https://learn.microsoft.com/dotnet/framework/network-programming/tls). + +## Category 7: clock skew + +**Log**: + +```text +[ERR] MQTT TLS handshake failed: The remote certificate is invalid: certificate is not yet valid. +``` + +**Cause**: the agent's clock is set to a time before the certificate's `notBefore` date. Common on freshly-provisioned VMs whose NTP sync has not yet happened. + +**Fix**: configure NTP and let the clock sync. Re-attempting after the clock corrects resolves it without restart. + +## Mutual TLS + +For brokers that require client-certificate authentication (mTLS), the relay's `tls.pem.certificatePath` is the agent's client certificate (not the broker's CA), and `tls.pem.privateKeyPath` is the agent's private key. The full config: + +```yaml +- mqtt-relay: + server: broker.example.com + port: 8883 + useTls: true + tls: + pem: + certificateAuthority: /etc/mtconnect/ca.crt # broker's CA + certificatePath: /etc/mtconnect/agent.crt # agent's client cert + privateKeyPath: /etc/mtconnect/agent.key # agent's client key + privateKeyPassword: +``` + +The broker's CA file validates the broker's server certificate; the agent's certificate and key authenticate the agent to the broker. Both halves are required for mTLS. + +## Verifying with openssl + +When the handshake fails and the cause is not obvious from the log, the next step is to reproduce the handshake outside the agent: + +```sh +openssl s_client -connect broker.example.com:8883 \ + -CAfile /etc/mtconnect/ca.crt \ + -cert /etc/mtconnect/agent.crt \ + -key /etc/mtconnect/agent.key \ + -tls1_2 < /dev/null +``` + +A successful run prints the broker's certificate chain and the negotiated cipher. A failed run prints the same error category the agent would see; cross-check against the categories above. + +## Where to next + +- [Configure modules: MQTT relay](/configure/module-config#mqtt-relay) — the full TLS config-key reference. +- [Cookbook: Configure MQTT relay](/cookbook/configure-mqtt-relay) — the TLS-enabled relay walk-through. +- [Configure & Use: OpenSSL setup](/configure/integrations/openssl) — generating certificates for development. +- [Troubleshooting: Common error modes](/troubleshooting/common-error-modes) — for non-TLS connection failures. diff --git a/docs/troubleshooting/schema-version-mismatches.md b/docs/troubleshooting/schema-version-mismatches.md new file mode 100644 index 000000000..b87898d3c --- /dev/null +++ b/docs/troubleshooting/schema-version-mismatches.md @@ -0,0 +1,139 @@ +# Schema version mismatches + +The MTConnect spec is published per major.minor version, with one XSD per envelope per version. When the agent, the consumer, and the device model disagree on which version is in play, the symptoms are subtle — a `/probe` response that omits an attribute the consumer expected, a `Devices.xml` that fails validation, an MQTT payload that does not parse — and the fix depends on the version misalignment's shape. This page is the diagnostic playbook. + +## What "version" means in three places + +At least three distinct version values can be in play simultaneously: + +1. **`Devices.xml` namespace**: the spec version the device model is authored against (`urn:mtconnect.org:MTConnectDevices:2.5`). The XSD validator uses this to pick the schema. +2. **Agent's `defaultVersion`**: the spec version the agent serializes responses for when the request omits `?version=`. Configured in `agent.config.yaml`. +3. **Request's `?version=` parameter**: the consumer's per-request override of the agent's default. + +The agent reconciles these per request: + +```mermaid +flowchart TD + Req[Consumer request] --> Q{Has ?version=} + Q -->|yes| RV[Use request version] + Q -->|no| AV{Has agent defaultVersion} + AV -->|yes| AVv[Use agent defaultVersion] + AV -->|no| MV[Use MTConnectVersions.Max] + RV --> SER[Serialize response] + AVv --> SER + MV --> SER + SER --> CK{Devices.xml namespace newer than target} + CK -->|yes| ERR[Error response] + CK -->|no| OUT[Response envelope] +``` + +Three distinct mismatch shapes follow from this flow. + +## Mismatch 1: consumer requests a version newer than the agent supports + +**Symptom**: the agent returns an Error envelope: + +```xml + +
+ + The requested version '2.8' is not supported by this agent. + + +``` + +**Cause**: the consumer asked for a version higher than `MTConnectVersions.Max`. The library's `Max` advertises the highest version the library can serialize for. + +**Fix**: either upgrade the agent (so `MTConnectVersions.Max` covers the requested version), or have the consumer pin to a version the agent supports. + +## Mismatch 2: Devices.xml namespace exceeds the agent's `Max` + +**Symptom**: the agent fails to start with: + +```text +[ERR] Devices.xml declares namespace 'urn:mtconnect.org:MTConnectDevices:3.0', + but this agent supports up to MTConnectDevices_2.7.xsd. +``` + +**Cause**: the device model was authored against a spec version the library has not yet shipped support for. + +**Fix**: upgrade the library, or downgrade the `Devices.xml` namespace to the highest version the library supports. If the device model uses features introduced in the newer version, those features will need to be re-authored against the older shape — see [Cookbook: Migrate between MTConnect versions](/cookbook/migrate-versions). + +## Mismatch 3: consumer rejects an attribute introduced in a later version + +**Symptom**: the consumer's parser throws an error like `Unknown attribute 'hash' on Header element`. + +**Cause**: the agent is serializing responses for a higher version than the consumer's parser was built against. A consumer pinned to v2.1 sees the v2.2-introduced `Hash` attribute on `Header` and rejects it. + +**Fix**: either upgrade the consumer's parser, or pin the consumer's requests with `?version=2.1`. The agent prunes v2.2-introduced attributes when serializing for v2.1. + +## Mismatch 4: consumer expects a DataItem that does not appear + +**Symptom**: the consumer queries `/current?path=//DataItem[@type='ASSET_COUNT']` and the response is empty, even though the device model declares an `AssetCount` DataItem on the Agent Device. + +**Cause**: the requested version is below the DataItem's `MinimumVersion`. `ASSET_COUNT` enters at v1.2; a request with `?version=1.0` elides it. + +**Fix**: pin the request to a version at or above the DataItem's `MinimumVersion`. The introduction version is on the DataItem's API reference page. + +## Mismatch 5: SHDR adapter sends a DataItem key the agent does not have + +**Symptom**: the agent logs `[WRN] Received SHDR observation for unknown DataItem 'x-pos-actual' on Device 'mill-01'`. + +**Cause**: the adapter is using a DataItem key (`Id` or `Name`) that does not exist in the version-resolved Device model. This often happens when the adapter was authored against a model that has since been pruned because the agent runs at an older version that elides the DataItem. + +**Fix**: serialize the Device model at the version the adapter expects, or update the adapter to send only DataItem keys that survive at the agent's target version. + +## How to read the version on the wire + +Every response carries a `schemaVersion` attribute on the `Header` element: + +```xml +
+``` + +Inspect the response to confirm which version the agent actually serialized at: + +```sh +curl -s http://agent:5000/probe | grep schemaVersion +``` + +The output: + +```text +
+``` + +If `schemaVersion` is not what you expected, the agent picked it from one of the three sources above; check `agent.config.yaml`'s `defaultVersion`, then re-read the request URL for a `?version=` parameter. + +## How to read the version a class lives at + +A consumer wondering "is this DataItem available at v2.0?" can introspect: + +```csharp +using System; +using MTConnect.Devices.DataItems; + +var minVer = new AssetCountDataItem().MinimumVersion; +Console.WriteLine($"AssetCount introduced at {minVer}"); +// → AssetCount introduced at 1.2 +``` + +Every class exposes `MinimumVersion` and `MaximumVersion` properties; the introduction-version metadata is generated from the SysML model's `introducedAtVersion` tag and is auditable through the type's API reference page. + +## Production patterns + +To avoid surprise mismatches in production: + +- **Pin explicitly**: set `defaultVersion` in `agent.config.yaml` and `?version=` in every consumer request. Default-to-Max is the source of "the agent upgraded and now my consumer breaks" stories. +- **Validate at build time**: run `xmllint --noout --schema ` against `Devices.xml` in CI. The agent does this on startup; CI catches it earlier. +- **Test against the version pair**: a consumer pinned to v2.1 should have a test suite that asserts its behavior against a v2.1-pinned agent, not against an agent running at `MTConnectVersions.Max`. +- **Audit on bump**: when bumping the library version, re-run the consumer-side schema validator against captured responses. The `Header.schemaVersion` in those captures tells you which schema to validate against. + +## Where to next + +- [Cookbook: Migrate between MTConnect versions](/cookbook/migrate-versions) — the migration playbook. +- [Compliance: Per-version matrix](/compliance/per-version-matrix) — which features ship in which version. +- [Troubleshooting: XSD validation failures](/troubleshooting/xsd-validation-failures) — the diagnostic flow when validation fails. +- [Configure an agent](/configure/agent-config) — where `defaultVersion` lives. diff --git a/docs/troubleshooting/xsd-validation-failures.md b/docs/troubleshooting/xsd-validation-failures.md new file mode 100644 index 000000000..abe5b852f --- /dev/null +++ b/docs/troubleshooting/xsd-validation-failures.md @@ -0,0 +1,172 @@ +# XSD validation failures + +The MTConnect XSDs are strict. When a `Devices.xml` or a runtime envelope fails XSD validation, the library logs a structured error and (for `Devices.xml` at agent startup) refuses to continue. This page documents the common failures, what they mean, and how to fix each. + +## Symptoms + +A failed validation typically surfaces as one of: + +- Agent startup logs a `XmlSchemaException` and exits with a non-zero code. +- A request to `/probe` returns a `MTConnectError` envelope with `errorCode="INVALID_DEVICES"`. +- A consumer rejects the agent's response with a "schema validation failed" exception. +- A compliance test fixture fails with an assertion message naming an XSD line number. + +## Diagnostic flow + +```mermaid +flowchart TD + A[Validation failure observed] --> B{Where?} + B -->|Agent startup| C[Check agent log for XmlSchemaException] + B -->|Runtime endpoint| D[Capture the response envelope] + B -->|Compliance test| E[Read the test's expected XSD line] + C --> F[Open Devices.xml at the failing element] + D --> F + E --> F + F --> G{Failure category} + G -->|Unknown element| H[XSD does not allow this child] + G -->|Missing required attribute| I[XSD requires an attribute the model omitted] + G -->|Enum value| J[XSD constrains the value to an enum list] + G -->|Type mismatch| K[XSD expects a different shape] +``` + +Resolve based on the failure category below. + +## Category 1: Unknown element + +Example log: + +```text +The element 'Component' has invalid child element 'CustomThing'. +List of possible elements expected: 'DataItems, Components, Compositions, References, Configuration'. +``` + +**Diagnosis**: the `Devices.xml` declares an element the XSD does not allow at that nesting depth. Most often this is a Component / Composition / DataItem type that was introduced in a later spec version than the document's namespace declares — for example, a v2.4 `PalletAsset` measurement in a document whose namespace is `urn:mtconnect.org:MTConnectAssets:2.3`. + +**Fix**: + +1. Identify the element's introduction version (see [Per-version matrix](/compliance/per-version-matrix) or the API page for the element). +2. Bump the document's namespace to match the introduction version, or remove the offending element. +3. Re-validate. + +## Category 2: Missing required attribute + +Example log: + +```text +The element 'DataItem' is missing the required attribute 'id'. +``` + +**Diagnosis**: a DataItem (or Component, Device, Composition) declared in the model omits an attribute the XSD marks `use="required"`. `id` is required everywhere; `category` and `type` are required on every `DataItem`. + +**Fix**: + +1. Open the offending element. +2. Add the missing attribute. For `id`, generate a unique value across the Device. +3. Re-validate. + +## Category 3: Enum value violation + +Example log: + +```text +The 'category' attribute is invalid. The value 'INFO' is invalid according to its datatype. +The enumeration constraint failed. +``` + +**Diagnosis**: an attribute carries a value not in the XSD's enumerated list. For `category`, the spec-defined values are `EVENT`, `SAMPLE`, `CONDITION` ([`MTConnect.Devices.DataItemCategory`](/api/MTConnect.Devices/DataItemCategory)). For `representation`, the values are `VALUE`, `DATA_SET`, `TABLE`, `TIME_SERIES` ([`MTConnect.Devices.DataItemRepresentation`](/api/MTConnect.Devices/DataItemRepresentation)). + +**Fix**: + +1. Look up the attribute's spec-defined enum on the API reference page for the containing element. +2. Replace the invalid value with a spec-defined one. +3. Re-validate. + +## Category 4: Type mismatch + +Example log: + +```text +The 'sampleRate' attribute is invalid. The value 'fast' does not match the pattern '[+-]?\d*(\.\d+)?'. +``` + +**Diagnosis**: a numeric or pattern-constrained attribute carries a non-conforming value. `sampleRate`, `sampleInterval`, `assetCount`, and most timestamps have format-pattern constraints. + +**Fix**: + +1. Inspect the attribute's XSD declaration (the `xs:pattern` or `xs:simpleType` it points at). +2. Re-format the value to match. +3. Re-validate. + +## Category 5: XSD 1.1 assertion failure + +A small number of MTConnect XSDs use XSD 1.1's `xs:assert` element to encode cross-attribute constraints (such as "if `representation='DATA_SET'`, then ...). The .NET BCL's XSD validator is XSD 1.0; it does not enforce `xs:assert` at parse time. The library injects runtime checks for the most-likely-to-be-violated assertions, but a validator on a different toolchain (Java's Xerces, libxml2 with XSD 1.1 enabled) might surface an assertion failure the .NET validator did not. + +**Symptom**: validation succeeds against `MTConnect.NET`'s XSD validator but fails against an external XSD 1.1 validator. + +**Fix**: + +1. Identify the failing assertion in the external validator's log. +2. Adjust the model to satisfy the assertion. The library's runtime checks log a warning when the same constraint is at risk. +3. If the assertion is not enforced by the library at runtime, file an issue at [TrakHound/MTConnect.NET](https://github.com/TrakHound/MTConnect.NET/issues) so the library can pick it up. + +## A worked example + +A consumer sends this `Devices.xml`: + +```xml + + + + + + + + + +``` + +The agent rejects it with: + +```text +[ERR] XmlSchemaException: The element 'DataItem' with type 'CONTROLLER_MODE' is declared + under the Device root, but CONTROLLER_MODE is only allowed under a Controller component. +``` + +**Diagnosis**: `CONTROLLER_MODE` is spec-defined to live on a `Controller` component, not directly under the Device. The XSD encodes this via element-substitution groups; the validator catches it. + +**Fix**: wrap the `DataItem` in a `Controller` component: + +```xml + + + + + + + + + +``` + +Re-validate; the agent now starts. + +## Cross-validator differences + +Different XSD validators report the same error in different shapes. A short translation guide: + +| Validator | "Unknown element" wording | +|---|---| +| .NET BCL `XmlSchemaValidator` | `The element ... has invalid child element ...` | +| `xmllint` | `element ...: This element is not expected.` | +| Java Xerces | `cvc-complex-type.2.4.a: Invalid content was found starting with element ...` | + +If a CI test validates against one toolchain and a local check uses another, expect different wording. The substance is the same. + +## Where to next + +- [Per-version compliance matrix](/compliance/per-version-matrix) — confirm which version introduces an element. +- [Compliance: Wire-format compliance](/compliance/wire-format) — the validation tier in the compliance harness. +- [Troubleshooting: Schema version mismatches](/troubleshooting/schema-version-mismatches) — when the validation issue is a version mis-pin rather than a content error. +- [Concepts: Devices](/concepts/devices) — the model-authoring fundamentals. diff --git a/docs/wire-formats/index.md b/docs/wire-formats/index.md new file mode 100644 index 000000000..a46972817 --- /dev/null +++ b/docs/wire-formats/index.md @@ -0,0 +1,44 @@ +# Wire formats + +`MTConnect.NET` ships codecs for every wire format the MTConnect Standard recognizes, plus the SHDR adapter protocol that feeds the agent from upstream. This section is the codec-level reference — sample envelopes, codec class names, spec-version compatibility, and Mermaid sequence diagrams for the wire-flow handshakes. + +## The five formats + +- **[XML](./xml)** — the canonical wire format defined by the per-version XSDs (`MTConnectStreams_.xsd`, `MTConnectDevices_.xsd`, `MTConnectAssets_.xsd`, `MTConnectError_.xsd`). Codec lives in `MTConnect.NET-XML`. Validated at write-time against the corresponding XSD. +- **[JSON v1](./json-v1)** — the legacy JSON codec, object-keyed everywhere. Pre-dates the formal cppagent JSON v2 codec; shipped for compatibility with consumers built against early MTConnect.NET releases. Codec lives in `MTConnect.NET-JSON`. +- **[JSON-CPPAGENT (v2)](./json-cppagent)** — the cppagent reference's current JSON codec. Array-of-wrappers where order matters; object-keyed where it doesn't. Byte-for-byte cppagent parity is the library's compliance target. Codec lives in `MTConnect.NET-JSON-cppagent`. +- **[JSON-CPPAGENT-MQTT](./json-cppagent-mqtt)** — JSON-CPPAGENT v2 envelopes published over MQTT topics with a documented topic tree. Codec lives in `MTConnect.NET-JSON-cppagent` plus the `MTConnect.NET-MQTT` transport layer. +- **[SHDR](./shdr)** — the Simple Hierarchical Data Representation; the line-oriented adapter protocol that ships values from a PLC reader into the agent. Codec lives in `MTConnect.NET-SHDR`. + +## Picking a format + +```mermaid +flowchart TD + Start{What are you building?} --> Cons{Consumer or adapter?} + Cons -->|Consumer| Lang{Target language / runtime} + Cons -->|Adapter| SHDR[SHDR] + Lang -->|Dashboard / browser| XML[XML] + Lang -->|Modern .NET / Python / Node| JSONv2[JSON-CPPAGENT v2] + Lang -->|MQTT subscriber| JSONMQTT[JSON-CPPAGENT-MQTT] + Lang -->|Legacy MTConnect.NET-only| JSONv1[JSON v1] +``` + +- Pulling data into a dashboard? XML is the canonical format and every consumer can read it. +- Building a modern consumer in any non-browser runtime? Use JSON-CPPAGENT v2 — it's the cppagent-parity format and the spec's current direction. +- Subscribing to a stream over MQTT? Use JSON-CPPAGENT-MQTT. +- Maintaining an old consumer built before the JSON v2 codec landed? JSON v1 still ships. +- Feeding the agent from upstream equipment? Use SHDR if your reader speaks it; the MQTT adapter and HTTP adapter are alternatives. + +## Spec-version compatibility + +Every wire-format page lists the MTConnect spec versions the format is conformant for, along with the per-version differences (new envelope types, new attributes, deprecated fields). The agent emits the wire format that matches the spec version the consumer requests. + +## Round-tripping + +Every codec in `MTConnect.NET` is symmetric — it both reads and writes its format. Consumers can read agent output, modify it, and re-emit it without information loss. The per-codec test suites assert round-trip identity against fixtures generated from the SysML model and against captures from the cppagent reference. + +## See also + +- [Compliance](/compliance/) — the wire-format compliance matrix and the known divergences from the cppagent reference, with justifications. +- [Configure & Use](/configure/) — how to enable each wire format on the agent and the adapter. +- [API reference](/api/) — the codec classes (`MTConnectXmlSerializer`, `MTConnectJsonSerializer`, `MTConnectCppAgentJsonSerializer`, `ShdrLine`, …) and their public surface. diff --git a/docs/Json.md b/docs/wire-formats/json-v1.md similarity index 100% rename from docs/Json.md rename to docs/wire-formats/json-v1.md diff --git a/docs/wire-formats/json-v2-cppagent-mqtt.md b/docs/wire-formats/json-v2-cppagent-mqtt.md new file mode 100644 index 000000000..d5a25fa03 --- /dev/null +++ b/docs/wire-formats/json-v2-cppagent-mqtt.md @@ -0,0 +1,138 @@ +# JSON-CPPAGENT-MQTT + +JSON-CPPAGENT-MQTT publishes JSON-CPPAGENT v2 envelopes over an MQTT broker on a documented topic tree. The codec is the same `MTConnect.NET-JSON-cppagent` library that serializes HTTP responses, but with an MQTT-flavored formatter that splits per-device documents into per-topic payloads. Consumers subscribe to a fixed `//` pattern and parse the resulting messages with any JSON parser that handles the HTTP form of JSON-CPPAGENT v2. + +## Document format ID + +The codec registers as `JSON-cppagent-mqtt` in the formatter registry. It inherits from the HTTP JSON-CPPAGENT formatter and overrides only the Devices and Assets methods so the MQTT broker module emits one device or one asset per message rather than a multi-device array. + +## Codec classes + +| Class | Role | +|---|---| +| [`MTConnect.Formatters.JsonMqttResponseDocumentFormatter`](/api/mtconnect-formatters/JsonMqttResponseDocumentFormatter) | MQTT-flavored `IResponseDocumentFormatter` derived from the HTTP codec. Overrides `Format(IDevicesResponseDocument)` to emit a single `JsonDeviceContainer` and `Format(IAssetsResponseDocument)` to emit a single asset per message. Returns `application/json`. | +| [`MTConnect.Formatters.JsonMqttEntityFormatter`](/api/mtconnect-formatters/JsonMqttEntityFormatter) | Per-entity formatter for MQTT relays that publish per-observation messages. | +| [`MTConnect.Devices.Json.JsonDeviceContainer`](/api/mtconnect-devices-json/JsonDeviceContainer) | Single-device wrapper the MQTT formatter emits in place of the multi-device `JsonDevicesResponseDocument`. | +| [`MTConnect.Assets.Json.JsonAssetContainer`](/api/mtconnect-assets-json/JsonAssetContainer) | Single-asset wrapper the MQTT formatter emits per asset message. | +| [`MTConnect.MTConnectMqttDocumentServer`](/api/mtconnect/MTConnectMqttDocumentServer) | Holds the topic constants — `Probe`, `Current`, `Sample`, `Asset` — that downstream agent modules use to build the published topic. | + +## Topic tree + +The default topic tree, as composed by the [MqttBroker agent module](/modules/mqtt-broker) using [`MTConnectMqttDocumentServer`](/api/mtconnect/MTConnectMqttDocumentServer) constants: + +| Topic pattern | Payload | Retained? | +|---|---|---| +| `/Probe/` | One `MTConnectDevices` envelope, single-device wrapper. | Yes — late-joiners receive the latest probe on connect. | +| `/Current/` | One `MTConnectStreams` envelope, single-device, snapshot semantics. | Yes — `/current`-equivalent for new subscribers. | +| `/Sample/` | One `MTConnectStreams` envelope, single-device, sample-stream semantics. | No — sample messages stream live. | +| `/Asset//` | One `MTConnectAssets` envelope, single asset. | Yes — current state of the named asset. | + +The prefix defaults to `MTConnect` (see the [MqttBroker module configuration](/modules/mqtt-broker) and [MqttAdapter module configuration](/modules/mqtt-adapter) pages); operators override it per deployment. The agent's MqttBroker module fans documents out across these topics; the MqttAdapter module subscribes to `/#` and ingests messages back into an agent. + +## Sample envelope + +A `Current` message on `MTConnect/Current/5fd88408-7811-3c6b-5400-11f4026b6890` carries the same JSON-CPPAGENT v2 envelope shape the HTTP codec emits, scoped to a single device. The payload below is the per-device slice of the HTTP fixture: + +```json +{ + "MTConnectStreams": { + "jsonVersion": 2, + "schemaVersion": "2.0", + "Header": { + "instanceId": 1702144894, + "version": "6.0.1.0", + "sender": "DESKTOP-HV74M4N", + "bufferSize": 150000, + "firstSequence": 1, + "lastSequence": 246, + "nextSequence": 247, + "deviceModelChangeTime": "2023-12-09T18:01:38.0133172Z", + "creationTime": "2023-12-10T03:06:48.4086283Z" + }, + "Streams": { + "DeviceStream": [ + { + "name": "M12346", + "uuid": "5fd88408-7811-3c6b-5400-11f4026b6890", + "ComponentStream": [ + { + "component": "Device", + "componentId": "d1", + "name": "M12346", + "uuid": "5fd88408-7811-3c6b-5400-11f4026b6890", + "Events": { + "Application": [ + { + "value": "UNAVAILABLE", + "dataItemId": "gui", + "timestamp": "2023-12-09T18:01:37.7811108Z", + "sequence": 11 + } + ] + } + } + ] + } + ] + } + } +} +``` + +The fixture derivation is `libraries/MTConnect.NET-JSON-cppagent/Examples/MTConnectStreamsResponseDocument.json`, scoped to a single `DeviceStream`. An Asset message on `MTConnect/Asset//` carries a single-asset envelope rather than the per-type-array shape the HTTP Assets endpoint returns. + +## Spec-version compatibility + +The MQTT formatter is a thin override of the HTTP JSON-CPPAGENT codec; the on-the-wire JSON shape is identical to the [JSON-CPPAGENT v2](./json-v2-cppagent) page's coverage. Topic shape and retention policy are set by the agent's MqttBroker module configuration; they are deployment metadata, not part of the MTConnect Standard. + +| Spec version | Codec shape | Notes | +|---|---|---| +| v1.0 – v1.8 | Same as JSON-CPPAGENT v2 HTTP. | Topic tree applies uniformly across versions; the per-message envelope carries the negotiated `schemaVersion`. | +| v2.0 – v2.5 | Same as JSON-CPPAGENT v2 HTTP — default + canonical target. | The MQTT codec's NuGet ships alongside the HTTP codec and tracks the same upper bound. | +| v2.6 – v2.7 | Codec shape unchanged; type-system additions tracked under [Compliance](/compliance/). | The MqttBroker module exposes the same fields on every published envelope as the HTTP module would on `/current` and `/sample`. | + +The reference implementation for the JSON shape remains cppagent's [`JsonPrinter`](https://github.com/mtconnect/cppagent/blob/main/src/mtconnect/printer/JsonPrinter.cpp). The MTConnect Standard does not specify an MQTT transport for JSON envelopes; the topic tree this library uses is convention, not normative. + +## Wire-flow sequence + +```mermaid +sequenceDiagram + participant Adapter as SHDR / HTTP adapter + participant Agent as Agent + MqttBroker module + participant Codec as JsonMqttResponseDocumentFormatter + participant Broker as MQTT broker + participant Consumer + + Adapter->>Agent: Push observation (SHDR / HTTP / dotnet adapter API) + Agent->>Agent: Update IMTConnectAgent buffer + Agent->>Agent: Build per-device IStreamsResponseOutputDocument + Agent->>Codec: Format(document, options) + Codec->>Codec: Project to single-device JsonStreamsResponseDocument + Codec-->>Agent: FormatWriteResult(payload, "application/json") + Agent->>Broker: PUBLISH /Current/ + payload (retain=true) + Broker-->>Consumer: Deliver message on subscribed topic + Consumer->>Consumer: Parse JSON-CPPAGENT v2 envelope +``` + +For Sample-topic messages the same pipeline runs but with retain set false; for Asset-topic messages the broker module switches to the [`JsonAssetContainer`](/api/mtconnect-assets-json/JsonAssetContainer) per-asset shape via [`JsonMqttResponseDocumentFormatter.Format(IAssetsResponseDocument)`](/api/mtconnect-formatters/JsonMqttResponseDocumentFormatter) and publishes on `/Asset//`. + +Reads (ingress) run via the [MqttAdapter agent module](/modules/mqtt-adapter): the module subscribes to `/#`, routes each message to [`JsonMqttResponseDocumentFormatter.CreateDevicesResponseDocument`](/api/mtconnect-formatters/JsonMqttResponseDocumentFormatter) (or the Assets equivalent), and projects back to the canonical `IDevicesResponseDocument` / `IAssetsResponseDocument` interfaces. + +## Caveats and known divergences + +- **No normative spec — neither for the JSON shape nor for the MQTT topic tree.** The JSON envelope mirrors cppagent's HTTP output; the topic tree is this library's convention, aligned with cppagent's MQTT module where it overlaps. Consumers should consider the topic shape stable but not standardized. +- **One device per message, one asset per message.** The MQTT formatter overrides the HTTP formatter's Devices and Assets methods to emit a single-device or single-asset payload, in contrast to the HTTP envelope that may carry many devices or many asset types. Subscribers that expect multi-device payloads will mis-parse MQTT messages. +- **Retain semantics differ by topic.** Probe, Current, and Asset messages are retained so a late-joining subscriber receives the current state on connect; Sample messages stream live and are not retained. This matches the snapshot vs change-feed distinction the HTTP endpoints draw between `/current` and `/sample`. +- **Topic prefix is operator-configured.** The default `MTConnect` prefix is the MqttBroker module's default; operators are free to change it, and a consumer that hard-codes `MTConnect/` will silently fail against a renamed deployment. Discover the prefix via the deployment's agent configuration, not from this page. +- **QoS is operator-configured.** The MqttBroker module exposes a per-broker QoS setting (default 1); message ordering across QoS-0 deployments is the broker's responsibility, not the codec's. +- **JSON-level caveats inherit.** Every caveat on the [JSON-CPPAGENT v2](./json-v2-cppagent#caveats-and-known-divergences) page (`UNAVAILABLE` sentinel, string `schemaVersion`, single-element-arrays, etc.) applies identically here. +- **Topic-tree extensibility is non-normative.** Some downstream MQTT bridges add per-DataItem topics (`/Observation/`). The library's MqttBroker module ships only the four topic kinds in the table above; downstream extensions live in adapter / bridge code, not in this codec. + +## See also + +- [`MTConnect.NET-JSON-cppagent` library README](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-JSON-cppagent/README.md) — package install + per-version notes. +- [JSON-CPPAGENT v2](./json-v2-cppagent) — the same envelope shape over HTTP. +- [MqttBroker module](/modules/mqtt-broker) — agent-side configuration that drives the publish topic tree. +- [MqttAdapter module](/modules/mqtt-adapter) — agent-side ingress that consumes the published topic tree. +- [MQTT-Protocol guide](/configure/integrations/mqtt-protocol) — operator-side topic tree and prefix configuration. +- [Compliance](/compliance/) — JSON-CPPAGENT vs cppagent reference parity matrix and divergence ledger. diff --git a/docs/wire-formats/json-v2-cppagent.md b/docs/wire-formats/json-v2-cppagent.md new file mode 100644 index 000000000..029c88acb --- /dev/null +++ b/docs/wire-formats/json-v2-cppagent.md @@ -0,0 +1,143 @@ +# JSON-CPPAGENT (v2) + +The JSON-CPPAGENT codec produces output that matches the cppagent reference implementation's JSON v2 format byte-for-byte. The MTConnect Standard does not currently specify a JSON wire format via SysML XMI / XSD / prose; cppagent's [`src/printer/JsonPrinter.cpp`](https://github.com/mtconnect/cppagent/blob/main/src/mtconnect/printer/JsonPrinter.cpp) is the de-facto specification. This library's codec targets that reference so a consumer written against cppagent's JSON output works against an `MTConnect.NET` agent without per-implementation conditionals, and vice versa. + +The format uses three structural idioms: + +- **Object-keyed top-level wrappers** — `MTConnectStreams`, `MTConnectDevices`, `MTConnectAssets`, `MTConnectError` — one per envelope kind. +- **Array-of-wrappers for ordered collections** — Streams' `DeviceStream`, `ComponentStream`, the per-category observation arrays (`Events`, `Samples`, `Condition`), and Assets' per-type containers (`CuttingTool`, `File`, …) all serialize as JSON arrays so order is preserved. +- **Object-keyed properties for attribute-style data** — `Header`, individual observation properties, asset measurement properties. + +## Document format ID + +The codec registers as `JSON-cppagent` in the formatter registry. + +## Codec classes + +| Class | Role | +|---|---| +| [`MTConnect.Formatters.JsonHttpResponseDocumentFormatter`](/api/mtconnect-formatters/JsonHttpResponseDocumentFormatter) | Top-level `IResponseDocumentFormatter` for the four envelope kinds. Returns `application/json`. | +| [`MTConnect.Formatters.JsonHttpEntityFormatter`](/api/mtconnect-formatters/JsonHttpEntityFormatter) | Per-entity formatter (single Observation, single Asset) for callers that splice individual entities into a larger document. | +| [`MTConnect.Streams.Json.JsonStreamsResponseDocument`](/api/mtconnect-streams-json/JsonStreamsResponseDocument) | DTO that mirrors the `MTConnectStreams` envelope. | +| [`MTConnect.Devices.Json.JsonDevicesResponseDocument`](/api/mtconnect-devices-json/JsonDevicesResponseDocument) | DTO that mirrors the `MTConnectDevices` envelope. | +| [`MTConnect.Assets.Json.JsonAssetsResponseDocument`](/api/mtconnect-assets-json/JsonAssetsResponseDocument) | DTO that mirrors the `MTConnectAssets` envelope. | +| [`MTConnect.Streams.Json.JsonDeviceStream`](/api/mtconnect-streams-json/JsonDeviceStream) / [`JsonComponentStream`](/api/mtconnect-streams-json/JsonComponentStream) | Per-device + per-component stream containers. | +| [`MTConnect.Streams.Json.JsonObservation`](/api/mtconnect-streams-json/JsonObservation) | Base shape for every observation under `Events`, `Samples`, and `Condition`. | +| [`MTConnect.JsonFunctions`](/api/mtconnect/JsonFunctions) | Serializer options bundle (default vs indented) shared across the codec. | + +## Sample envelope + +The codec's output for a `/current` request demonstrates every idiom — the top-level `MTConnectStreams` wrapper, the `jsonVersion`: 2 marker, the `Header` object, and the array-of-wrappers shape for `DeviceStream`, `ComponentStream`, and the per-DataItem observation arrays (`AdapterUri`, `ConnectionStatus`, etc.). + +```json +{ + "MTConnectStreams": { + "jsonVersion": 2, + "schemaVersion": "2.0", + "Header": { + "instanceId": 1702144894, + "version": "6.0.1.0", + "sender": "DESKTOP-HV74M4N", + "bufferSize": 150000, + "firstSequence": 1, + "lastSequence": 246, + "nextSequence": 247, + "deviceModelChangeTime": "2023-12-09T18:01:38.0133172Z", + "creationTime": "2023-12-10T03:06:48.4086283Z" + }, + "Streams": { + "DeviceStream": [ + { + "name": "agent", + "uuid": "b85fa5f1-bc29-40e0-9893-c8ef8eac6761", + "ComponentStream": [ + { + "component": "Adapter", + "componentId": "adapter_shdr_56697b5624", + "name": "adapterShdr", + "Events": { + "AdapterUri": [ + { + "value": "shdr://localhost:7878", + "dataItemId": "adapter_shdr_56697b5624_adapterUri", + "name": "adapterUri", + "timestamp": "2023-12-09T18:01:39.8259158Z", + "sequence": 243 + } + ], + "ConnectionStatus": [ + { + "value": "LISTEN", + "dataItemId": "adapter_shdr_56697b5624_connectionStatus", + "name": "connectionStatus", + "timestamp": "2023-12-09T18:01:52.1224823Z", + "sequence": 246 + } + ] + } + } + ] + } + ] + } + } +} +``` + +The fixture is `libraries/MTConnect.NET-JSON-cppagent/Examples/MTConnectStreamsResponseDocument.json`. Assets and Devices envelopes follow the same envelope-wrapper + array-of-types pattern; the assets sample under the same `Examples/` directory shows the per-type containers (`CuttingTool`, `File`, …) holding asset arrays. + +## Spec-version compatibility + +cppagent's JSON v2 codec covers the same MTConnect data model as the XML codec, so the version coverage matches the XML page's table where the codec is implemented. The library currently targets MTConnect versions up to v2.5 (see [`MTConnectVersions.Max`](/api/mtconnect/MTConnectVersions)); the NuGet package's description states the same upper bound. + +| Spec version | Status in this library | Notes | +|---|---|---| +| v1.0 – v1.8 | Read + write. | The codec emits the same JSON shape regardless of MTConnect version; the version surfaces on the document via `schemaVersion`. | +| v2.0 – v2.5 | Read + write. | Default + canonical target. | +| v2.6 – v2.7 | Codec shape unchanged; new type-system additions (e.g. Pallet rich measurements) are tracked under [Compliance](/compliance/). | cppagent has continued to evolve its emitted JSON across these releases; the divergence ledger in [Compliance](/compliance/) lists every observed difference. | + +The `jsonVersion` field on the envelope is fixed at `2` for this codec. A future JSON v3 codec, should one land, would carry `jsonVersion: 3`; consumers gate on that value to pick a parser. + +The reference implementation is at [`mtconnect/cppagent`](https://github.com/mtconnect/cppagent); the normative MTConnect Standard for the type-system data the JSON carries is the SysML XMI at [`mtconnect/mtconnect_sysml_model`](https://github.com/mtconnect/mtconnect_sysml_model) and the XSDs at [schemas.mtconnect.org](https://schemas.mtconnect.org/) (the XSDs pin XML wire shape; the JSON codec mirrors the same field set without inheriting the XML attribute-vs-element distinction). + +## Wire-flow sequence + +```mermaid +sequenceDiagram + participant Consumer + participant Agent as Agent HTTP module + participant Codec as JsonHttpResponseDocumentFormatter + participant Serializer as System.Text.Json + + Consumer->>Agent: GET /current (Accept: application/json) + Agent->>Agent: Resolve device + path → IStreamsResponseOutputDocument + Agent->>Codec: Format(document, options) + Codec->>Codec: Project to JsonStreamsResponseDocument DTO + Codec->>Codec: Apply indent option from query string + Codec->>Serializer: JsonSerializer.Serialize(stream, dto, options) + Serializer-->>Codec: stream + Codec-->>Agent: FormatWriteResult(stream, "application/json") + Agent-->>Consumer: 200 OK + application/json body +``` + +Reads run the same pipeline in reverse via [`JsonHttpResponseDocumentFormatter.CreateStreamsResponseDocument`](/api/mtconnect-formatters/JsonHttpResponseDocumentFormatter) (and the matching Devices / Assets methods): `System.Text.Json` deserializes into the `Json*ResponseDocument` DTOs, which then project back to the canonical `IStreamsResponseDocument` / `IDevicesResponseDocument` / `IAssetsResponseDocument` interfaces the rest of the library consumes. + +## Caveats and known divergences + +- **No normative spec.** The MTConnect Standard does not specify a JSON wire format. The de-facto reference is cppagent's `JsonPrinter`; the [Compliance](/compliance/) section tracks any divergence between this library's output and that reference. +- **Field ordering inside objects is not load-bearing.** JSON object keys are unordered by specification. The codec emits them in DTO-declaration order for diff-readability against the cppagent reference, but a consumer that gates on key order is non-conformant to RFC 8259. +- **Array order is load-bearing.** Arrays in this codec (`DeviceStream`, `ComponentStream`, the per-DataItem observation arrays under `Events` / `Samples` / `Condition`, the per-type asset arrays) preserve insertion order. Consumers that re-order arrays on parse will mis-render time-series data and condition transitions. +- **Single-element collections still serialize as arrays.** Even when only one `DeviceStream` is present, the field is `"DeviceStream": [ { … } ]`. This matches cppagent and lets a consumer parse with a single shape regardless of cardinality; consumers must not special-case the 1-element case. +- **`UNAVAILABLE` is the canonical sentinel for missing observations.** The codec emits `"value": "UNAVAILABLE"` (a string) rather than `null` or an absent field, matching cppagent. +- **`schemaVersion` is a string, not a number.** The field carries `"2.0"`, `"2.5"`, etc. — never `2.0` as a JSON number. Older toolchains that strip the quotes will round-trip to a different shape. +- **Round-trip is asymmetric for some Asset subtypes.** The codec serializes every shipped asset type, but read-path coverage lags for assets that the agent doesn't ingest as a primary type (e.g. legacy QIF-wrapped payloads). The [Compliance](/compliance/) section enumerates which asset types round-trip cleanly. +- **Indentation is request-time selectable.** Passing `indentOutput=true` in the formatter options (or `pretty=true` on an HTTP query string, depending on the agent module) switches to the indented `System.Text.Json` profile. The default is compact output, matching cppagent's default. + +## See also + +- [`MTConnect.NET-JSON-cppagent` library README](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-JSON-cppagent/README.md) — package install + per-version notes. +- [JSON-CPPAGENT-MQTT](./json-v2-cppagent-mqtt) — the same envelope shape published over MQTT topics. +- [JSON v1](./json-v1) — the legacy JSON codec. +- [XML](./xml) — the canonical, XSD-pinned wire format. +- [cppagent `JsonPrinter` source](https://github.com/mtconnect/cppagent/blob/main/src/mtconnect/printer/JsonPrinter.cpp) — the reference implementation this codec mirrors. +- [Compliance](/compliance/) — JSON-CPPAGENT vs cppagent reference parity matrix and divergence ledger. diff --git a/docs/wire-formats/shdr.md b/docs/wire-formats/shdr.md new file mode 100644 index 000000000..afb0057e0 --- /dev/null +++ b/docs/wire-formats/shdr.md @@ -0,0 +1,170 @@ +# SHDR + +SHDR — Simple Hierarchical Data Representation — is the line-oriented adapter protocol that feeds the MTConnect agent from upstream equipment (PLCs, machine controllers, sensors). It is the only wire format on this page that flows *into* the agent rather than out of it; the agent surfaces the resulting observations through the HTTP wire formats (XML, JSON-CPPAGENT v2). The protocol is line-delimited ASCII over a TCP socket: one observation (or one observation batch) per newline-terminated line. + +The MTConnect Standard documents SHDR as the canonical adapter protocol in [Part 7.0 — Protocol Information Model](https://docs.mtconnect.org/). The library's [`MTConnect.NET-SHDR`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-SHDR/README.md) package implements both sides — adapter (TCP server that publishes lines) and agent ingress client (TCP client that consumes lines). + +## Line shape + +Every SHDR line carries an optional ISO 8601 UTC timestamp followed by pipe-delimited fields: + +``` +||[||…] +``` + +- **Timestamp** — optional. When the adapter omits it, the agent stamps the line with its receive time. +- **Key** — the DataItem ID (or the device-scoped `:` form when the adapter speaks for multiple devices on the same socket). +- **Value** — the observation value, encoded per the representation kind (`VALUE`, `DATA_SET`, `TABLE`, `TIME_SERIES`, `CONDITION`). + +The protocol layers four control idioms on top of that base: + +- **Asset push** — `|@ASSET@|||` (with `--multiline--` framing when the asset is multi-line XML). +- **Asset removal** — `|@REMOVE_ASSET@|` and `|@REMOVE_ALL_ASSETS@|`. +- **Device push** — `|@DEVICE@|` for adapters that ship Devices.xml fragments inline. +- **Commands** — `* : ` (e.g. `* deviceModel: `, `* heartbeat: 10000`) for connection-level negotiation. + +## Codec classes + +| Class | Role | +|---|---| +| [`MTConnect.Shdr.ShdrLine`](/api/mtconnect-shdr/ShdrLine) | Low-level line tokenizer. Splits a raw byte sequence on `\n`, separates the optional timestamp, and yields field tokens. | +| [`MTConnect.Shdr.ShdrDataItem`](/api/mtconnect-shdr/ShdrDataItem) | Round-trip codec for the `VALUE` representation (Events + Samples). `ToString()` emits SHDR; `FromString()` parses. | +| [`MTConnect.Shdr.ShdrCondition`](/api/mtconnect-shdr/ShdrCondition) | Codec for Conditions. Each fault state serializes as `\|\|\|\|`. | +| [`MTConnect.Shdr.ShdrTimeSeries`](/api/mtconnect-shdr/ShdrTimeSeries) | Codec for the `TIME_SERIES` representation. Emits `\|\| … `. | +| [`MTConnect.Shdr.ShdrDataSet`](/api/mtconnect-shdr/ShdrDataSet) | Codec for the `DATA_SET` representation. Emits space-separated `=` entries. | +| [`MTConnect.Shdr.ShdrTable`](/api/mtconnect-shdr/ShdrTable) | Codec for the `TABLE` representation. Emits space-separated `={=…}` entries. | +| [`MTConnect.Shdr.ShdrAsset`](/api/mtconnect-shdr/ShdrAsset) | Codec for `@ASSET@` push lines, including the `--multiline--` envelope for XML assets. | +| [`MTConnect.Shdr.ShdrMessage`](/api/mtconnect-shdr/ShdrMessage) | Codec for `MESSAGE`-representation Events (which carry a native code alongside the value). | +| [`MTConnect.Shdr.ShdrFaultState`](/api/mtconnect-shdr/ShdrFaultState) | Per-fault DTO used by `ShdrCondition`. | +| [`MTConnect.Adapters.Shdr.ShdrAdapter`](/api/mtconnect-adapters-shdr/ShdrAdapter) | Adapter-side TCP server that serializes queued observations and publishes lines on connect / on change. | +| [`MTConnect.Adapters.Shdr.ShdrIntervalAdapter`](/api/mtconnect-adapters-shdr/ShdrIntervalAdapter) | Adapter variant that flushes the most-recent value of each DataItem on a fixed interval. | +| [`MTConnect.Adapters.Shdr.ShdrQueueAdapter`](/api/mtconnect-adapters-shdr/ShdrQueueAdapter) | Adapter variant that publishes every queued observation on `SendBuffer()`. | +| [`MTConnect.Adapters.Shdr.ShdrIntervalQueueAdapter`](/api/mtconnect-adapters-shdr/ShdrIntervalQueueAdapter) | Adapter variant that flushes the full queue on a fixed interval. | +| [`MTConnect.Shdr.ShdrClient`](/api/mtconnect-shdr/ShdrClient) | Agent-side TCP client that reads from an `ShdrAdapter`, parses each line, and pushes observations into an `IMTConnectAgent`. | + +## Sample lines + +A simple Event observation, with the adapter emitting timestamps: + +``` +2023-01-26T16:48:17.0206852Z|L2estop|ARMED +``` + +A device-scoped observation (multi-device adapter on a single socket): + +``` +2023-01-26T20:54:34.1694626Z|OKUMA-Lathe:L2estop|ARMED +``` + +A batch of observations on one line (separator between key/value pairs is `|`): + +``` +2023-01-26T20:50:53.6161001Z|L2p1execution|READY|L2p1Fovr|100|L2p1partcount|15|L2p1Fact|250 +``` + +A Condition with native diagnostics: + +``` +2022-02-01T13:55:11.8460000Z|L2p1system|FAULT|404|100|LOW|Testing from new adapter +``` + +A `TIME_SERIES` sample, six readings at 100 Hz: + +``` +2023-01-26T20:39:28.1540686Z|L2p1Sensor|6|100|12 15 14 18 25 30 +``` + +A `DATA_SET` of named scalars: + +``` +2023-01-26T20:40:30.6718334Z|L2p1Variables|V1=5 V2=205 +``` + +A `TABLE` of tool measurements: + +``` +2023-01-26T20:40:55.8702675Z|L2p1ToolTable|T1={LENGTH=7.123 DIAMETER=0.494 TOOL_LIFE=0.35} T2={LENGTH=10.456 DIAMETER=0.125 TOOL_LIFE=1} +``` + +A multi-line CuttingTool asset push: + +``` +2023-01-26T17:56:59.9694353Z|@ASSET@|5.12|CuttingTool|--multiline--W5XZBJ2QZV + + + 0 + + 7.6543 + + + +--multiline--W5XZBJ2QZV +``` + +An asset removal: + +``` +2023-01-26T18:21:57.8208518Z|@REMOVE_ASSET@|file.test +``` + +Every fixture above is reproduced in [`libraries/MTConnect.NET-SHDR/README.md`](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-SHDR/README.md) with the codec call that produced it. + +## Spec-version compatibility + +SHDR's line shape is stable across the MTConnect Standard's lifetime — the protocol was specified before the MTConnect v2.x type-system additions and has not gained new line forms. The only version-driven evolution is in the value space: new representations (`DATA_SET` in v1.4, `TABLE` in v1.5, `TIME_SERIES` carrying ≥ 1 sample) extended what the existing line shapes can carry without changing the framing. + +| Spec version | SHDR coverage in this library | +|---|---| +| v1.0 – v1.3 | `VALUE` representation (Events + Samples), Conditions, asset push, asset removal. | +| v1.4 | Adds `DATA_SET` representation. | +| v1.5 | Adds `TABLE` representation. | +| v1.6 – v2.5 | No new SHDR line forms; observation values follow the typed-DataItem rules of the target version. | + +For all versions, the canonical authority on SHDR is Part 7.0 of the MTConnect Standard at [docs.mtconnect.org](https://docs.mtconnect.org/). The reference adapter implementations in [`mtconnect/cppagent`](https://github.com/mtconnect/cppagent) under `simulator/` and `lib/` carry working SHDR samples cross-validated against the same protocol. + +## Wire-flow sequence + +```mermaid +sequenceDiagram + participant PLC as PLC / equipment reader + participant Adapter as ShdrAdapter (TCP server) + participant Client as ShdrClient (TCP client, agent side) + participant Agent as IMTConnectAgent + + PLC->>Adapter: Push DataItem value (in-process API) + Note over Adapter: Queue observation; format via ShdrDataItem.ToString() + Client->>Adapter: TCP connect (heartbeat negotiation) + Adapter-->>Client: "* heartbeat: " + Client-->>Adapter: "* PING" + Adapter-->>Client: "* PONG " + loop Per observation + Adapter-->>Client: ||\n + Client->>Client: ShdrLine.FromString → ShdrDataItem / ShdrCondition / … + Client->>Agent: AddObservation(deviceUuid, dataItemId, value, timestamp) + end + PLC->>Adapter: Push asset (CuttingTool / File / …) + Adapter-->>Client: |@ASSET@|||--multiline--\n\n--multiline--\n + Client->>Client: ShdrAsset.FromString → IAsset + Client->>Agent: AddAsset(asset) +``` + +The heartbeat exchange (`* heartbeat`, `* PING`, `* PONG`) is the protocol's connection-keepalive contract; the agent disconnects an adapter that stops PONGing within twice the negotiated heartbeat. The library's [`ShdrClient`](/api/mtconnect-shdr/ShdrClient) handles the keepalive on the agent side; the [`ShdrAdapter`](/api/mtconnect-adapters-shdr/ShdrAdapter) family handles it on the equipment side. + +## Caveats and known divergences + +- **Timestamps are optional but recommended.** When the adapter omits a leading timestamp, the agent stamps the observation at its receive time — which may be milliseconds-to-seconds later than the actual physical event, depending on adapter throughput and TCP buffering. The `ShdrAdapter.OutputTimestamps` knob (default `true`) controls this. +- **Pipe is reserved.** Values that include `|` must be escaped or the line will misparse. The library's `ShdrDataItem.ToString()` does not currently escape; producers passing pipe-bearing strings must encode them out-of-band (URL-encoding is the cppagent convention). +- **Newline is reserved.** SHDR is strictly line-delimited; multi-line values use the `--multiline--` framing exclusively for assets. Embedding a literal `\n` in a non-asset value will desynchronize the parser; producers must encode or strip them. +- **`@ASSET@` payloads are XML even on JSON-CPPAGENT deployments.** The asset push payload is an XML fragment regardless of which HTTP wire format the agent serves. The agent re-serializes into JSON-CPPAGENT v2 (or XML, or both) on the egress side. +- **Single-line vs multi-line assets is adapter-configured.** Setting `MultilineAssets = false` on the adapter inlines short asset XML on the same line; setting it to `true` (the default) uses the `--multiline--` framing. The token is randomly generated per asset and must not appear inside the asset XML; the [`ShdrAsset`](/api/mtconnect-shdr/ShdrAsset) codec regenerates the token until it is unique against the payload. +- **`@REMOVE_ALL_ASSETS@` targets a type, not a device.** The line `\|@REMOVE_ALL_ASSETS@\|File` removes every File asset on the device the adapter speaks for. There is no device-spanning variant; a multi-device adapter sends one removal per device-scoped key. +- **Reconnect drops in-flight buffer.** When the TCP connection drops mid-stream, observations queued in the adapter's send buffer are lost unless the adapter is an [`ShdrQueueAdapter`](/api/mtconnect-adapters-shdr/ShdrQueueAdapter) variant. The agent does not back-fill; consumers who require zero loss should use the queue-adapter family or a transport with persistent delivery (e.g. the [MqttAdapter module](/modules/mqtt-adapter)). +- **No native TLS.** SHDR is plaintext TCP. Deployments that require encryption tunnel through SSH, stunnel, a service mesh, or a TLS-terminating proxy. The library does not negotiate TLS on the SHDR socket directly. +- **Adapter-side device push (`@DEVICE@`) is opt-in.** Most adapters keep Devices.xml on the agent side and let the agent's probe response describe the model. Adapters that ship the device model inline use `@DEVICE@`; consumers should confirm the deployment's source-of-truth before assuming either path. + +## See also + +- [`MTConnect.NET-SHDR` library README](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-SHDR/README.md) — adapter setup, configuration knobs, and per-representation usage examples. +- [XML](./xml), [JSON-CPPAGENT v2](./json-v2-cppagent), [JSON-CPPAGENT-MQTT](./json-v2-cppagent-mqtt) — the egress wire formats the agent surfaces once SHDR observations land in its buffer. +- [Configure an adapter](/configure/) — operator-side guidance on bringing up an adapter against a PLC or equipment reader. +- [cppagent SHDR simulator](https://github.com/mtconnect/cppagent/tree/main/simulator) — reference adapter the library's SHDR codec cross-validates against. diff --git a/docs/wire-formats/xml.md b/docs/wire-formats/xml.md new file mode 100644 index 000000000..32c6596b0 --- /dev/null +++ b/docs/wire-formats/xml.md @@ -0,0 +1,129 @@ +# XML + +XML is the canonical MTConnect wire format. Every MTConnect Standard version (v1.0 through v2.5 in this library; v2.7 in the standard at large) defines an XSD set that pins the on-the-wire envelope shape — `MTConnectStreams_.xsd`, `MTConnectDevices_.xsd`, `MTConnectAssets_.xsd`, and `MTConnectError_.xsd`. The library's XML codec produces output that validates against the matching-version XSD published at [schemas.mtconnect.org](https://schemas.mtconnect.org/). + +The codec round-trips: it both reads agent output (e.g. an HTTP `GET /current` response) and writes envelopes for the agent to serve. Reads dispatch on the document's `xmlns` value to select the matching MTConnect version (see [`MTConnect.Namespaces`](/api/mtconnect/Namespaces) for the URI → version table). + +## Document format ID + +The codec registers as `XML` in the formatter registry. Agent modules and adapters pass that string into `IResponseDocumentFormatter` / `IEntityFormatter` lookups to select XML output. + +## Codec classes + +| Class | Role | +|---|---| +| [`MTConnect.Formatters.XmlResponseDocumentFormatter`](/api/mtconnect-formatters/XmlResponseDocumentFormatter) | Top-level `IResponseDocumentFormatter` for the four envelope kinds (Streams, Devices, Assets, Error). Returns `application/xml`. | +| [`MTConnect.Formatters.XmlEntityFormatter`](/api/mtconnect-formatters/XmlEntityFormatter) | Per-entity formatter (single Observation, single Asset, etc.) for callers that splice individual entities into a larger document. | +| [`MTConnect.Formatters.XmlPathFormatter`](/api/mtconnect-formatters/XmlPathFormatter) | XPath-style path resolver used by the `path=` query parameter on `/current` and `/sample`. | +| [`MTConnect.Streams.Xml.XmlStreamsResponseDocument`](/api/mtconnect-streams-xml/XmlStreamsResponseDocument) | DTO that mirrors the `` envelope. | +| [`MTConnect.Devices.Xml.XmlDevicesResponseDocument`](/api/mtconnect-devices-xml/XmlDevicesResponseDocument) | DTO that mirrors the `` envelope. | +| [`MTConnect.Assets.Xml.XmlAssetsDocument`](/api/mtconnect-assets-xml/XmlAssetsDocument) | DTO that mirrors the `` envelope. | +| [`MTConnect.Errors.Xml.XmlErrorDocument`](/api/mtconnect-errors-xml/XmlErrorDocument) | DTO that mirrors the `` envelope. | +| [`MTConnect.XmlValidator`](/api/mtconnect/XmlValidator) | XSD validator that loads the embedded per-version schema set under [`MTConnect.Schemas`](/api/mtconnect/Schemas) and reports structural errors. | + +## Sample envelope + +A minimal `` response captures the shape every Streams document follows — a `
` with sequence + buffer metadata, a `` container, one `` per device, one `` per addressed component, and a category container (``, ``, or ``) holding the observations. + +```xml + + +
+ + + + + + + + + + + +``` + +The fixture is `tests/MTConnect.NET-XML-Tests/Streams-Files/Current-Simple.xml`. Devices, Assets, and Error envelopes share the same `
` + payload pattern, with the per-envelope payload swapped (``, ``, ``). + +## Spec-version compatibility + +The codec walks the `xmlns` attribute on the root element to pick the version. The XSDs are embedded into `MTConnect.NET-XML.dll` and exposed via [`MTConnect.Schemas`](/api/mtconnect/Schemas); the [`MTConnect.XmlValidator`](/api/mtconnect/XmlValidator) class loads them on demand and runs structural validation against the matching version. + +| Spec version | XML namespace | Status in this library | +|---|---|---| +| v1.0 | `urn:mtconnect.org:MTConnectStreams:1.0` (and the matching Devices / Assets / Error) | Read + write. | +| v1.1 | `urn:mtconnect.org:MTConnectStreams:1.1` | Read + write. | +| v1.2 | `urn:mtconnect.org:MTConnectStreams:1.2` | Read + write. | +| v1.3 | `urn:mtconnect.org:MTConnectStreams:1.3` | Read + write. | +| v1.4 | `urn:mtconnect.org:MTConnectStreams:1.4` | Read + write. | +| v1.5 | `urn:mtconnect.org:MTConnectStreams:1.5` | Read + write. | +| v1.6 | `urn:mtconnect.org:MTConnectStreams:1.6` | Read + write. | +| v1.7 | `urn:mtconnect.org:MTConnectStreams:1.7` | Read + write. | +| v1.8 | `urn:mtconnect.org:MTConnectStreams:1.8` | Read + write. | +| v2.0 | `urn:mtconnect.org:MTConnectStreams:2.0` | Read + write. | +| v2.1 | `urn:mtconnect.org:MTConnectStreams:2.1` | Read + write. | +| v2.2 | `urn:mtconnect.org:MTConnectStreams:2.2` | Read + write. | +| v2.3 | `urn:mtconnect.org:MTConnectStreams:2.3` | Read + write. | +| v2.4 | `urn:mtconnect.org:MTConnectStreams:2.4` | Read + write. | +| v2.5 | `urn:mtconnect.org:MTConnectStreams:2.5` | Read + write. The library's current `MTConnectVersions.Max`. | + +The per-envelope coverage rolls up to the same table — Streams, Devices, Assets, and Error all ship XSDs across the same version span. There is no v1.9 row because the MTConnect Standard skipped that number between v1.8 and v2.0; the XSD set has no `1.9` namespace and the library tracks the canonical gap. See the [`MTConnectVersions`](/api/mtconnect/MTConnectVersions) constants for the full enum. + +For v2.6 and v2.7 namespaces, the codec falls through to the v2.5 reader path; the library's compliance posture for those versions is tracked under [Compliance](/compliance/). Authoritative XSDs for every version are at [schemas.mtconnect.org](https://schemas.mtconnect.org/) and the normative SysML XMI is at [`mtconnect/mtconnect_sysml_model`](https://github.com/mtconnect/mtconnect_sysml_model). Prose narration lives at [docs.mtconnect.org](https://docs.mtconnect.org/) in Part 2.0 (Streams), Part 3.0 (Devices), and Part 4.0 (Assets). + +## Wire-flow sequence + +The `/probe`, `/current`, `/sample`, and `/asset` HTTP endpoints all follow the same envelope-build pipeline. The Mermaid diagram below shows a `/current` request from a consumer through the agent's HTTP module, the codec, and back to the wire. + +```mermaid +sequenceDiagram + participant Consumer + participant Agent as Agent HTTP module + participant Codec as XmlResponseDocumentFormatter + participant Validator as XmlValidator (optional) + + Consumer->>Agent: GET /current?path=//Controller + Agent->>Agent: Resolve device + path → IStreamsResponseOutputDocument + Agent->>Codec: Format(document, options) + Codec->>Codec: Serialize Header + Streams subtree + Codec->>Codec: Apply xmlns for negotiated MTConnect version + alt Validation enabled + Codec->>Validator: ValidateXml(stream, version) + Validator-->>Codec: XmlValidationResponse + end + Codec-->>Agent: FormatWriteResult(stream, "application/xml") + Agent-->>Consumer: 200 OK + application/xml body +``` + +Reads run the same pipeline in reverse: the agent (or an `XmlAdapter` peer) reads the response stream, [`MTConnect.MTConnectVersion`](/api/mtconnect/MTConnectVersion) walks the document's `xmlns` to pick the version, and the matching DTO deserializes the payload. + +## Caveats and known divergences + +- **Schema validation is opt-in.** The codec emits XML unconditionally; it does not validate every write against the XSD. Call [`XmlValidator.ValidateXml`](/api/mtconnect/XmlValidator) explicitly when validation matters (e.g. before persisting an envelope or before relaying to a downstream consumer that gates on validation). +- **The v1.9 namespace does not exist.** The MTConnect Standard numbered v1.8 → v2.0 directly. A document carrying `urn:mtconnect.org:MTConnectStreams:1.9` is malformed by definition; the codec's namespace lookup returns the default empty `Version` for it, and downstream code paths treat the result as an unknown version. +- **XSD 1.1 features are not enforced.** The published XSDs include XSD 1.1 assertions and conditional type assignments that .NET's `XmlReader` does not evaluate. Validation catches structural shape only; spec-prose rules (e.g. cross-element constraints not expressible in pure XSD 1.0) are enforced by the agent's typed object model, not by the validator. The compliance harness under `tests/Compliance/` carries the XSD 1.1 + xlink runner that fills the gap. +- **Schema-pinned attribute order is not load-bearing.** The MTConnect XSDs declare attributes in a documented order, but XML itself is order-insensitive for attributes. The codec emits attributes in the order the DTOs declare them; consumers that gate on a particular ordering are non-conformant to the XML specification, not to MTConnect. +- **The `m:` namespace prefix is conventional, not required.** The library emits `xmlns:m="urn:mtconnect.org:MTConnectStreams:"` alongside the default `xmlns` declaration because the reference fixtures use that prefix. Consumers must accept any prefix (or none) bound to the same URI — the MTConnect Standard pins the namespace URI, not the prefix. + +## See also + +- [`MTConnect.NET-XML` library README](https://github.com/TrakHound/MTConnect.NET/blob/master/libraries/MTConnect.NET-XML/README.md) — package install + per-version notes. +- [JSON v1](./json-v1) — the legacy JSON codec that pre-dates the cppagent JSON shape. +- [JSON-CPPAGENT v2](./json-v2-cppagent) — the modern JSON wire format with cppagent parity. +- [SHDR](./shdr) — the adapter-side line protocol that feeds the agent. +- [Compliance](/compliance/) — the per-envelope, per-version conformance matrix. +- [Configure & Use](/configure/) — how to enable XML output on an agent + how to read it from a consumer. diff --git a/libraries/Directory.Build.props b/libraries/Directory.Build.props new file mode 100644 index 000000000..9d4b14675 --- /dev/null +++ b/libraries/Directory.Build.props @@ -0,0 +1,23 @@ + + + + + + + + true + $(WarningsAsErrors);CS1591 + + + diff --git a/libraries/MTConnect.NET-Common/Adapters/AdapterEventArgs.cs b/libraries/MTConnect.NET-Common/Adapters/AdapterEventArgs.cs index 4a4b4db5d..edaa4b5af 100644 --- a/libraries/MTConnect.NET-Common/Adapters/AdapterEventArgs.cs +++ b/libraries/MTConnect.NET-Common/Adapters/AdapterEventArgs.cs @@ -3,13 +3,32 @@ namespace MTConnect.Adapters { + /// + /// Carries an adapter event payload together with the identifier of the + /// client connection it relates to, so handlers can correlate the event + /// with a specific consumer of the adapter's TCP stream. + /// + /// The type of the event payload. public struct AdapterEventArgs { + /// + /// The identifier of the client connection the event applies to. Empty + /// or null when the event is not scoped to a single client. + /// public string ClientId { get; set; } + /// + /// The event payload. + /// public T Data { get; set; } + /// + /// Initializes the event arguments with the originating client + /// identifier and the payload. + /// + /// The client connection identifier. + /// The event payload. public AdapterEventArgs(string clientId, T data) { ClientId = clientId; diff --git a/libraries/MTConnect.NET-Common/Adapters/IMTConnectAdapter.cs b/libraries/MTConnect.NET-Common/Adapters/IMTConnectAdapter.cs index f64f3effd..866c9d6aa 100644 --- a/libraries/MTConnect.NET-Common/Adapters/IMTConnectAdapter.cs +++ b/libraries/MTConnect.NET-Common/Adapters/IMTConnectAdapter.cs @@ -6,6 +6,10 @@ namespace MTConnect.Adapters { + /// + /// An MTConnect adapter: collects observations, assets, and devices from + /// a data source and streams them to one or more MTConnect Agents. + /// public interface IMTConnectAdapter { /// @@ -60,6 +64,11 @@ public interface IMTConnectAdapter /// bool SendLast(long timestamp = 0); + /// + /// Flushes the entire buffered set of items, assets, and devices to + /// the Agent regardless of change state. Returns true when the + /// buffer was sent. + /// bool SendBuffer(); @@ -69,21 +78,70 @@ public interface IMTConnectAdapter void SetUnavailable(long timestamp = 0); + /// + /// Queues an observation for the given DataItem with the supplied + /// value, timestamped at the current time. + /// + /// The DataItem identifier. + /// The observed value. void AddObservation(string dataItemId, object value); + /// + /// Queues an observation for the given DataItem with the supplied + /// value and explicit timestamp. + /// + /// The DataItem identifier. + /// The observed value. + /// The observation timestamp. void AddObservation(string dataItemId, object value, DateTime timestamp); + /// + /// Queues an observation for the given DataItem with the supplied + /// value and a Unix-epoch timestamp. + /// + /// The DataItem identifier. + /// The observed value. + /// The observation timestamp as Unix nanoseconds. void AddObservation(string dataItemId, object value, long timestamp); + /// + /// Queues a fully formed observation input. + /// + /// The observation to queue. void AddObservation(IObservationInput observation); + /// + /// Queues and immediately sends an observation for the given DataItem, + /// timestamped at the current time. Returns true when sent. + /// + /// The DataItem identifier. + /// The observed value. bool SendObservation(string dataItemId, object value); + /// + /// Queues and immediately sends an observation for the given DataItem + /// with an explicit timestamp. Returns true when sent. + /// + /// The DataItem identifier. + /// The observed value. + /// The observation timestamp. bool SendObservation(string dataItemId, object value, DateTime timestamp); + /// + /// Queues and immediately sends an observation for the given DataItem + /// with a Unix-epoch timestamp. Returns true when sent. + /// + /// The DataItem identifier. + /// The observed value. + /// The observation timestamp as Unix nanoseconds. bool SendObservation(string dataItemId, object value, long timestamp); + /// + /// Queues and immediately sends a fully formed observation input. + /// Returns true when sent. + /// + /// The observation to send. bool SendObservation(IObservationInput observation); diff --git a/libraries/MTConnect.NET-Common/Adapters/IMTConnectAdapterModule.cs b/libraries/MTConnect.NET-Common/Adapters/IMTConnectAdapterModule.cs index d64b5e3ae..0aa6d7910 100644 --- a/libraries/MTConnect.NET-Common/Adapters/IMTConnectAdapterModule.cs +++ b/libraries/MTConnect.NET-Common/Adapters/IMTConnectAdapterModule.cs @@ -8,27 +8,65 @@ namespace MTConnect.Adapters { + /// + /// A pluggable adapter module: a data-source-specific component that feeds + /// observations, assets, and devices into an . + /// public interface IMTConnectAdapterModule { + /// + /// The unique identifier of the module. + /// string Id { get; } + /// + /// A human-readable description of the module. + /// string Description { get; } + /// + /// The adapter the module feeds. Set by the host before + /// . + /// IMTConnectAdapter Adapter { get; set; } + /// + /// Raised when the module emits a log entry. + /// event MTConnectLogEventHandler LogReceived; + /// + /// Starts the module so it begins producing data for the adapter. + /// void Start(); + /// + /// Stops the module and releases any data-source resources. + /// void Stop(); + /// + /// Pushes a batch of observations to the adapter. Returns true + /// when accepted. + /// + /// The observations to add. bool AddObservations(IEnumerable observations); + /// + /// Pushes a batch of assets to the adapter. Returns true when + /// accepted. + /// + /// The assets to add. bool AddAssets(IEnumerable assets); + /// + /// Pushes a batch of devices to the adapter. Returns true when + /// accepted. + /// + /// The devices to add. bool AddDevices(IEnumerable devices); } } diff --git a/libraries/MTConnect.NET-Common/Adapters/MTConnectAdapter.cs b/libraries/MTConnect.NET-Common/Adapters/MTConnectAdapter.cs index 986c850e2..e4a3ee514 100644 --- a/libraries/MTConnect.NET-Common/Adapters/MTConnectAdapter.cs +++ b/libraries/MTConnect.NET-Common/Adapters/MTConnectAdapter.cs @@ -36,6 +36,10 @@ public class MTConnectAdapter : IMTConnectAdapter private CancellationTokenSource _stop; + + /// + /// The cancellation source signalled by ; subclasses observe its token to terminate background work. + /// protected CancellationTokenSource StopToken => _stop; @@ -59,13 +63,25 @@ public class MTConnectAdapter : IMTConnectAdapter /// public bool OutputTimestamps { get; set; } + /// + /// When true, incoming observation timestamps are replaced with the send time rather than preserved. + /// public bool IgnoreTimestamps { get; set; } + /// + /// The transport callback invoked to deliver a batch of observations to the Agent; returns true on success. The concrete transport adapter supplies this. + /// public Func, bool> WriteObservationsFunction { get; set; } + /// + /// The transport callback invoked to deliver a batch of assets to the Agent; returns true on success. + /// public Func, bool> WriteAssetsFunction { get; set; } + /// + /// The transport callback invoked to deliver a batch of devices to the Agent; returns true on success. + /// public Func, bool> WriteDevicesFunction { get; set; } @@ -80,6 +96,11 @@ public class MTConnectAdapter : IMTConnectAdapter public event EventHandler> SendError; + /// + /// Initializes the adapter. When is non-null, a background worker flushes queued changes on that millisecond cadence; otherwise sends are caller-driven. Duplicate filtering and timestamp output default to enabled. + /// + /// The send interval in milliseconds, or null for no background worker. + /// When true, the interval worker drains the observation buffer instead of only changed values. public MTConnectAdapter(int? interval = null, bool bufferEnabled = false) { _interval = interval; @@ -119,8 +140,14 @@ public void Stop() } + /// + /// Hook invoked at the end of ; the base implementation does nothing. Transport adapters override it to begin listening for connections. + /// protected virtual void OnStart() { } + /// + /// Hook invoked at the end of ; the base implementation does nothing. Transport adapters override it to tear down connections. + /// protected virtual void OnStop() { } @@ -152,6 +179,9 @@ private async Task Worker(CancellationToken cancellationToken) catch (Exception) { } } + /// + /// Invoked each time the send interval elapses; flushes the observation buffer when buffering is enabled, otherwise sends only changed values. Overridable to customize the flush behavior. + /// protected virtual void OnIntervalElapsed() { if (_bufferEnabled) @@ -176,6 +206,10 @@ public void SetUnavailable(long timestamp = 0) #region "Write" + /// + /// Sends a single observation through the transport by wrapping it in a one-element batch; returns false when the observation is null. + /// + /// The observation to send. protected bool Write(IObservationInput observation) { if (observation != null) @@ -186,6 +220,10 @@ protected bool Write(IObservationInput observation) return false; } + /// + /// Sends a batch of observations via ; returns true (a no-op success) when no transport callback is configured. + /// + /// The observations to send. protected bool Write(IEnumerable observations) { if (WriteObservationsFunction != null) @@ -227,6 +265,9 @@ public bool SendLast(long timestamp = 0) } + /// + /// Drains the buffered observations and then sends any changed assets and devices to the Agent; stops at the first failing stage. + /// public bool SendBuffer() { bool success; @@ -238,32 +279,63 @@ public bool SendBuffer() } + /// + /// Hook invoked after a changed-data send; the base implementation does nothing. + /// protected virtual void OnChangedSent() { } + /// + /// Hook invoked after a last-known-values resend; the base implementation does nothing. + /// protected virtual void OnLastSent() { } #endregion #region "Observations" + /// + /// Hook invoked whenever an observation is accepted into the current set; the base implementation does nothing. + /// + /// The observation that was added. protected virtual void OnObservationAdd(IObservationInput observation) { } + /// + /// Queues an observation for the given DataItem with the current time as its timestamp. + /// + /// The DataItem key the value belongs to. + /// The observed value. public void AddObservation(string dataItemKey, object value) { AddObservation(dataItemKey, value, UnixDateTime.Now); } + /// + /// Queues an observation for the given DataItem at the specified time. + /// + /// The DataItem key the value belongs to. + /// The observed value. + /// The observation time. public void AddObservation(string dataItemKey, object value, DateTime timestamp) { AddObservation(dataItemKey, value, timestamp.ToUnixTime()); } + /// + /// Queues an observation for the given DataItem at the specified Unix-tick timestamp. + /// + /// The DataItem key the value belongs to. + /// The observed value. + /// The observation time in Unix ticks. public void AddObservation(string dataItemKey, object value, long timestamp) { AddObservation(new ObservationInput(dataItemKey, value, timestamp)); } + /// + /// Queues an observation, stamping it with the adapter's device key and the current time when unset, and (when duplicate filtering is on) discarding it if it is unchanged from the current value for that DataItem. + /// + /// The observation to queue. public void AddObservation(IObservationInput observation) { if (observation != null) @@ -310,6 +382,10 @@ public void AddObservation(IObservationInput observation) } } + /// + /// Queues each observation in the sequence via . + /// + /// The observations to queue. public void AddObservations(IEnumerable observations) { if (!observations.IsNullOrEmpty()) @@ -322,21 +398,42 @@ public void AddObservations(IEnumerable observations) } + /// + /// Immediately sends an observation for the given DataItem with the current time, bypassing the queue. + /// + /// The DataItem key the value belongs to. + /// The observed value. public bool SendObservation(string dataItemId, object value) { return SendObservation(dataItemId, value, UnixDateTime.Now); } + /// + /// Immediately sends an observation for the given DataItem at the specified time, bypassing the queue. + /// + /// The DataItem key the value belongs to. + /// The observed value. + /// The observation time. public bool SendObservation(string dataItemId, object value, DateTime timestamp) { return SendObservation(dataItemId, value, timestamp.ToUnixTime()); } + /// + /// Immediately sends an observation for the given DataItem at the specified Unix-tick timestamp, bypassing the queue. + /// + /// The DataItem key the value belongs to. + /// The observed value. + /// The observation time in Unix ticks. public bool SendObservation(string dataItemId, object value, long timestamp) { return SendObservation(new ObservationInput(dataItemId, value, timestamp)); } + /// + /// Immediately sends an observation, stamping it with the adapter's device key and the current time when unset, removing it from the pending current set, and recording it as the last sent value on success. + /// + /// The observation to send. public bool SendObservation(IObservationInput observation) { if (observation != null) @@ -370,6 +467,10 @@ public bool SendObservation(IObservationInput observation) return false; } + /// + /// Immediately sends each observation in the sequence; returns false if any individual send fails (all are still attempted), true when the sequence is empty. + /// + /// The observations to send. public bool SendObservations(IEnumerable dataItems) { var success = true; @@ -390,6 +491,10 @@ public bool SendObservations(IEnumerable dataItems) } + /// + /// Records, per DataItem, the most recent of the supplied observations as the last sent value so it can be resent on reconnection. + /// + /// The observations that were just sent. protected void UpdateLastObservations(IEnumerable observations) { if (!observations.IsNullOrEmpty()) @@ -415,6 +520,9 @@ protected void UpdateLastObservations(IEnumerable observation } + /// + /// Sends every current observation not yet marked as sent, applying the timestamp-output and ignore-timestamp policies, and records them as last sent on success. + /// protected bool WriteChangedObservations() { var now = UnixDateTime.Now; @@ -461,6 +569,10 @@ protected bool WriteChangedObservations() } } + /// + /// Resends the last sent value of every DataItem, used to repopulate the Agent after a reconnection; honors the timestamp-output policy. + /// + /// Unused reserved parameter for an override timestamp. protected bool WriteLastObservations(long timestamp = 0) { // Get a list of all Last Obserations @@ -492,6 +604,10 @@ protected bool WriteLastObservations(long timestamp = 0) } } + /// + /// Dequeues up to buffered observations and sends them, honoring the timestamp-output policy and recording them as last sent on success. + /// + /// The maximum number of buffered observations to send in this pass. public bool WriteBufferObservations(int count = 1000) { var observations = _observationsBuffer.Take(count); @@ -664,6 +780,10 @@ private void AddAssets(IEnumerable assets) } + /// + /// Records, per AssetId, the most recent of the supplied assets as the last sent value so it can be resent on reconnection. + /// + /// The assets that were just sent. protected void UpdateLastAsset(IEnumerable assets) { if (!assets.IsNullOrEmpty()) @@ -685,6 +805,9 @@ protected void UpdateLastAsset(IEnumerable assets) } + /// + /// Sends every current asset not yet marked as sent and records them as last sent on success. + /// protected bool WriteChangedAssets() { // Get a list of all Current Assets @@ -725,6 +848,9 @@ protected bool WriteChangedAssets() } } + /// + /// Resends every last sent asset, used to repopulate the Agent after a reconnection. + /// protected bool WriteAllAssets() { // Get a list of all Assets @@ -879,6 +1005,10 @@ private void AddDevices(IEnumerable devices) } + /// + /// Records, per DeviceKey, the most recent of the supplied devices as the last sent value so it can be resent on reconnection. + /// + /// The devices that were just sent. protected void UpdateLastDevice(IEnumerable devices) { if (!devices.IsNullOrEmpty()) @@ -900,6 +1030,9 @@ protected void UpdateLastDevice(IEnumerable devices) } + /// + /// Sends every current device not yet marked as sent and records them as last sent on success. + /// protected bool WriteChangedDevices() { // Get a list of all Current Devices @@ -940,6 +1073,9 @@ protected bool WriteChangedDevices() } } + /// + /// Resends every last sent device, used to repopulate the Agent after a reconnection. + /// protected bool WriteAllDevices() { // Get a list of all Devices diff --git a/libraries/MTConnect.NET-Common/Adapters/MTConnectAdapterModule.cs b/libraries/MTConnect.NET-Common/Adapters/MTConnectAdapterModule.cs index 3a080784f..7773ac7a1 100644 --- a/libraries/MTConnect.NET-Common/Adapters/MTConnectAdapterModule.cs +++ b/libraries/MTConnect.NET-Common/Adapters/MTConnectAdapterModule.cs @@ -7,56 +7,104 @@ namespace MTConnect.Adapters { + /// + /// Base class for a pluggable adapter module that feeds observations, assets, and devices into an from a source-specific protocol; subclasses implement the connection lifecycle and ingestion. + /// public abstract class MTConnectAdapterModule : IMTConnectAdapterModule { + /// + /// The unique identifier of this module instance. + /// public string Id { get; set; } + /// + /// A human-readable description of what this module does. + /// public string Description { get; set; } + /// + /// The adapter this module feeds data into. + /// public IMTConnectAdapter Adapter { get; set; } + /// + /// Raised when the module emits a log entry. + /// public event MTConnectLogEventHandler LogReceived; + /// + /// Initializes the module with its unique identifier. + /// + /// The module identifier. public MTConnectAdapterModule(string id) { Id = id; } + /// + /// Starts the module by invoking the overridable . + /// public void Start() { OnStart(); } + /// + /// Stops the module by invoking the overridable . + /// public void Stop() { OnStop(); } + /// + /// Lifecycle hook invoked by ; the base implementation does nothing. + /// protected virtual void OnStart() { } + /// + /// Lifecycle hook invoked by ; the base implementation does nothing. + /// protected virtual void OnStop() { } + /// + /// Handles observations passing through the module; the base implementation accepts them unconditionally. Overrides may transform or filter. + /// + /// The observations to process. public virtual bool AddObservations(IEnumerable observations) { return true; } + /// + /// Handles assets passing through the module; the base implementation accepts them unconditionally. + /// + /// The assets to process. public virtual bool AddAssets(IEnumerable assets) { return true; } + /// + /// Handles devices passing through the module; the base implementation accepts them unconditionally. + /// + /// The devices to process. public virtual bool AddDevices(IEnumerable devices) { return true; } + /// + /// Raises with the given severity and message. + /// + /// The severity of the entry. + /// The log message. protected void Log(MTConnectLogLevel logLevel, string message) { if (LogReceived != null) LogReceived.Invoke(this, logLevel, message); diff --git a/libraries/MTConnect.NET-Common/Adapters/MTConnectAdapterModules.cs b/libraries/MTConnect.NET-Common/Adapters/MTConnectAdapterModules.cs index 8fe133255..80f171891 100644 --- a/libraries/MTConnect.NET-Common/Adapters/MTConnectAdapterModules.cs +++ b/libraries/MTConnect.NET-Common/Adapters/MTConnectAdapterModules.cs @@ -7,6 +7,9 @@ namespace MTConnect.Adapters { + /// + /// Discovers implementations across loaded assemblies, instantiates one per matching configuration entry, and drives their start/stop lifecycle as a group. + /// public class MTConnectAdapterModules { private static readonly List _moduleTypes = new List(); @@ -16,16 +19,29 @@ public class MTConnectAdapterModules private readonly IAdapterApplicationConfiguration _configuration; + /// + /// The currently loaded module instances. + /// public IEnumerable Modules = _modules.Values; + /// + /// Raised once for each module as it is instantiated during . + /// public event EventHandler ModuleLoaded; + /// + /// Initializes the loader with the application configuration that supplies per-module settings. + /// + /// The adapter application configuration. public MTConnectAdapterModules(IAdapterApplicationConfiguration configuration) { _configuration = configuration; } + /// + /// Scans loaded assemblies for module types and creates one instance per matching configuration entry, raising for each; instantiation failures are swallowed so one bad module does not block the rest. + /// public void Load() { InitializeModules(); @@ -63,6 +79,9 @@ public void Load() } } + /// + /// Starts every loaded module. + /// public void Start() { Dictionary modules; @@ -76,6 +95,9 @@ public void Start() } } + /// + /// Stops every loaded module and clears the loaded set. + /// public void Stop() { Dictionary modules; diff --git a/libraries/MTConnect.NET-Common/Agents/IMTConnectAgent.cs b/libraries/MTConnect.NET-Common/Agents/IMTConnectAgent.cs index d4dbc3e37..400fedf08 100644 --- a/libraries/MTConnect.NET-Common/Agents/IMTConnectAgent.cs +++ b/libraries/MTConnect.NET-Common/Agents/IMTConnectAgent.cs @@ -14,11 +14,11 @@ namespace MTConnect.Agents { - /// - /// An Agent is the centerpiece of an MTConnect implementation. - /// It organizes and manages individual pieces of information published by one or more pieces of equipment. - /// - public interface IMTConnectAgent + /// + /// An Agent is the centerpiece of an MTConnect implementation. + /// It organizes and manages individual pieces of information published by one or more pieces of equipment. + /// + public interface IMTConnectAgent { /// /// Gets the Device that represents the Agent in the Information Model @@ -138,31 +138,97 @@ public interface IMTConnectAgent #region "Entities" + /// + /// Get the Device with the specified key. + /// + /// The Name or Uuid of the requested Device. + /// The matching Device, or null if no Device with the key exists. IDevice GetDevice(string deviceKey); + /// + /// Get the Device with the specified key, projected to the given MTConnect Version. + /// + /// The Name or Uuid of the requested Device. + /// The MTConnect Version the returned Device is projected to. + /// The matching Device, or null if no Device with the key exists. IDevice GetDevice(string deviceKey, Version mtconnectVersion); + /// + /// Get all Devices held by the Agent. + /// + /// The collection of Devices. IEnumerable GetDevices(); + /// + /// Get all Devices held by the Agent, projected to the given MTConnect Version. + /// + /// The MTConnect Version the returned Devices are projected to. + /// The collection of Devices. IEnumerable GetDevices(Version mtconnectVersion); + /// + /// Get all Devices of the specified Device type. + /// + /// The Device type to filter by (for example, Device or Agent). + /// The collection of matching Devices. IEnumerable GetDevices(string deviceType); + /// + /// Get all Devices of the specified Device type, projected to the given MTConnect Version. + /// + /// The Device type to filter by (for example, Device or Agent). + /// The MTConnect Version the returned Devices are projected to. + /// The collection of matching Devices. IEnumerable GetDevices(string deviceType, Version mtconnectVersion); + /// + /// Get a specific DataItem belonging to the given Device. + /// + /// The Name or Uuid of the Device that owns the DataItem. + /// The Id or Name of the requested DataItem. + /// The matching DataItem, or null if it cannot be resolved. IDataItem GetDataItem(string deviceKey, string dataItemKey); + /// + /// Get the most recent observation for every DataItem across all Devices. + /// + /// The MTConnect Version the returned observations are projected to. + /// The current observations. IEnumerable GetCurrentObservations(Version mtconnectVersion = null); + /// + /// Get the most recent observation for every DataItem belonging to the specified Device. + /// + /// The Name or Uuid of the Device. + /// The MTConnect Version the returned observations are projected to. + /// The current observations for the Device. IEnumerable GetCurrentObservations(string deviceKey, Version mtconnectVersion = null); + /// + /// Get the most recent observation for a specific DataItem belonging to the specified Device. + /// + /// The Name or Uuid of the Device. + /// The Id or Name of the DataItem. + /// The MTConnect Version the returned observations are projected to. + /// The current observations for the DataItem. IEnumerable GetCurrentObservations(string deviceKey, string dataItemKey, Version mtconnectVersion = null); + /// + /// Get all Assets held by the Agent. + /// + /// The MTConnect Version the returned Assets are projected to. + /// The collection of Assets. IEnumerable GetAssets(Version mtconnectVersion = null); + /// + /// Get all Assets associated with the specified Device. + /// + /// The Name or Uuid of the Device. + /// The MTConnect Version the returned Assets are projected to. + /// The collection of Assets for the Device. IEnumerable GetAssets(string deviceKey, Version mtconnectVersion = null); /// @@ -198,20 +264,20 @@ public interface IMTConnectAgent /// Returns True if the Assets were successfully removed bool RemoveAllAssets(string assetType, DateTime timestamp); - #endregion + #endregion - #region "Add" + #region "Add" - /// - /// Add a new MTConnectDevice to the Agent's Buffer - /// - IDevice AddDevice(IDevice device, bool intializeDataItems = true); + /// + /// Add a new MTConnectDevice to the Agent's Buffer + /// + IDevice AddDevice(IDevice device, bool intializeDataItems = true); - /// - /// Add new MTConnectDevices to the Agent's Buffer - /// - IEnumerable AddDevices(IEnumerable devices, bool intializeDataItems = true); + /// + /// Add new MTConnectDevices to the Agent's Buffer + /// + IEnumerable AddDevices(IEnumerable devices, bool intializeDataItems = true); /// @@ -352,15 +418,15 @@ public interface IMTConnectAgent /// True if the Observation was added successfully bool AddObservation(string deviceKey, IObservationInput observationInput, bool? ignoreTimestamp = null, bool? convertUnits = null, bool? ignoreCase = null, bool forceUpdate = false); - /// - /// Add new Observations to the Agent for the specified Device - /// - bool AddObservations(IEnumerable observationInputs); + /// + /// Add new Observations to the Agent for the specified Device + /// + bool AddObservations(IEnumerable observationInputs); - /// - /// Add new Observations for DataItems to the Agent using the "deviceKey" property to override the DeviceKey set in each ObservationInput - /// - bool AddObservations(string deviceKey, IEnumerable observationInputs); + /// + /// Add new Observations for DataItems to the Agent using the "deviceKey" property to override the DeviceKey set in each ObservationInput + /// + bool AddObservations(string deviceKey, IEnumerable observationInputs); /// @@ -381,8 +447,18 @@ public interface IMTConnectAgent bool AddAssets(string deviceKey, IEnumerable assets); + /// + /// Notify the Agent that an observation has been added so that downstream consumers and events can be triggered. + /// + /// The observation that was added. void OnObservationAdded(IObservation observation); + /// + /// Notify the Agent that an observation was rejected because it failed validation. + /// + /// The Uuid of the Device the observation was intended for. + /// The Id of the DataItem the observation was intended for. + /// The validation result describing why the observation was rejected. void OnInvalidObservationAdded(string deviceUuid, string dataItemId, ValidationResult result); #endregion diff --git a/libraries/MTConnect.NET-Common/Agents/IMTConnectAgentBroker.cs b/libraries/MTConnect.NET-Common/Agents/IMTConnectAgentBroker.cs index bd2bb3dbe..ef30f4275 100644 --- a/libraries/MTConnect.NET-Common/Agents/IMTConnectAgentBroker.cs +++ b/libraries/MTConnect.NET-Common/Agents/IMTConnectAgentBroker.cs @@ -46,8 +46,14 @@ public interface IMTConnectAgentBroker : IMTConnectAgent ulong NextSequence { get; } + /// + /// Lookup of Device UUID to its assigned buffer index, used to resolve a Device to its slot in the streaming buffer. + /// Dictionary DeviceIndexes { get; } + /// + /// Lookup of DataItem key to its assigned buffer index, used to resolve a DataItem to its slot in the streaming buffer. + /// Dictionary DataItemIndexes { get; } diff --git a/libraries/MTConnect.NET-Common/Agents/IMTConnectAgentModule.cs b/libraries/MTConnect.NET-Common/Agents/IMTConnectAgentModule.cs index 116154738..986cba2c8 100644 --- a/libraries/MTConnect.NET-Common/Agents/IMTConnectAgentModule.cs +++ b/libraries/MTConnect.NET-Common/Agents/IMTConnectAgentModule.cs @@ -5,20 +5,43 @@ namespace MTConnect.Agents { + /// + /// A pluggable extension that is hosted by an MTConnect Agent and participates in the Agent startup and shutdown lifecycle. + /// public interface IMTConnectAgentModule { + /// + /// A unique identifier that distinguishes this module from other modules loaded by the Agent. + /// string Id { get; } + /// + /// A human-readable description of the purpose this module serves within the Agent. + /// string Description { get; } + /// + /// Raised when the module emits a log entry, allowing the host Agent to surface module diagnostics. + /// event MTConnectLogEventHandler LogReceived; + /// + /// Invoked during Agent startup before Devices are loaded into the Agent. + /// + /// When true, the module should initialize DataItems with their default observations. void StartBeforeLoad(bool initializeDataItems); + /// + /// Invoked during Agent startup after Devices have been loaded into the Agent. + /// + /// When true, the module should initialize DataItems with their default observations. void StartAfterLoad(bool initializeDataItems); + /// + /// Invoked during Agent shutdown so the module can release resources and stop any background activity. + /// void Stop(); } } diff --git a/libraries/MTConnect.NET-Common/Agents/IMTConnectAgentProcessor.cs b/libraries/MTConnect.NET-Common/Agents/IMTConnectAgentProcessor.cs index d81014c64..8e000911b 100644 --- a/libraries/MTConnect.NET-Common/Agents/IMTConnectAgentProcessor.cs +++ b/libraries/MTConnect.NET-Common/Agents/IMTConnectAgentProcessor.cs @@ -7,21 +7,46 @@ namespace MTConnect.Agents { + /// + /// A pluggable extension that intercepts observations and Assets as they flow into an MTConnect Agent, allowing each item to be transformed, enriched, or filtered before it is stored. + /// public interface IMTConnectAgentProcessor { + /// + /// A unique identifier that distinguishes this processor from other processors loaded by the Agent. + /// string Id { get; } + /// + /// A human-readable description of the transformation this processor applies. + /// string Description { get; } + /// + /// Raised when the processor emits a log entry, allowing the host Agent to surface processor diagnostics. + /// event MTConnectLogEventHandler LogReceived; + /// + /// Invoked once during Agent startup so the processor can perform any initialization required before it begins processing data. + /// void Load(); + /// + /// Process an incoming observation before it is added to the Agent. + /// + /// The observation, together with its resolved Device and DataItem context, to process. + /// The observation input to store, or null to suppress the observation. IObservationInput Process(ProcessObservation observation); + /// + /// Process an incoming Asset before it is added to the Agent. + /// + /// The Asset to process. + /// The Asset to store, or null to suppress the Asset. IAsset Process(IAsset asset); } } diff --git a/libraries/MTConnect.NET-Common/Agents/InputValidationLevel.cs b/libraries/MTConnect.NET-Common/Agents/InputValidationLevel.cs index d45d61cc6..b0786c5e4 100644 --- a/libraries/MTConnect.NET-Common/Agents/InputValidationLevel.cs +++ b/libraries/MTConnect.NET-Common/Agents/InputValidationLevel.cs @@ -3,11 +3,30 @@ namespace MTConnect.Agents { + /// + /// Controls how the Agent reacts when input data fails validation against + /// the device model. + /// public enum InputValidationLevel { + /// + /// Accept invalid input unchanged; perform no validation action. + /// Ignore, + + /// + /// Accept invalid input but emit a validation warning. + /// Warning, + + /// + /// Drop the invalid input and continue processing the remainder. + /// Remove, + + /// + /// Reject the entire input on the first validation failure. + /// Strict } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Agents/MTConnectAgent.cs b/libraries/MTConnect.NET-Common/Agents/MTConnectAgent.cs index c928ceee5..29117174b 100644 --- a/libraries/MTConnect.NET-Common/Agents/MTConnectAgent.cs +++ b/libraries/MTConnect.NET-Common/Agents/MTConnectAgent.cs @@ -28,18 +28,55 @@ public class MTConnectAgent : IMTConnectAgent, IDisposable private readonly IAgentConfiguration _configuration; private readonly MTConnectAgentInformation _information; + /// + /// Reverse lookup of Device buffer index to Device UUID. + /// protected readonly Dictionary _deviceUuids = new Dictionary(); + + /// + /// Reverse lookup of DataItem buffer index to DataItem Id. + /// protected readonly Dictionary _dataItemIds = new Dictionary(); + + /// + /// The highest Device buffer index allocated so far; incremented when a new Device is encountered. + /// protected int _lastDeviceIndex = 0; + + /// + /// The highest DataItem buffer index allocated so far; incremented when a new DataItem is encountered. + /// protected int _lastDataItemIndex = 0; - protected readonly ConcurrentDictionary _deviceKeys = new ConcurrentDictionary(); // Resolves either the Device Name or UUID to the Device UUID - protected readonly ConcurrentDictionary _devices = new ConcurrentDictionary(); // Resolves either the Device Name or UUID to the Device + /// + /// Resolves either a Device Name or UUID to the canonical Device UUID. + /// + protected readonly ConcurrentDictionary _deviceKeys = new ConcurrentDictionary(); + + /// + /// Resolves either a Device Name or UUID to the corresponding Device. + /// + protected readonly ConcurrentDictionary _devices = new ConcurrentDictionary(); + + /// + /// Caches the DataItems belonging to each Device, keyed by Device UUID. + /// protected readonly ConcurrentDictionary> _deviceDataItems = new ConcurrentDictionary>(); + + /// + /// Caches the DataItem Ids belonging to each Device, keyed by Device UUID. + /// protected readonly ConcurrentDictionary> _deviceDataItemIds = new ConcurrentDictionary>(); - protected readonly ConcurrentDictionary _dataItemKeys = new ConcurrentDictionary(); // Caches DeviceUuid:DataItemKey to DeviceUuid:DataItemId - protected readonly ConcurrentDictionary _dataItems = new ConcurrentDictionary(); // Key = DeviceUuid:DataItemId + /// + /// Caches the resolution of a DeviceUuid:DataItemKey pair to its canonical DeviceUuid:DataItemId form. + /// + protected readonly ConcurrentDictionary _dataItemKeys = new ConcurrentDictionary(); + + /// + /// Caches DataItems by their canonical DeviceUuid:DataItemId key. + /// + protected readonly ConcurrentDictionary _dataItems = new ConcurrentDictionary(); private readonly ConcurrentDictionary _currentObservations = new ConcurrentDictionary(); private readonly ConcurrentDictionary> _currentConditions = new ConcurrentDictionary>(); @@ -202,6 +239,13 @@ public string Sender #region "Constructors" + /// + /// Initializes a new Agent with a default configuration. + /// + /// An optional UUID for the Agent; when omitted, one is generated. + /// The InstanceId identifying the lifetime of the Agent buffer; when 0, a new value is created. + /// The timestamp, in Unix ticks, of the most recent Device model change. + /// When true, the built-in Agent Device is added during construction. public MTConnectAgent( string uuid = null, ulong instanceId = 0, @@ -220,6 +264,14 @@ public MTConnectAgent( InitializeAgentDevice(initializeAgentDevice); } + /// + /// Initializes a new Agent with an explicit configuration. + /// + /// The Agent configuration; when null, a default configuration is used. + /// An optional UUID for the Agent; when omitted, one is generated. + /// The InstanceId identifying the lifetime of the Agent buffer; when 0, a new value is created. + /// The timestamp, in Unix ticks, of the most recent Device model change. + /// When true, the built-in Agent Device is added during construction. public MTConnectAgent( IAgentConfiguration configuration, string uuid = null, @@ -264,6 +316,9 @@ public void Stop() StopAgentInformationUpdateTimer(); } + /// + /// Stop the Agent and release shared resources held by the garbage collector helper. + /// public void Dispose() { Stop(); @@ -274,6 +329,10 @@ public void Dispose() #region "Initialization" + /// + /// Create the built-in Agent Device that represents the Agent itself in the Information Model and register its keys. + /// + /// When true, the Agent Device DataItems are initialized with their default observations. protected void InitializeAgentDevice(bool initializeDataItems = true) { if (_configuration.EnableAgentDevice) @@ -317,6 +376,11 @@ internal void UpdateAgentDevice() #region "Entities" + /// + /// Resolve a Device key to its canonical Device UUID, accepting either a Device Name or UUID and falling back to a case-insensitive Name match. + /// + /// The Name or UUID of the Device. + /// The canonical Device UUID, or null if the key cannot be resolved. public string GetDeviceUuid(string deviceKey) { if (!string.IsNullOrEmpty(deviceKey)) @@ -337,6 +401,12 @@ public string GetDeviceUuid(string deviceKey) return null; } + /// + /// Project a set of Devices to the requested MTConnect Version, dropping any Device that is not valid for that Version. + /// + /// The Devices to project. + /// The target MTConnect Version; when null, the Agent's current Version is used. + /// The projected Devices. protected List ProcessDevices(IEnumerable devices, Version mtconnectVersion = null) { var objs = new List(); @@ -354,6 +424,7 @@ protected List ProcessDevices(IEnumerable devices, Version mtc } + /// public IDevice GetDevice(string deviceKey) { var deviceUuid = GetDeviceUuid(deviceKey); @@ -371,6 +442,7 @@ public IDevice GetDevice(string deviceKey) return null; } + /// public IDevice GetDevice(string deviceKey, Version mtconnectVersion) { var deviceUuid = GetDeviceUuid(deviceKey); @@ -388,6 +460,7 @@ public IDevice GetDevice(string deviceKey, Version mtconnectVersion) return null; } + /// public IEnumerable GetDevices() { var allDevices = new List(); @@ -403,6 +476,7 @@ public IEnumerable GetDevices() return null; } + /// public IEnumerable GetDevices(Version mtconnectVersion) { var allDevices = new List(); @@ -418,6 +492,7 @@ public IEnumerable GetDevices(Version mtconnectVersion) return null; } + /// public IEnumerable GetDevices(string deviceType) { var allDevices = new List(); @@ -427,7 +502,7 @@ public IEnumerable GetDevices(string deviceType) switch (deviceType) { case Agent.TypeId: - if (_agent != null) allDevices.Add(_agent); + if (_agent != null) allDevices.Add(_agent); break; case Device.TypeId: @@ -451,6 +526,7 @@ public IEnumerable GetDevices(string deviceType) return null; } + /// public IEnumerable GetDevices(string deviceType, Version mtconnectVersion) { var allDevices = new List(); @@ -467,7 +543,7 @@ public IEnumerable GetDevices(string deviceType, Version mtconnectVersi var devices = _devices.Select(o => o.Value).ToList(); if (!devices.IsNullOrEmpty()) allDevices.AddRange(devices); break; - } + } } else { @@ -485,6 +561,7 @@ public IEnumerable GetDevices(string deviceType, Version mtconnectVersi } + /// public IDataItem GetDataItem(string deviceKey, string dataItemKey) { if (!string.IsNullOrEmpty(deviceKey) && !string.IsNullOrEmpty(dataItemKey)) @@ -560,6 +637,11 @@ private IDataItem GetDataItemFromKey(IDevice device, string key) return null; } + /// + /// Get all DataItems belonging to the specified Device. + /// + /// The Name or UUID of the Device. + /// The Device's DataItems, or null if the Device cannot be resolved. public IEnumerable GetDataItems(string deviceKey) { if (!string.IsNullOrEmpty(deviceKey)) @@ -579,6 +661,7 @@ public IEnumerable GetDataItems(string deviceKey) } + /// public IEnumerable GetCurrentObservations(Version mtconnectVersion = null) { var observations = new List(); @@ -601,6 +684,7 @@ public IEnumerable GetCurrentObservations(Version mtconnectV return observations; } + /// public IEnumerable GetCurrentObservations(string deviceKey, Version mtconnectVersion = null) { var observations = new List(); @@ -644,6 +728,7 @@ public IEnumerable GetCurrentObservations(string deviceKey, return observations; } + /// public IEnumerable GetCurrentObservations(string deviceKey, string dataItemKey, Version mtconnectVersion = null) { var observations = new List(); @@ -707,11 +792,13 @@ private IObservationOutput CreateObservation(IDataItem dataItem, IObservation ob } + /// public virtual IEnumerable GetAssets(Version mtconnectVersion = null) { return null; } + /// public virtual IEnumerable GetAssets(string deviceKey, Version mtconnectVersion = null) { return null; @@ -768,6 +855,11 @@ public virtual bool RemoveAllAssets(string assetType, DateTime timestamp) #region "Internal" + /// + /// Seed every DataItem of the given Device with an initial UNAVAILABLE observation so the Device has a complete current state immediately after it is added. + /// + /// The Device whose DataItems are initialized. + /// The timestamp, in Unix ticks, applied to the initial observations; when 0, the current time is used. public virtual void InitializeDataItems(IDevice device, long timestamp = 0) { if (device != null) @@ -809,6 +901,13 @@ public virtual void InitializeDataItems(IDevice device, long timestamp = 0) } + /// + /// Determine whether a new observation should be stored by applying the DataItem's period and delta filters against the current observation, always accepting Discrete DataItems and first observations. + /// + /// The UUID of the Device that owns the DataItem. + /// The DataItem the observation is reported for. + /// The incoming observation input. + /// true if the observation passes the filters and should be stored; otherwise false. protected bool CheckCurrentObservation(string deviceUuid, IDataItem dataItem, IObservationInput observation) { if (_currentObservations != null && observation != null && !string.IsNullOrEmpty(deviceUuid) && dataItem != null) @@ -842,6 +941,13 @@ protected bool CheckCurrentObservation(string deviceUuid, IDataItem dataItem, IO return false; } + /// + /// Determine whether a new condition observation changes the current condition state for the DataItem and therefore should be stored. + /// + /// The UUID of the Device that owns the DataItem. + /// The condition DataItem the observation is reported for. + /// The incoming condition observation input. + /// true if the condition state changes and the observation should be stored; otherwise false. protected bool CheckCurrentCondition(string deviceUuid, IDataItem dataItem, IObservationInput observation) { if (_currentConditions != null && observation != null && !string.IsNullOrEmpty(deviceUuid) && dataItem != null) @@ -918,6 +1024,13 @@ protected bool CheckCurrentCondition(string deviceUuid, IDataItem dataItem, IObs } + /// + /// Replace the cached current observation for the given Device and DataItem with the supplied observation. + /// + /// The UUID of the Device that owns the DataItem. + /// The DataItem the observation is reported for. + /// The observation to record as the current value. + /// true if the current observation cache was updated. protected bool UpdateCurrentObservation(string deviceUuid, IDataItem dataItem, IObservation observation) { if (_currentObservations != null && observation != null && !string.IsNullOrEmpty(deviceUuid) && dataItem != null) @@ -931,6 +1044,13 @@ protected bool UpdateCurrentObservation(string deviceUuid, IDataItem dataItem, I return false; } + /// + /// Update the cached current condition state for the given Device and DataItem with the supplied condition observation. + /// + /// The UUID of the Device that owns the DataItem. + /// The condition DataItem the observation is reported for. + /// The condition observation to record in the current state. + /// true if the current condition cache was updated. protected bool UpdateCurrentCondition(string deviceUuid, IDataItem dataItem, IObservation observation) { if (_currentConditions != null && observation != null && !string.IsNullOrEmpty(deviceUuid) && dataItem != null) @@ -1240,9 +1360,9 @@ private Device NormalizeDevice(IDevice device) // Generate Device Hash obj.Hash = obj.GenerateHash(); - + return obj; - } + } } return null; @@ -1679,22 +1799,22 @@ private string Remove3dSuffix(string s) /// Used to force the update of the Observation. This overrides any value or duplication filters. /// True if the Observation was added successfully public bool AddObservation(IDataItem dataItem, object value, bool? convertUnits = null, bool? ignoreCase = null, bool forceUpdate = false) - { + { if (dataItem != null && dataItem.Device != null && !string.IsNullOrEmpty(dataItem.Device.Uuid) && !string.IsNullOrEmpty(dataItem.Id)) { - var input = new ObservationInput - { - DeviceKey = dataItem.Device.Uuid, - DataItemKey = dataItem.Id, - Values = new List { new ObservationValue(ValueKeys.Result, value) }, - Timestamp = UnixDateTime.Now - }; + var input = new ObservationInput + { + DeviceKey = dataItem.Device.Uuid, + DataItemKey = dataItem.Id, + Values = new List { new ObservationValue(ValueKeys.Result, value) }, + Timestamp = UnixDateTime.Now + }; - return AddObservation(input, convertUnits: convertUnits, ignoreCase: ignoreCase, forceUpdate: forceUpdate); - } + return AddObservation(input, convertUnits: convertUnits, ignoreCase: ignoreCase, forceUpdate: forceUpdate); + } return false; - } + } /// /// Add a new Observation to the Agent for the specified Device and DataItem @@ -1716,7 +1836,7 @@ public bool AddObservation(string deviceKey, string dataItemKey, object value, b Timestamp = UnixDateTime.Now }; - return AddObservation(input, convertUnits: convertUnits, ignoreCase: ignoreCase, forceUpdate: forceUpdate); + return AddObservation(input, convertUnits: convertUnits, ignoreCase: ignoreCase, forceUpdate: forceUpdate); } /// @@ -1730,22 +1850,22 @@ public bool AddObservation(string deviceKey, string dataItemKey, object value, b /// Used to force the update of the Observation. This overrides any value or duplication filters. /// True if the Observation was added successfully public bool AddObservation(IDataItem dataItem, object value, long timestamp, bool? convertUnits = null, bool? ignoreCase = null, bool forceUpdate = false) - { - if (dataItem != null && dataItem.Device != null && !string.IsNullOrEmpty(dataItem.Device.Uuid) && !string.IsNullOrEmpty(dataItem.Id)) - { - var input = new ObservationInput - { - DeviceKey = dataItem.Device.Uuid, - DataItemKey = dataItem.Id, - Values = new List { new ObservationValue(ValueKeys.Result, value) }, - Timestamp = timestamp - }; + { + if (dataItem != null && dataItem.Device != null && !string.IsNullOrEmpty(dataItem.Device.Uuid) && !string.IsNullOrEmpty(dataItem.Id)) + { + var input = new ObservationInput + { + DeviceKey = dataItem.Device.Uuid, + DataItemKey = dataItem.Id, + Values = new List { new ObservationValue(ValueKeys.Result, value) }, + Timestamp = timestamp + }; - return AddObservation(input, convertUnits: convertUnits, ignoreCase: ignoreCase, forceUpdate: forceUpdate); - } + return AddObservation(input, convertUnits: convertUnits, ignoreCase: ignoreCase, forceUpdate: forceUpdate); + } - return false; - } + return false; + } /// /// Add a new Observation to the Agent for the specified Device and DataItem @@ -1782,22 +1902,22 @@ public bool AddObservation(string deviceKey, string dataItemKey, object value, l /// Used to force the update of the Observation. This overrides any value or duplication filters. /// True if the Observation was added successfully public bool AddObservation(IDataItem dataItem, object value, DateTime timestamp, bool? convertUnits = null, bool? ignoreCase = null, bool forceUpdate = false) - { - if (dataItem != null && dataItem.Device != null && !string.IsNullOrEmpty(dataItem.Device.Uuid) && !string.IsNullOrEmpty(dataItem.Id)) - { - var input = new ObservationInput - { - DeviceKey = dataItem.Device.Uuid, - DataItemKey = dataItem.Id, - Values = new List { new ObservationValue(ValueKeys.Result, value) }, - Timestamp = timestamp.ToUnixTime() - }; + { + if (dataItem != null && dataItem.Device != null && !string.IsNullOrEmpty(dataItem.Device.Uuid) && !string.IsNullOrEmpty(dataItem.Id)) + { + var input = new ObservationInput + { + DeviceKey = dataItem.Device.Uuid, + DataItemKey = dataItem.Id, + Values = new List { new ObservationValue(ValueKeys.Result, value) }, + Timestamp = timestamp.ToUnixTime() + }; - return AddObservation(input, convertUnits: convertUnits, ignoreCase: ignoreCase, forceUpdate: forceUpdate); - } + return AddObservation(input, convertUnits: convertUnits, ignoreCase: ignoreCase, forceUpdate: forceUpdate); + } - return false; - } + return false; + } /// /// Add a new Observation to the Agent for the specified Device and DataItem @@ -2097,32 +2217,40 @@ public bool AddObservations(IEnumerable observationInputs) return false; } - /// - /// Add new Observations for DataItems to the Agent using the "deviceKey" property to override the DeviceKey set in each ObservationInput - /// - public bool AddObservations(string deviceKey, IEnumerable observationInputs) - { - if (!observationInputs.IsNullOrEmpty()) - { - bool success = false; + /// + /// Add new Observations for DataItems to the Agent using the "deviceKey" property to override the DeviceKey set in each ObservationInput + /// + public bool AddObservations(string deviceKey, IEnumerable observationInputs) + { + if (!observationInputs.IsNullOrEmpty()) + { + bool success = false; - foreach (var observationInput in observationInputs) - { - success = AddObservation(deviceKey, observationInput); - if (!success) break; - } + foreach (var observationInput in observationInputs) + { + success = AddObservation(deviceKey, observationInput); + if (!success) break; + } - return success; - } + return success; + } - return false; - } + return false; + } - protected virtual ulong OnAddObservation(string deviceUuid, IDataItem dataItem, IObservationInput observationInput) + /// + /// Extension point invoked when an observation is added so a derived Agent can persist it to a buffer; the base implementation stores nothing and returns 0. + /// + /// The UUID of the Device that owns the DataItem. + /// The DataItem the observation is reported for. + /// The observation input being added. + /// The sequence number assigned by the buffer, or 0 when the observation is not buffered. + protected virtual ulong OnAddObservation(string deviceUuid, IDataItem dataItem, IObservationInput observationInput) { return 0; } + /// public void OnObservationAdded(IObservation observation) { if (ObservationAdded != null) @@ -2131,6 +2259,7 @@ public void OnObservationAdded(IObservation observation) } } + /// public void OnInvalidObservationAdded(string deviceUuid, string dataItemId, ValidationResult result) { if (InvalidObservationAdded != null) @@ -2143,11 +2272,21 @@ public void OnInvalidObservationAdded(string deviceUuid, string dataItemId, Vali #region "Assets" + /// + /// Extension point invoked when an existing Asset is updated so a derived Agent can persist the change; the base implementation does nothing and returns true. + /// + /// The updated Asset. + /// true if the update was handled successfully. protected virtual bool OnAssetUpdate(IAsset asset) { return true; } + /// + /// Extension point invoked when a new Asset is added so a derived Agent can persist it; the base implementation does nothing and returns true. + /// + /// The newly added Asset. + /// true if the Asset was handled successfully. protected virtual bool OnNewAssetAdded(IAsset asset) { return true; diff --git a/libraries/MTConnect.NET-Common/Agents/MTConnectAgentBroker.cs b/libraries/MTConnect.NET-Common/Agents/MTConnectAgentBroker.cs index 693ef54eb..c88e3da44 100644 --- a/libraries/MTConnect.NET-Common/Agents/MTConnectAgentBroker.cs +++ b/libraries/MTConnect.NET-Common/Agents/MTConnectAgentBroker.cs @@ -29,7 +29,14 @@ public class MTConnectAgentBroker : MTConnectAgent, IMTConnectAgentBroker, IDisp private readonly IMTConnectObservationBuffer _observationBuffer; private readonly IMTConnectAssetBuffer _assetBuffer; private readonly List _deviceAssetCounts = new List(); + /// + /// Backing store mapping Device UUID to its assigned buffer index; accessed under the broker lock. + /// protected Dictionary _deviceIndexes = new Dictionary(); + + /// + /// Backing store mapping DataItem key to its assigned buffer index; accessed under the broker lock. + /// protected Dictionary _dataItemIndexes = new Dictionary(); @@ -66,6 +73,7 @@ public class MTConnectAgentBroker : MTConnectAgent, IMTConnectAgentBroker, IDisp public ulong NextSequence => _observationBuffer != null ? _observationBuffer.NextSequence : 0; + /// public Dictionary DeviceIndexes { get @@ -81,6 +89,7 @@ public Dictionary DeviceIndexes } } + /// public Dictionary DataItemIndexes { get @@ -144,6 +153,13 @@ public Dictionary DataItemIndexes #region "Constructors" + /// + /// Initializes a new broker with default in-memory observation and Asset buffers and a default configuration. + /// + /// An optional UUID for the Agent; when omitted, one is generated. + /// The InstanceId identifying the lifetime of the Agent buffer. + /// The timestamp, in Unix ticks, of the most recent Device model change. + /// When true, the built-in Agent Device is added during construction. public MTConnectAgentBroker( string uuid = null, ulong instanceId = 0, @@ -151,7 +167,7 @@ public MTConnectAgentBroker( bool initializeAgentDevice = true ) : base(uuid, instanceId, deviceModelChangeTime, false) { - var config = new AgentConfiguration(); + var config = new AgentConfiguration(); //_deviceBuffer = new MTConnectDeviceBuffer(); _observationBuffer = new MTConnectObservationBuffer(); _assetBuffer = new MTConnectAssetBuffer(); @@ -159,6 +175,14 @@ public MTConnectAgentBroker( InitializeAgentDevice(initializeAgentDevice); } + /// + /// Initializes a new broker that derives its buffer sizing from the supplied configuration. + /// + /// The Agent configuration; when null, a default configuration is used. + /// An optional UUID for the Agent; when omitted, one is generated. + /// The InstanceId identifying the lifetime of the Agent buffer. + /// The timestamp, in Unix ticks, of the most recent Device model change. + /// When true, the built-in Agent Device is added during construction. public MTConnectAgentBroker( IAgentConfiguration configuration, string uuid = null, @@ -175,6 +199,15 @@ public MTConnectAgentBroker( InitializeAgentDevice(initializeAgentDevice); } + /// + /// Initializes a new broker backed by the supplied observation and Asset buffers. + /// + /// The observation buffer to use; when null, a default in-memory buffer is created. + /// The Asset buffer to use; when null, a default in-memory buffer is created. + /// An optional UUID for the Agent; when omitted, one is generated. + /// The InstanceId identifying the lifetime of the Agent buffer. + /// The timestamp, in Unix ticks, of the most recent Device model change. + /// When true, the built-in Agent Device is added during construction. public MTConnectAgentBroker( IMTConnectObservationBuffer observationBuffer, IMTConnectAssetBuffer assetBuffer, @@ -191,6 +224,16 @@ public MTConnectAgentBroker( InitializeAgentDevice(initializeAgentDevice); } + /// + /// Initializes a new broker with an explicit configuration and explicit observation and Asset buffers. + /// + /// The Agent configuration; when null, a default configuration is used. + /// The observation buffer to use; when null, a default buffer is created from the configuration. + /// The Asset buffer to use; when null, a default buffer is created from the configuration. + /// An optional UUID for the Agent; when omitted, one is generated. + /// The InstanceId identifying the lifetime of the Agent buffer. + /// The timestamp, in Unix ticks, of the most recent Device model change. + /// When true, the built-in Agent Device is added during construction. public MTConnectAgentBroker( IAgentConfiguration configuration, IMTConnectObservationBuffer observationBuffer, @@ -212,6 +255,10 @@ public MTConnectAgentBroker( #region "Initialization" + /// + /// Restore the current observation and condition state from a set of persisted buffer observations, typically used when recovering a buffer on startup. + /// + /// The persisted buffer observations to replay into the current-state caches. public void InitializeCurrentObservations(IEnumerable bufferObservations) { if (!bufferObservations.IsNullOrEmpty()) @@ -247,6 +294,10 @@ public void InitializeCurrentObservations(IEnumerable bufferO } + /// + /// Seed the Device buffer-index lookup from previously persisted assignments so Devices retain their buffer slots across restarts. + /// + /// A mapping of Device UUID to its buffer index. public void InitializeDeviceIndex(IDictionary indexes) { if (!indexes.IsNullOrEmpty()) @@ -267,6 +318,10 @@ public void InitializeDeviceIndex(IDictionary indexes) } } + /// + /// Seed the DataItem buffer-index lookup from previously persisted assignments so DataItems retain their buffer slots across restarts. + /// + /// A mapping of DataItem key to its buffer index. public void InitializeDataItemIndex(IDictionary indexes) { if (!indexes.IsNullOrEmpty()) @@ -315,7 +370,7 @@ private IEnumerable GenerateBufferKeys(IDevice device) { // Read Cached DataItemIds for the Device _deviceDataItemIds.TryGetValue(device.Uuid, out var dataItemIds); - + var bufferKeys = new List(); if (!dataItemIds.IsNullOrEmpty()) { @@ -358,6 +413,11 @@ private static int GenerateBufferKey(int deviceIndex, int dataItemIndex) } + /// + /// Resolve a Device buffer index back to its Device UUID. + /// + /// The buffer index assigned to the Device. + /// The Device UUID, or null if the index is not assigned. public string GetDeviceUuid(int deviceIndex) { if (_deviceUuids.TryGetValue(deviceIndex, out var deviceUuid)) @@ -368,6 +428,11 @@ public string GetDeviceUuid(int deviceIndex) return null; } + /// + /// Resolve a Device UUID to its buffer index, assigning and caching a new index if one does not yet exist. + /// + /// The UUID of the Device. + /// The buffer index for the Device, or 0 if the UUID is null. public int GetDeviceIndex(string deviceUuid) { var index = 0; @@ -390,6 +455,11 @@ public int GetDeviceIndex(string deviceUuid) return index; } + /// + /// Resolve a set of Device UUIDs to their buffer indexes, assigning new indexes as needed. + /// + /// The UUIDs of the Devices to resolve. + /// The buffer indexes, in the same order as the supplied UUIDs. public IEnumerable GetDeviceIndexes(IEnumerable deviceUuids) { var indexes = new List(); @@ -406,6 +476,11 @@ public IEnumerable GetDeviceIndexes(IEnumerable deviceUuids) } + /// + /// Resolve a DataItem buffer index back to its DataItem Id. + /// + /// The buffer index assigned to the DataItem. + /// The DataItem Id, or null if the index is not assigned. public string GetDataItemId(int dataItemIndex) { if (_dataItemIds.TryGetValue(dataItemIndex, out var dataItemId)) @@ -416,6 +491,11 @@ public string GetDataItemId(int dataItemIndex) return null; } + /// + /// Extract the DataItem index encoded in a composite buffer key and resolve it to its DataItem Id. + /// + /// The composite buffer key that encodes both the Device and DataItem indexes. + /// The DataItem Id, or null if the encoded index is not assigned. public string GetDataItemIdFromBufferKey(int bufferKey) { var dataItemIndex = BufferObservation.GetDataItemIndexFromBufferKey(bufferKey); @@ -427,6 +507,12 @@ public string GetDataItemIdFromBufferKey(int bufferKey) return null; } + /// + /// Resolve a Device-scoped DataItem to its buffer index, assigning and caching a new index if one does not yet exist. + /// + /// The UUID of the Device that owns the DataItem. + /// The Id of the DataItem. + /// The buffer index for the DataItem, or 0 if the DataItem Id is null. public int GetDataItemIndex(string deviceUuid, string dataItemId) { var index = 0; @@ -555,7 +641,7 @@ private MTConnectErrorHeader GetErrorHeader(Version mtconnectVersion = null) // `version` attribute on every response document Header. // Per , // this attribute is the MTConnect release the agent serves - // (Part 1.0 §3 Header), not the library assembly version. + // (Part 1.0 section 3 Header), not the library assembly version. // Pads build + revision with zero so the emitted shape matches // the cppagent reference (e.g. "2.5.0.0") regardless of how // many segments the source `Version` carried. @@ -1692,6 +1778,7 @@ public IErrorResponseDocument GetErrorResponseDocument(IEnumerable error #region "Add" + /// public override void InitializeDataItems(IDevice device, long timestamp = 0) { if (device != null && _observationBuffer != null) @@ -1790,6 +1877,7 @@ public override void InitializeDataItems(IDevice device, long timestamp = 0) } } + /// protected override ulong OnAddObservation(string deviceUuid, IDataItem dataItem, IObservationInput observationInput) { if (_observationBuffer != null && dataItem != null && observationInput != null) @@ -1833,11 +1921,13 @@ protected override ulong OnAddObservation(string deviceUuid, IDataItem dataItem, return 0; } + /// protected override bool OnAssetUpdate(IAsset asset) { return _assetBuffer.AddAsset(asset); } + /// protected override bool OnNewAssetAdded(IAsset asset) { if (asset != null) diff --git a/libraries/MTConnect.NET-Common/Agents/MTConnectAgentInformation.cs b/libraries/MTConnect.NET-Common/Agents/MTConnectAgentInformation.cs index ff6f3c897..1670879c1 100644 --- a/libraries/MTConnect.NET-Common/Agents/MTConnectAgentInformation.cs +++ b/libraries/MTConnect.NET-Common/Agents/MTConnectAgentInformation.cs @@ -9,36 +9,69 @@ namespace MTConnect.Agents { + /// + /// Persistent identity and buffer-index state for an MTConnect Agent that is saved to and restored from a JSON file so the Agent retains its UUID, InstanceId, and buffer slot assignments across restarts. + /// public class MTConnectAgentInformation { + /// + /// The default file name used to persist the Agent information. + /// public const string Filename = "agent.information.json"; + /// + /// A token regenerated on every save, used to detect when the persisted information has changed. + /// [JsonPropertyName("changeToken")] public string ChangeToken { get; set; } + /// + /// The stable unique identifier of the Agent. + /// [JsonPropertyName("uuid")] public string Uuid { get; set; } + /// + /// The InstanceId reported by the Agent, identifying the lifetime of its buffer. + /// [JsonPropertyName("instanceId")] public ulong InstanceId { get; set; } + /// + /// The timestamp, in Unix ticks, of the most recent change to the Device model. + /// [JsonPropertyName("deviceModelChangeTime")] public long DeviceModelChangeTime { get; set; } + /// + /// The persisted lookup of Device UUID to its assigned buffer index, restored so buffer slots remain stable across restarts. + /// [JsonPropertyName("devices")] public Dictionary DeviceIndexes { get; set; } + /// + /// The persisted lookup of DataItem key to its assigned buffer index, restored so buffer slots remain stable across restarts. + /// [JsonPropertyName("dataItems")] public Dictionary DataItemIndexes { get; set; } + /// + /// Initializes a new instance with a freshly generated UUID and an InstanceId set to the current time. + /// public MTConnectAgentInformation() { Uuid = Guid.NewGuid().ToString(); InstanceId = (ulong)UnixDateTime.Now; } + /// + /// Initializes a new instance with the given identity values. + /// + /// The stable unique identifier of the Agent. + /// The InstanceId identifying the lifetime of the Agent buffer. + /// The timestamp, in Unix ticks, of the most recent Device model change. public MTConnectAgentInformation(string uuid, ulong instanceId = 0, long deviceModelChangeTime = 0) { Uuid = uuid; @@ -47,6 +80,11 @@ public MTConnectAgentInformation(string uuid, ulong instanceId = 0, long deviceM } + /// + /// Read persisted Agent information from a JSON file. + /// + /// An optional file path; when omitted or relative, it is resolved against the application base directory and defaults to . + /// The deserialized Agent information, or null if the file is missing, empty, or cannot be read. public static MTConnectAgentInformation Read(string path = null) { var configurationPath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, Filename); @@ -75,6 +113,10 @@ public static MTConnectAgentInformation Read(string path = null) return null; } + /// + /// Persist this Agent information to a JSON file, regenerating before writing. + /// + /// An optional file path; when omitted, the file is written to the application base directory as . public void Save(string path = null) { var configurationPath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, Filename); diff --git a/libraries/MTConnect.NET-Common/Agents/MTConnectAgentModule.cs b/libraries/MTConnect.NET-Common/Agents/MTConnectAgentModule.cs index cfb6518c1..17ef3f743 100644 --- a/libraries/MTConnect.NET-Common/Agents/MTConnectAgentModule.cs +++ b/libraries/MTConnect.NET-Common/Agents/MTConnectAgentModule.cs @@ -5,50 +5,97 @@ namespace MTConnect.Agents { + /// + /// Base class for implementations that provides access to the host Agent broker and turns the lifecycle calls into overridable hook methods. + /// public abstract class MTConnectAgentModule : IMTConnectAgentModule { private readonly IMTConnectAgentBroker _agent; + /// + /// A unique identifier that distinguishes this module from other modules loaded by the Agent. + /// public string Id { get; set; } + /// + /// A human-readable description of the purpose this module serves within the Agent. + /// public string Description { get; set; } + /// + /// The Agent broker that hosts this module, available to derived classes for querying and publishing data. + /// public IMTConnectAgentBroker Agent => _agent; + /// + /// Raised when the module emits a log entry, allowing the host Agent to surface module diagnostics. + /// public event MTConnectLogEventHandler LogReceived; + /// + /// Initializes a new instance bound to the given host Agent broker. + /// + /// The Agent broker that hosts this module. public MTConnectAgentModule(IMTConnectAgentBroker agent) { _agent = agent; } + /// + /// Invoked during Agent startup before Devices are loaded; dispatches to . + /// + /// When true, the module should initialize DataItems with their default observations. public void StartBeforeLoad(bool initializeDataItems) { OnStartBeforeLoad(initializeDataItems); } + /// + /// Invoked during Agent startup after Devices are loaded; dispatches to . + /// + /// When true, the module should initialize DataItems with their default observations. public void StartAfterLoad(bool initializeDataItems) { OnStartAfterLoad(initializeDataItems); } + /// + /// Invoked during Agent shutdown; dispatches to . + /// public void Stop() { OnStop(); } + /// + /// Override to perform work before Devices are loaded into the Agent. The default implementation does nothing. + /// + /// When true, the module should initialize DataItems with their default observations. protected virtual void OnStartBeforeLoad(bool initializeDataItems) { } + /// + /// Override to perform work after Devices are loaded into the Agent. The default implementation does nothing. + /// + /// When true, the module should initialize DataItems with their default observations. protected virtual void OnStartAfterLoad(bool initializeDataItems) { } + /// + /// Override to release resources during Agent shutdown. The default implementation does nothing. + /// protected virtual void OnStop() { } + /// + /// Raise with the given log entry. + /// + /// The severity of the log entry. + /// The log message. + /// An optional identifier used to correlate related log entries. protected void Log(MTConnectLogLevel logLevel, string message, string logId = null) { if (LogReceived != null) LogReceived.Invoke(this, logLevel, message, logId); diff --git a/libraries/MTConnect.NET-Common/Agents/MTConnectAgentModules.cs b/libraries/MTConnect.NET-Common/Agents/MTConnectAgentModules.cs index 816fdfdd3..c832b01b3 100644 --- a/libraries/MTConnect.NET-Common/Agents/MTConnectAgentModules.cs +++ b/libraries/MTConnect.NET-Common/Agents/MTConnectAgentModules.cs @@ -8,6 +8,9 @@ namespace MTConnect.Agents { + /// + /// Discovers implementations from loaded assemblies, instantiates the ones enabled in the Agent configuration, and relays their lifecycle calls and log events. + /// public class MTConnectAgentModules { private static readonly List _moduleTypes = new List(); @@ -18,17 +21,31 @@ public class MTConnectAgentModules private readonly IMTConnectAgentBroker _mtconnectAgent; + /// + /// Raised once for each module after it has been instantiated and is ready to be started. + /// public event EventHandler ModuleLoaded; + /// + /// Raised when any hosted module emits a log entry. + /// public event MTConnectLogEventHandler LogReceived; + /// + /// Initializes a new instance bound to the given Agent configuration and Agent broker. + /// + /// The Agent configuration used to determine which modules are enabled and how many instances to create. + /// The Agent broker passed to each module instance. public MTConnectAgentModules(IAgentApplicationConfiguration configuration, IMTConnectAgentBroker mtconnectAgent) { _configuration = configuration; _mtconnectAgent = mtconnectAgent; } + /// + /// Discover all available module types and create instances for every module that is enabled in the configuration. + /// public void Load() { InitializeModules(); @@ -86,13 +103,17 @@ public void Load() catch { } } } - } + } } } } } } + /// + /// Invoke on every loaded module. + /// + /// When true, modules should initialize DataItems with their default observations. public void StartBeforeLoad(bool initializeDataItems) { Dictionary modules; @@ -106,6 +127,10 @@ public void StartBeforeLoad(bool initializeDataItems) } } + /// + /// Invoke on every loaded module. + /// + /// When true, modules should initialize DataItems with their default observations. public void StartAfterLoad(bool initializeDataItems) { Dictionary modules; @@ -119,6 +144,9 @@ public void StartAfterLoad(bool initializeDataItems) } } + /// + /// Invoke on every loaded module and clear the module cache. + /// public void Stop() { Dictionary modules; diff --git a/libraries/MTConnect.NET-Common/Agents/MTConnectAgentProcessor.cs b/libraries/MTConnect.NET-Common/Agents/MTConnectAgentProcessor.cs index 2699ae2d5..5b919fc0c 100644 --- a/libraries/MTConnect.NET-Common/Agents/MTConnectAgentProcessor.cs +++ b/libraries/MTConnect.NET-Common/Agents/MTConnectAgentProcessor.cs @@ -7,24 +7,54 @@ namespace MTConnect.Agents { + /// + /// Base class for implementations that turns the processing calls into overridable hook methods, defaulting to a pass-through transformation. + /// public abstract class MTConnectAgentProcessor : IMTConnectAgentProcessor { + /// + /// A unique identifier that distinguishes this processor from other processors loaded by the Agent. + /// public string Id { get; set; } + /// + /// A human-readable description of the transformation this processor applies. + /// public string Description { get; set; } + /// + /// Raised when the processor emits a log entry, allowing the host Agent to surface processor diagnostics. + /// public event MTConnectLogEventHandler LogReceived; + /// + /// Override to perform initialization required before processing begins. The default implementation does nothing. + /// public virtual void Load() { } + /// + /// Process an incoming observation by dispatching to . + /// + /// The observation, together with its resolved Device and DataItem context, to process. + /// The observation input to store, or null to suppress the observation. public IObservationInput Process(ProcessObservation observation) => OnProcess(observation); + /// + /// Process an incoming Asset by dispatching to . + /// + /// The Asset to process. + /// The Asset to store, or null to suppress the Asset. public IAsset Process(IAsset asset) => OnProcess(asset); + /// + /// Override to transform an incoming observation. The default implementation copies the observation through unchanged. + /// + /// The observation, together with its resolved Device and DataItem context, to process. + /// The observation input to store, or null when the input observation is null. protected virtual IObservationInput OnProcess(ProcessObservation observation) { if (observation != null) @@ -40,9 +70,19 @@ protected virtual IObservationInput OnProcess(ProcessObservation observation) return null; } + /// + /// Override to transform an incoming Asset. The default implementation returns the Asset unchanged. + /// + /// The Asset to process. + /// The Asset to store. protected virtual IAsset OnProcess(IAsset asset) => asset; + /// + /// Raise with the given log entry. + /// + /// The severity of the log entry. + /// The log message. protected void Log(MTConnectLogLevel logLevel, string message) { if (LogReceived != null) LogReceived.Invoke(this, logLevel, message); diff --git a/libraries/MTConnect.NET-Common/Agents/MTConnectAgentProcessors.cs b/libraries/MTConnect.NET-Common/Agents/MTConnectAgentProcessors.cs index 38a1fe9bb..f06b2192e 100644 --- a/libraries/MTConnect.NET-Common/Agents/MTConnectAgentProcessors.cs +++ b/libraries/MTConnect.NET-Common/Agents/MTConnectAgentProcessors.cs @@ -10,6 +10,9 @@ namespace MTConnect.Agents { + /// + /// Discovers implementations from loaded assemblies, instantiates the ones enabled in the Agent configuration, and runs incoming observations and Assets through the resulting processor chain. + /// public class MTConnectAgentProcessors { private static readonly List _processorTypes = new List(); @@ -20,16 +23,29 @@ public class MTConnectAgentProcessors private readonly IAgentApplicationConfiguration _configuration; + /// + /// Raised once for each processor after it has been instantiated and loaded. + /// public event EventHandler ProcessorLoaded; + /// + /// Raised when any hosted processor emits a log entry. + /// public event MTConnectLogEventHandler LogReceived; + /// + /// Initializes a new instance bound to the given Agent configuration. + /// + /// The Agent configuration used to determine which processors are enabled. public MTConnectAgentProcessors(IAgentApplicationConfiguration configuration) { _configuration = configuration; } + /// + /// Discover all available processor types and create and load instances for every processor that is enabled in the configuration. + /// public void Load() { InitializeProcessors(); @@ -70,6 +86,11 @@ public void Load() } + /// + /// Run an incoming observation through every loaded processor in turn, returning the final transformed result. + /// + /// The observation, together with its resolved Device and DataItem context, to process. + /// The observation input produced by the processor chain; when no processors are loaded, a faithful copy of the input observation. public IObservationInput Process(ProcessObservation observation) { var defaultObservation = new ObservationInput(); @@ -92,6 +113,11 @@ public IObservationInput Process(ProcessObservation observation) return outputObservation; } + /// + /// Run an incoming Asset through every loaded processor in turn, returning the final transformed result. + /// + /// The Asset to process. + /// The Asset produced by the processor chain; when no processors are loaded, the input Asset unchanged. public IAsset Process(IAsset asset) { var outputAsset = asset; @@ -109,6 +135,9 @@ public IAsset Process(IAsset asset) return outputAsset; } + /// + /// Release all loaded processors and clear the processor cache. + /// public void Dispose() { lock (_lock) diff --git a/libraries/MTConnect.NET-Common/Agents/MTConnectInputAgentModule.cs b/libraries/MTConnect.NET-Common/Agents/MTConnectInputAgentModule.cs index a0f6953a1..6150200d4 100644 --- a/libraries/MTConnect.NET-Common/Agents/MTConnectInputAgentModule.cs +++ b/libraries/MTConnect.NET-Common/Agents/MTConnectInputAgentModule.cs @@ -15,6 +15,9 @@ namespace MTConnect.Agents { + /// + /// Base class for Agent modules that act as an input data source: the module contributes a Device, then periodically polls for new data and publishes observations and Assets to the host Agent. Derived classes supply the Device and reading logic by overriding the hook methods. + /// public abstract class MTConnectInputAgentModule : IMTConnectAgentModule { private readonly IMTConnectAgentBroker _agent; @@ -23,20 +26,42 @@ public abstract class MTConnectInputAgentModule : IMTConnectAgentModule private bool _isStarted; + /// + /// A unique identifier that distinguishes this module from other modules loaded by the Agent. + /// public string Id { get; set; } + /// + /// A human-readable description of the data source this module represents. + /// public string Description { get; set; } + /// + /// The data-source configuration, including the read interval used by the polling loop. + /// public IDataSourceConfiguration Configuration { get; set; } + /// + /// The Agent broker this module publishes observations and Assets to. + /// public IMTConnectAgentBroker Agent => _agent; + /// + /// The Device this module contributed to the Agent, available once has run. + /// public IDevice Device => _device; + /// + /// Raised when the module emits a log entry, allowing the host Agent to surface module diagnostics. + /// public event MTConnectLogEventHandler LogReceived; + /// + /// Initializes a new instance bound to the given Agent broker, with a default data-source configuration. + /// + /// The Agent broker that hosts this module. public MTConnectInputAgentModule(IMTConnectAgentBroker agent) { _agent = agent; @@ -44,6 +69,10 @@ public MTConnectInputAgentModule(IMTConnectAgentBroker agent) } + /// + /// Run and add this module's Device to the Agent before Devices are loaded. + /// + /// When true, the module should initialize DataItems with their default observations. public void StartBeforeLoad(bool initializeDataItems) { OnStartBeforeLoad(initializeDataItems); @@ -51,6 +80,10 @@ public void StartBeforeLoad(bool initializeDataItems) _device = _agent.AddDevice(OnAddDevice()); } + /// + /// Run and start the polling loop after Devices are loaded. + /// + /// When true, the module should initialize DataItems with their default observations. public void StartAfterLoad(bool initializeDataItems) { OnStartAfterLoad(initializeDataItems); @@ -59,22 +92,47 @@ public void StartAfterLoad(bool initializeDataItems) } + /// + /// Override to perform work before the module's Device is added to the Agent. The default implementation does nothing. + /// + /// When true, the module should initialize DataItems with their default observations. protected virtual void OnStartBeforeLoad(bool initializeDataItems) { } + /// + /// Override to perform work after the module's Device is added and before polling starts. The default implementation does nothing. + /// + /// When true, the module should initialize DataItems with their default observations. protected virtual void OnStartAfterLoad(bool initializeDataItems) { } - protected virtual void OnStop() + /// + /// Invoked during shutdown; the default implementation stops the polling loop. Override to release additional resources. + /// + protected virtual void OnStop() { Stop(); } + /// + /// Override to perform a synchronous read on each polling cycle. The default implementation does nothing. + /// protected virtual void OnRead() { } + /// + /// Override to perform an asynchronous read on each polling cycle. The default implementation completes immediately. + /// + /// A task representing the asynchronous read. protected virtual Task OnReadAsync() { return Task.CompletedTask; } + /// + /// Override to supply the Device this module contributes to the Agent. The default implementation returns null. + /// + /// The Device to add, or null if the module contributes no Device. protected virtual IDevice OnAddDevice() { return null; } + /// + /// Start the background polling loop if it is not already running. + /// public void Start() { if (!_isStarted) @@ -87,6 +145,9 @@ public void Start() } } + /// + /// Stop the background polling loop and run the shutdown hook if the module is running. + /// public void Stop() { if (_isStarted) @@ -124,6 +185,9 @@ private async Task Worker() #region "Unavailable" + /// + /// Publish an UNAVAILABLE observation for every DataItem on the module's Device, typically used when the data source goes offline. + /// public void SetUnavailable() { var dataItems = _device.GetDataItems(); @@ -138,6 +202,10 @@ public void SetUnavailable() } } + /// + /// Publish an UNAVAILABLE observation for the DataItem identified by the given key, using the current time. + /// + /// The Id or Name of the DataItem. public void SetUnavailable(string dataItemKey) { if (!string.IsNullOrEmpty(dataItemKey)) @@ -150,6 +218,11 @@ public void SetUnavailable(string dataItemKey) } } + /// + /// Publish an UNAVAILABLE observation for the DataItem identified by the given key at the specified time. + /// + /// The Id or Name of the DataItem. + /// The time the DataItem became unavailable. public void SetUnavailable(string dataItemKey, DateTime timestamp) { if (!string.IsNullOrEmpty(dataItemKey)) @@ -162,6 +235,11 @@ public void SetUnavailable(string dataItemKey, DateTime timestamp) } } + /// + /// Publish an UNAVAILABLE observation for the DataItem identified by the given key at the specified time. + /// + /// The Id or Name of the DataItem. + /// The time the DataItem became unavailable, in Unix ticks. public void SetUnavailable(string dataItemKey, long timestamp) { if (!string.IsNullOrEmpty(dataItemKey)) @@ -174,17 +252,31 @@ public void SetUnavailable(string dataItemKey, long timestamp) } } + /// + /// Publish an UNAVAILABLE observation for the given DataItem, using the current time. + /// + /// The DataItem to mark unavailable. public void SetUnavailable(IDataItem dataItem) { var timestamp = UnixDateTime.Now; SetUnavailable(dataItem, timestamp); } + /// + /// Publish an UNAVAILABLE observation for the given DataItem at the specified time. + /// + /// The DataItem to mark unavailable. + /// The time the DataItem became unavailable. public void SetUnavailable(IDataItem dataItem, DateTime timestamp) { SetUnavailable(dataItem, timestamp.ToUnixTime()); } + /// + /// Publish an UNAVAILABLE observation for the given DataItem at the specified time, emitting an UNAVAILABLE condition level for condition DataItems and the unavailable result value otherwise. + /// + /// The DataItem to mark unavailable. + /// The time the DataItem became unavailable, in Unix ticks. public void SetUnavailable(IDataItem dataItem, long timestamp) { if (dataItem != null && !string.IsNullOrEmpty(dataItem.Id)) @@ -211,6 +303,11 @@ public void SetUnavailable(IDataItem dataItem, long timestamp) #region "Value Observations" + /// + /// Publish a value observation for the given DataItem, using the current time. + /// + /// The DataItem to report against. + /// The observed value. public void AddValueObservation(IDataItem dataItem, object resultValue) { if (dataItem != null && !string.IsNullOrEmpty(dataItem.Id)) @@ -220,6 +317,12 @@ public void AddValueObservation(IDataItem dataItem, object resultValue) } } + /// + /// Publish a value observation for the given DataItem at the specified time. + /// + /// The DataItem to report against. + /// The observed value. + /// The time of the observation, in Unix ticks. public void AddValueObservation(IDataItem dataItem, object resultValue, long timestamp) { if (dataItem != null && !string.IsNullOrEmpty(dataItem.Id)) @@ -229,6 +332,12 @@ public void AddValueObservation(IDataItem dataItem, object resultValue, long tim } } + /// + /// Publish a value observation for the given DataItem at the specified time. + /// + /// The DataItem to report against. + /// The observed value. + /// The time of the observation. public void AddValueObservation(IDataItem dataItem, object resultValue, DateTime timestamp) { if (dataItem != null && !string.IsNullOrEmpty(dataItem.Id)) @@ -238,24 +347,47 @@ public void AddValueObservation(IDataItem dataItem, object resultValue, DateTime } } + /// + /// Publish a value observation for the DataItem identified by the given key, using the current time. + /// + /// The Id or Name of the DataItem. + /// The observed value. public void AddValueObservation(string dataItemKey, object resultValue) { var observation = new ObservationInput(dataItemKey, resultValue); AddObservation(observation); } + /// + /// Publish a value observation for the DataItem identified by the given key at the specified time. + /// + /// The Id or Name of the DataItem. + /// The observed value. + /// The time of the observation, in Unix ticks. public void AddValueObservation(string dataItemKey, object resultValue, long timestamp) { var observation = new ObservationInput(dataItemKey, resultValue, timestamp); AddObservation(observation); } + /// + /// Publish a value observation for the DataItem identified by the given key at the specified time. + /// + /// The Id or Name of the DataItem. + /// The observed value. + /// The time of the observation. public void AddValueObservation(string dataItemKey, object resultValue, DateTime timestamp) { var observation = new ObservationInput(dataItemKey, resultValue, timestamp); AddObservation(observation); } + /// + /// Publish a value observation, resolving the DataItem on the module's Device by its type and optional sub-type. + /// + /// The DataItem type to resolve. + /// The observed value. + /// An optional DataItem sub-type used to disambiguate the lookup. public void AddValueObservation(object result, object subType = null) where TDataItem : IDataItem { if (Agent != null && Device != null) @@ -264,6 +396,14 @@ public void AddValueObservation(object result, object subType = null) } } + /// + /// Publish a value observation, resolving the DataItem on a named Component of the module's Device. + /// + /// The Component type that owns the DataItem. + /// The DataItem type to resolve. + /// The observed value. + /// An optional Component name used to disambiguate the lookup. + /// An optional DataItem sub-type used to disambiguate the lookup. public void AddValueObservation(object result, string componentName = null, object subType = null) where TComponent : IComponent where TDataItem : IDataItem @@ -274,6 +414,15 @@ public void AddValueObservation(object result, string com } } + /// + /// Publish a value observation, resolving the DataItem on a Composition of a named Component of the module's Device. + /// + /// The Component type that owns the Composition. + /// The Composition type that owns the DataItem. + /// The DataItem type to resolve. + /// The observed value. + /// An optional Component name used to disambiguate the lookup. + /// An optional DataItem sub-type used to disambiguate the lookup. public void AddValueObservation(object result, string componentName = null, object subType = null) where TComponent : IComponent where TComposition : IComposition @@ -289,6 +438,16 @@ public void AddValueObservation(object resu #region "Condition Observations" + /// + /// Publish a condition fault-state observation for the DataItem identified by the given key, using the current time. + /// + /// The Id or Name of the condition DataItem. + /// The condition level being reported. + /// An optional native code identifying the condition on the source equipment. + /// An optional human-readable description of the condition. + /// An optional native severity reported by the source equipment. + /// An optional qualifier that further classifies the condition. + /// An optional identifier used to correlate updates to the same condition. public void AddConditionObservation( string dataItemKey, ConditionLevel level, @@ -302,6 +461,17 @@ public void AddConditionObservation( AddConditionObservation(dataItemKey, level, UnixDateTime.Now, nativeCode, message, nativeSeverity, qualifier, conditionId); } + /// + /// Publish a condition fault-state observation for the DataItem identified by the given key at the specified time. + /// + /// The Id or Name of the condition DataItem. + /// The condition level being reported. + /// The time of the observation. + /// An optional native code identifying the condition on the source equipment. + /// An optional human-readable description of the condition. + /// An optional native severity reported by the source equipment. + /// An optional qualifier that further classifies the condition. + /// An optional identifier used to correlate updates to the same condition. public void AddConditionObservation( string dataItemKey, ConditionLevel level, @@ -316,6 +486,17 @@ public void AddConditionObservation( AddConditionObservation(dataItemKey, level, timestamp.ToUnixTime(), nativeCode, message, nativeSeverity, qualifier, conditionId); } + /// + /// Publish a condition fault-state observation for the DataItem identified by the given key at the specified time. + /// + /// The Id or Name of the condition DataItem. + /// The condition level being reported. + /// The time of the observation, in Unix ticks. + /// An optional native code identifying the condition on the source equipment. + /// An optional human-readable description of the condition. + /// An optional native severity reported by the source equipment. + /// An optional qualifier that further classifies the condition. + /// An optional identifier used to correlate updates to the same condition. public void AddConditionObservation( string dataItemKey, ConditionLevel level, @@ -344,6 +525,17 @@ public void AddConditionObservation( } } + /// + /// Publish a condition fault-state observation, resolving the DataItem on the module's Device by its type and optional sub-type. + /// + /// The condition DataItem type to resolve. + /// The condition level being reported. + /// An optional native code identifying the condition on the source equipment. + /// An optional human-readable description of the condition. + /// An optional native severity reported by the source equipment. + /// An optional qualifier that further classifies the condition. + /// An optional identifier used to correlate updates to the same condition. + /// An optional DataItem sub-type used to disambiguate the lookup. public void AddConditionObservation( ConditionLevel level, string nativeCode = null, @@ -375,6 +567,19 @@ public void AddConditionObservation( } } + /// + /// Publish a condition fault-state observation, resolving the DataItem on a named Component of the module's Device. + /// + /// The Component type that owns the DataItem. + /// The condition DataItem type to resolve. + /// The condition level being reported. + /// An optional native code identifying the condition on the source equipment. + /// An optional human-readable description of the condition. + /// An optional native severity reported by the source equipment. + /// An optional qualifier that further classifies the condition. + /// An optional identifier used to correlate updates to the same condition. + /// An optional Component name used to disambiguate the lookup. + /// An optional DataItem sub-type used to disambiguate the lookup. public void AddConditionObservation( ConditionLevel level, string nativeCode = null, @@ -412,6 +617,12 @@ public void AddConditionObservation( #region "DataSet Observations" + /// + /// Publish a Data Set observation containing a single entry for the DataItem identified by the given key. + /// + /// The Id or Name of the Data Set DataItem. + /// The key of the Data Set entry. + /// The value of the Data Set entry. public void AddDataSetObservation(string dataItemKey, string entryKey, object value) { if (Agent != null && Device != null && !string.IsNullOrEmpty(dataItemKey) && !string.IsNullOrEmpty(entryKey) && value != null) @@ -425,6 +636,11 @@ public void AddDataSetObservation(string dataItemKey, string entryKey, object va } } + /// + /// Publish a Data Set observation containing a single entry for the DataItem identified by the given key. + /// + /// The Id or Name of the Data Set DataItem. + /// The Data Set entry to publish. public void AddDataSetObservation(string dataItemKey, IDataSetEntry entry) { if (Agent != null && Device != null && !string.IsNullOrEmpty(dataItemKey) && entry != null) @@ -438,6 +654,11 @@ public void AddDataSetObservation(string dataItemKey, IDataSetEntry entry) } } + /// + /// Publish a Data Set observation containing the given entries for the DataItem identified by the given key. + /// + /// The Id or Name of the Data Set DataItem. + /// The Data Set entries to publish. public void AddDataSetObservation(string dataItemKey, IEnumerable entries) { if (Agent != null && Device != null && !string.IsNullOrEmpty(dataItemKey) && !entries.IsNullOrEmpty()) @@ -451,6 +672,12 @@ public void AddDataSetObservation(string dataItemKey, IEnumerable } } + /// + /// Publish a Data Set observation, resolving the DataItem on the module's Device by its type and optional sub-type. + /// + /// The Data Set DataItem type to resolve. + /// The Data Set entries to publish. + /// An optional DataItem sub-type used to disambiguate the lookup. public void AddDataSetObservation( IEnumerable entries, string subType = null @@ -472,6 +699,14 @@ public void AddDataSetObservation( } } + /// + /// Publish a Data Set observation, resolving the DataItem on a named Component of the module's Device. + /// + /// The Component type that owns the DataItem. + /// The Data Set DataItem type to resolve. + /// The Data Set entries to publish. + /// An optional Component name used to disambiguate the lookup. + /// An optional DataItem sub-type used to disambiguate the lookup. public void AddDataSetObservation( IEnumerable entries, string componentName = null, @@ -499,6 +734,11 @@ public void AddDataSetObservation( #region "Table Observations" + /// + /// Publish a Table observation containing a single entry for the DataItem identified by the given key. + /// + /// The Id or Name of the Table DataItem. + /// The Table entry to publish. public void AddTableObservation(string dataItemKey, ITableEntry entry) { if (Agent != null && Device != null && !string.IsNullOrEmpty(dataItemKey) && entry != null) @@ -512,6 +752,11 @@ public void AddTableObservation(string dataItemKey, ITableEntry entry) } } + /// + /// Publish a Table observation containing the given entries for the DataItem identified by the given key. + /// + /// The Id or Name of the Table DataItem. + /// The Table entries to publish. public void AddTableObservation(string dataItemKey, IEnumerable entries) { if (Agent != null && Device != null && !string.IsNullOrEmpty(dataItemKey) && !entries.IsNullOrEmpty()) @@ -525,6 +770,12 @@ public void AddTableObservation(string dataItemKey, IEnumerable ent } } + /// + /// Publish a Table observation, resolving the DataItem on the module's Device by its type and optional sub-type. + /// + /// The Table DataItem type to resolve. + /// The Table entries to publish. + /// An optional DataItem sub-type used to disambiguate the lookup. public void AddTableObservation( IEnumerable entries, string subType = null @@ -546,6 +797,14 @@ public void AddTableObservation( } } + /// + /// Publish a Table observation, resolving the DataItem on a named Component of the module's Device. + /// + /// The Component type that owns the DataItem. + /// The Table DataItem type to resolve. + /// The Table entries to publish. + /// An optional Component name used to disambiguate the lookup. + /// An optional DataItem sub-type used to disambiguate the lookup. public void AddTableObservation( IEnumerable entries, string componentName = null, @@ -573,6 +832,11 @@ public void AddTableObservation( #region "TimeSeries Observations" + /// + /// Publish a Time Series observation containing the given samples for the DataItem identified by the given key. + /// + /// The Id or Name of the Time Series DataItem. + /// The ordered sample values. public void AddTimeSeriesObservation(string dataItemKey, IEnumerable samples) { if (Agent != null && Device != null && !string.IsNullOrEmpty(dataItemKey) && !samples.IsNullOrEmpty()) @@ -586,6 +850,12 @@ public void AddTimeSeriesObservation(string dataItemKey, IEnumerable sam } } + /// + /// Publish a Time Series observation, resolving the DataItem on the module's Device by its type and optional sub-type. + /// + /// The Time Series DataItem type to resolve. + /// The ordered sample values. + /// An optional DataItem sub-type used to disambiguate the lookup. public void AddTimeSeriesObservation( IEnumerable samples, string subType = null @@ -607,6 +877,14 @@ public void AddTimeSeriesObservation( } } + /// + /// Publish a Time Series observation, resolving the DataItem on a named Component of the module's Device. + /// + /// The Component type that owns the DataItem. + /// The Time Series DataItem type to resolve. + /// The ordered sample values. + /// An optional Component name used to disambiguate the lookup. + /// An optional DataItem sub-type used to disambiguate the lookup. public void AddTimeSeriesObservation( IEnumerable samples, string componentName = null, @@ -633,12 +911,20 @@ public void AddTimeSeriesObservation( #endregion + /// + /// Publish a prepared observation input to the Agent against the module's Device. + /// + /// The observation input to publish. public void AddObservation(IObservationInput observation) { Agent.AddObservation(_device.Uuid, observation); } - + + /// + /// Publish an Asset to the Agent, wrapping it in an Asset input bound to the module's Device. + /// + /// The Asset to publish. public void AddAsset(IAsset asset) { if (asset != null) @@ -647,12 +933,21 @@ public void AddAsset(IAsset asset) } } + /// + /// Publish a prepared Asset input to the Agent. + /// + /// The Asset input, including the target Device key. public void AddAsset(IAssetInput asset) { Agent.AddAsset(asset.DeviceKey, asset.Asset); } + /// + /// Raise with the given log entry. + /// + /// The severity of the log entry. + /// The log message. protected void Log(MTConnectLogLevel logLevel, string message) { if (LogReceived != null) LogReceived.Invoke(this, logLevel, message); diff --git a/libraries/MTConnect.NET-Common/Agents/Metrics/AssetMetric.cs b/libraries/MTConnect.NET-Common/Agents/Metrics/AssetMetric.cs index f293d51bc..7f0836558 100644 --- a/libraries/MTConnect.NET-Common/Agents/Metrics/AssetMetric.cs +++ b/libraries/MTConnect.NET-Common/Agents/Metrics/AssetMetric.cs @@ -16,12 +16,24 @@ public class AssetMetric private double _lastAverage = 0; + /// + /// The ID of the Asset these metrics track. + /// public string AssetId { get; set; } + /// + /// The running total number of asset updates recorded. + /// public int Count { get; set; } + /// + /// The Unix timestamp of the most recent asset update. + /// public long LastUpdated { get; set; } + /// + /// The number of asset updates recorded since the last rate-update window. + /// public int Delta { get @@ -33,6 +45,9 @@ public int Delta } } + /// + /// The exponentially smoothed asset update rate over the configured window. + /// public double Average { get @@ -45,8 +60,15 @@ public double Average } + /// + /// Initializes an empty metric, typically populated later. + /// public AssetMetric() { } + /// + /// Initializes a metric bound to the given Asset. + /// + /// The ID of the Asset to track. public AssetMetric(string assetId) { AssetId = assetId; diff --git a/libraries/MTConnect.NET-Common/Agents/Metrics/DeviceMetrics.cs b/libraries/MTConnect.NET-Common/Agents/Metrics/DeviceMetrics.cs index 2ff02049f..c160b47d2 100644 --- a/libraries/MTConnect.NET-Common/Agents/Metrics/DeviceMetrics.cs +++ b/libraries/MTConnect.NET-Common/Agents/Metrics/DeviceMetrics.cs @@ -25,8 +25,14 @@ public class DeviceMetrics private double _lastAssetAverage = 0; + /// + /// The UUID of the Device these metrics aggregate. + /// public string DeviceUuid { get; set; } + /// + /// The number of observations recorded across the device since the last rate-update window. + /// public int ObservationDelta { get @@ -38,6 +44,9 @@ public int ObservationDelta } } + /// + /// The exponentially smoothed observation update rate across the device. + /// public double ObservationAverage { get @@ -49,6 +58,9 @@ public double ObservationAverage } } + /// + /// The number of asset updates recorded across the device since the last rate-update window. + /// public int AssetDelta { get @@ -60,6 +72,9 @@ public int AssetDelta } } + /// + /// The exponentially smoothed asset update rate across the device. + /// public double AssetAverage { get @@ -72,8 +87,15 @@ public double AssetAverage } + /// + /// Initializes an empty device metrics aggregate, typically populated later. + /// public DeviceMetrics() { } + /// + /// Initializes a device metrics aggregate bound to the given Device. + /// + /// The UUID of the Device to track. public DeviceMetrics(string deviceUuid) { DeviceUuid = deviceUuid; @@ -122,6 +144,9 @@ internal void UpdateRate(double updateInterval, double windowInterval) } + /// + /// Returns the total observation count summed across every tracked DataItem. + /// public int GetObservationCount() { int count = 0; @@ -138,6 +163,9 @@ public int GetObservationCount() return count; } + /// + /// Returns the total asset-update count summed across every tracked Asset. + /// public int GetAssetCount() { int count = 0; @@ -155,6 +183,9 @@ public int GetAssetCount() } + /// + /// Returns a snapshot of the per-DataItem observation metrics. + /// public IEnumerable GetObservationMetrics() { lock (_lock) @@ -163,6 +194,10 @@ public IEnumerable GetObservationMetrics() } } + /// + /// Returns the observation metric for the given DataItem, or null when none is tracked. + /// + /// The DataItem ID to look up. public ObservationMetric GetObservationMetric(string dataItemId) { if (!string.IsNullOrEmpty(dataItemId)) @@ -180,6 +215,9 @@ public ObservationMetric GetObservationMetric(string dataItemId) } + /// + /// Returns a snapshot of the per-Asset update metrics. + /// public IEnumerable GetAssetMetrics() { lock (_lock) @@ -188,6 +226,10 @@ public IEnumerable GetAssetMetrics() } } + /// + /// Returns the asset metric for the given Asset, or null when none is tracked. + /// + /// The Asset ID to look up. public AssetMetric GetAssetMetric(string assetId) { if (!string.IsNullOrEmpty(assetId)) @@ -205,6 +247,10 @@ public AssetMetric GetAssetMetric(string assetId) } + /// + /// Records an observation for the given DataItem, creating its metric on first sighting and bumping its count and last-updated timestamp. + /// + /// The DataItem ID that produced an observation. public void UpdateObservation(string dataItemId) { if (!string.IsNullOrEmpty(dataItemId)) @@ -235,6 +281,10 @@ public void UpdateObservation(string dataItemId) } } + /// + /// Records an update for the given Asset, creating its metric on first sighting and bumping its count and last-updated timestamp. + /// + /// The Asset ID that was updated. public void UpdateAsset(string assetId) { if (!string.IsNullOrEmpty(assetId)) diff --git a/libraries/MTConnect.NET-Common/Agents/Metrics/MTConnectAgentMetrics.cs b/libraries/MTConnect.NET-Common/Agents/Metrics/MTConnectAgentMetrics.cs index 12ab19b75..fd1b40b24 100644 --- a/libraries/MTConnect.NET-Common/Agents/Metrics/MTConnectAgentMetrics.cs +++ b/libraries/MTConnect.NET-Common/Agents/Metrics/MTConnectAgentMetrics.cs @@ -27,13 +27,22 @@ public class MTConnectAgentMetrics : IDisposable private double _lastAssetAverage = 0; + /// + /// The interval at which rates are recalculated. + /// public TimeSpan UpdateInterval => _updateInterval; + /// + /// The averaging window over which rates are exponentially smoothed. + /// public TimeSpan WindowInterval => _windowInterval; + /// + /// The number of observations recorded agent-wide since the last rate-update window. + /// public int ObservationDelta { - get + get { lock (_lock) { @@ -42,6 +51,9 @@ public int ObservationDelta } } + /// + /// The exponentially smoothed agent-wide observation update rate. + /// public double ObservationAverage { get @@ -53,6 +65,9 @@ public double ObservationAverage } } + /// + /// The number of asset updates recorded agent-wide since the last rate-update window. + /// public int AssetDelta { get @@ -64,6 +79,9 @@ public int AssetDelta } } + /// + /// The exponentially smoothed agent-wide asset update rate. + /// public double AssetAverage { get @@ -75,9 +93,17 @@ public double AssetAverage } } + /// + /// Invoked for each device after every rate-update pass, supplying that device's refreshed metrics. + /// public EventHandler DeviceMetricsUpdated { get; set; } + /// + /// Starts a metrics handler that recalculates rates on the given interval, smoothing them over the given window. + /// + /// How often rates are recalculated. + /// The averaging window for exponential smoothing. public MTConnectAgentMetrics(TimeSpan updateInterval, TimeSpan windowInterval) { _updateTimer = new System.Timers.Timer(); @@ -93,6 +119,9 @@ public MTConnectAgentMetrics(TimeSpan updateInterval, TimeSpan windowInterval) } + /// + /// Stops the rate-update timer and releases its resources. + /// public void Dispose() { if (_updateTimer != null) _updateTimer.Dispose(); @@ -134,6 +163,9 @@ private void UpdateRate(double updateInterval, double windowInterval) } + /// + /// Returns a snapshot of the per-device metrics aggregates. + /// public IEnumerable GetDeviceMetrics() { lock (_lock) @@ -142,6 +174,10 @@ public IEnumerable GetDeviceMetrics() } } + /// + /// Returns the metrics aggregate for the given Device, or null when none is tracked. + /// + /// The Device UUID to look up. public DeviceMetrics GetDeviceMetric(string deviceUuid) { if (!string.IsNullOrEmpty(deviceUuid)) @@ -159,6 +195,9 @@ public DeviceMetrics GetDeviceMetric(string deviceUuid) } + /// + /// Returns the total observation count summed across every tracked device. + /// public int GetObservationCount() { int count = 0; @@ -175,6 +214,9 @@ public int GetObservationCount() return count; } + /// + /// Returns the total asset-update count summed across every tracked device. + /// public int GetAssetCount() { int count = 0; @@ -192,6 +234,11 @@ public int GetAssetCount() } + /// + /// Records an observation for the given Device/DataItem, creating the device aggregate on first sighting. + /// + /// The Device UUID that produced the observation. + /// The DataItem ID that produced the observation. public void UpdateObservation(string deviceUuid, string dataItemId) { if (!string.IsNullOrEmpty(deviceUuid) && !string.IsNullOrEmpty(dataItemId)) @@ -211,6 +258,11 @@ public void UpdateObservation(string deviceUuid, string dataItemId) } } + /// + /// Records an update for the given Device/Asset, creating the device aggregate on first sighting. + /// + /// The Device UUID the asset belongs to. + /// The Asset ID that was updated. public void UpdateAsset(string deviceUuid, string assetId) { if (!string.IsNullOrEmpty(deviceUuid) && !string.IsNullOrEmpty(assetId)) diff --git a/libraries/MTConnect.NET-Common/Agents/Metrics/ObservationMetric.cs b/libraries/MTConnect.NET-Common/Agents/Metrics/ObservationMetric.cs index bf1068b1d..57e02f33a 100644 --- a/libraries/MTConnect.NET-Common/Agents/Metrics/ObservationMetric.cs +++ b/libraries/MTConnect.NET-Common/Agents/Metrics/ObservationMetric.cs @@ -16,12 +16,24 @@ public class ObservationMetric private double _lastAverage = 0; + /// + /// The ID of the DataItem these metrics track. + /// public string DataItemId { get; set; } + /// + /// The running total number of observations recorded for the DataItem. + /// public int Count { get; set; } + /// + /// The Unix timestamp of the most recent observation update. + /// public long LastUpdated { get; set; } + /// + /// The number of observations recorded since the last rate-update window. + /// public int Delta { get @@ -33,6 +45,9 @@ public int Delta } } + /// + /// The exponentially smoothed observation update rate over the configured window. + /// public double Average { get @@ -45,8 +60,15 @@ public double Average } + /// + /// Initializes an empty metric, typically populated later. + /// public ObservationMetric() { } + /// + /// Initializes a metric bound to the given DataItem. + /// + /// The ID of the DataItem to track. public ObservationMetric(string dataItemId) { DataItemId = dataItemId; diff --git a/libraries/MTConnect.NET-Common/Agents/ProcessObservation.cs b/libraries/MTConnect.NET-Common/Agents/ProcessObservation.cs index 6093ce33c..c66fda5fd 100644 --- a/libraries/MTConnect.NET-Common/Agents/ProcessObservation.cs +++ b/libraries/MTConnect.NET-Common/Agents/ProcessObservation.cs @@ -10,17 +10,38 @@ namespace MTConnect.Agents { + /// + /// A mutable view of an observation as it passes through the Agent processor chain, pairing the raw observation values with the resolved Agent and DataItem context and exposing helpers to add, read, or clear individual values. + /// public class ProcessObservation { + /// + /// The Agent that received the observation. + /// public IMTConnectAgent Agent { get; set; } + /// + /// The DataItem the observation was reported for, including its owning Device. + /// public IDataItem DataItem { get; set; } + /// + /// The current set of observation values; processors may replace this collection to transform the observation. + /// public IEnumerable Values { get; set; } + /// + /// The time the observation occurred. + /// public DateTime Timestamp { get; set; } + /// + /// Initializes a new instance from a received observation input and its resolved context. + /// + /// The Agent that received the observation. + /// The DataItem the observation was reported for. + /// The received observation input whose values and timestamp seed this instance. public ProcessObservation(IMTConnectAgent agent, IDataItem dataItem, IObservationInput observation) { Agent = agent; @@ -30,11 +51,20 @@ public ProcessObservation(IMTConnectAgent agent, IDataItem dataItem, IObservatio } + /// + /// Add or replace the value with the given key. + /// + /// The key identifying the value (for example, CDATA or a representation entry key). + /// The value to store. public void AddValue(string valueKey, object value) { AddValue(new ObservationValue(valueKey, value)); } + /// + /// Add or replace an observation value, removing any existing value with the same key and dropping the new value if it is empty. + /// + /// The observation value to add. public void AddValue(ObservationValue observationValue) { var x = new List(); @@ -54,6 +84,11 @@ public void AddValue(ObservationValue observationValue) Values = x; } + /// + /// Get the value stored under the given key. + /// + /// The key identifying the value to retrieve. + /// The matching value, or null if no value with the key is present. public string GetValue(string valueKey) { if (!string.IsNullOrEmpty(valueKey) && !Values.IsNullOrEmpty()) @@ -65,6 +100,9 @@ public string GetValue(string valueKey) return null; } + /// + /// Remove all observation values, effectively suppressing the observation. + /// public void ClearValues() { Values = null; diff --git a/libraries/MTConnect.NET-Common/Assemblies.cs b/libraries/MTConnect.NET-Common/Assemblies.cs index 507fcdad9..822e1bd75 100644 --- a/libraries/MTConnect.NET-Common/Assemblies.cs +++ b/libraries/MTConnect.NET-Common/Assemblies.cs @@ -11,6 +11,9 @@ namespace MTConnect { + /// + /// Discovers and caches the DLL assemblies in the application base directory so that plugin modules can be located via reflection. + /// public static class Assemblies { private static Assembly[] _assemblies; diff --git a/libraries/MTConnect.NET-Common/Assets/Asset.cs b/libraries/MTConnect.NET-Common/Assets/Asset.cs index 7526bc402..aad182a77 100644 --- a/libraries/MTConnect.NET-Common/Assets/Asset.cs +++ b/libraries/MTConnect.NET-Common/Assets/Asset.cs @@ -28,6 +28,9 @@ public string Uuid set => _uuid = value; } + /// + /// Identifies this entity as an Asset within the MTConnect entity model. + /// public MTConnectEntityType EntityType => MTConnectEntityType.Asset; @@ -42,6 +45,10 @@ public string Uuid public ulong InstanceId { get; set; } + /// + /// Instantiates the concrete asset class registered for the given asset type name via its parameterless constructor; returns null when the type is unknown or cannot be constructed. + /// + /// The MTConnect asset type name (e.g. "CuttingTool"). public static IAsset Create(string type) { if (!string.IsNullOrEmpty(type)) @@ -68,6 +75,10 @@ public static IAsset Create(string type) return null; } + /// + /// Resolves the concrete CLR type registered for the given asset type name without instantiating it; returns null when the type is unknown. + /// + /// The MTConnect asset type name (e.g. "CuttingTool"). public static Type GetAssetType(string type) { if (!string.IsNullOrEmpty(type)) @@ -122,6 +133,10 @@ private static Dictionary GetAllTypes() } + /// + /// Prepares this asset for inclusion in a response document for the given MTConnect version: excludes the asset entirely when the version predates 1.2, drops the Hash for versions before 2.2 (where it is not defined), then delegates per-type adjustment to . + /// + /// The MTConnect version the response document targets. public IAsset Process(Version mtconnectVersion) { if (mtconnectVersion < MTConnectVersions.Version12) return null; @@ -131,16 +146,28 @@ public IAsset Process(Version mtconnectVersion) return OnProcess(mtconnectVersion); } + /// + /// Per-type version adjustment hook invoked by ; the base implementation returns the asset unchanged. Overrides may downgrade properties or return null to exclude the asset for a given version. + /// + /// The MTConnect version the response document targets. protected virtual IAsset OnProcess(Version mtconnectVersion) { return this; } + /// + /// Validates the asset against the given MTConnect version; the base implementation accepts all assets and is overridden by types with required fields or constraints. + /// + /// The MTConnect version to validate against. public virtual AssetValidationResult IsValid(Version mtconnectVersion) { return new AssetValidationResult(true); } + /// + /// Computes a content hash for change detection; the base implementation returns null and is overridden by concrete asset types that participate in hashing. + /// + /// When true, the asset timestamp is folded into the hash. public virtual string GenerateHash(bool includeTimestamp = true) { return null; diff --git a/libraries/MTConnect.NET-Common/Assets/Asset.g.cs b/libraries/MTConnect.NET-Common/Assets/Asset.g.cs index 5bdd2d404..41d96e041 100644 --- a/libraries/MTConnect.NET-Common/Assets/Asset.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Asset.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets /// public partial class Asset : IAsset { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Abstract Asset."; @@ -17,52 +20,52 @@ public partial class Asset : IAsset /// Unique identifier for an Asset. /// public string AssetId { get; set; } - + /// /// Technical information about an entity describing its physical layout, functional characteristics, and relationships with other entities. /// public MTConnect.Devices.Configurations.IConfiguration Configuration { get; set; } - + /// /// Textual description for Asset. /// public string Description { get; set; } - + /// /// Associated piece of equipment's UUID that supplied the Asset's data.uuid defined in Device Information Model. /// public string DeviceUuid { get; set; } - + /// /// Condensed message digest from a secure one-way hash function. FIPS PUB 180-4 /// public string Hash { get; set; } - + /// /// /// public System.Collections.Generic.IEnumerable Manufacturers { get; set; } - + /// /// /// public string Model { get; set; } - + /// /// Indicator that the Asset has been removed from the piece of equipment. /// public bool Removed { get; set; } - + /// /// /// public string SerialNumber { get; set; } - + /// /// /// public string Station { get; set; } - + /// /// Time the Asset data was last modified. /// diff --git a/libraries/MTConnect.NET-Common/Assets/AssetDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/AssetDescriptions.g.cs index 33b9ab9d6..a10e7d2f5 100644 --- a/libraries/MTConnect.NET-Common/Assets/AssetDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/AssetDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets { + /// + /// Description text for each property of Asset as defined by the MTConnect Standard. + /// public static class AssetDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/AssetValidationResult.cs b/libraries/MTConnect.NET-Common/Assets/AssetValidationResult.cs index cb92ed16a..d00983de2 100644 --- a/libraries/MTConnect.NET-Common/Assets/AssetValidationResult.cs +++ b/libraries/MTConnect.NET-Common/Assets/AssetValidationResult.cs @@ -3,13 +3,30 @@ namespace MTConnect.Assets { + /// + /// The outcome of validating an MTConnect Asset: whether it is valid and + /// an optional message describing the failure when it is not. + /// public struct AssetValidationResult { + /// + /// true when the asset passed validation. + /// public bool IsValid { get; set; } + /// + /// A message describing the validation failure, or null when + /// the asset is valid. + /// public string Message { get; set; } + /// + /// Initializes the result with the validity flag and an optional + /// failure message. + /// + /// Whether the asset is valid. + /// An optional failure message. public AssetValidationResult(bool isValid, string message = null) { IsValid = isValid; diff --git a/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ComponentConfigurationParametersAsset.cs b/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ComponentConfigurationParametersAsset.cs index 28dcd71a0..fb3681df0 100644 --- a/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ComponentConfigurationParametersAsset.cs +++ b/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ComponentConfigurationParametersAsset.cs @@ -8,9 +8,15 @@ namespace MTConnect.Assets.ComponentConfigurationParameters { public partial class ComponentConfigurationParametersAsset { + /// + /// The fixed Asset type identifier ("ComponentConfigurationParameters") written to the Type attribute and used to recognize this asset during deserialization. + /// public const string TypeId = "ComponentConfigurationParameters"; + /// + /// Initializes a new ComponentConfigurationParametersAsset, stamping the Asset Type with . + /// public ComponentConfigurationParametersAsset() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ComponentConfigurationParametersAsset.g.cs b/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ComponentConfigurationParametersAsset.g.cs index 286f75076..7de1b4777 100644 --- a/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ComponentConfigurationParametersAsset.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ComponentConfigurationParametersAsset.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.ComponentConfigurationParameters /// public partial class ComponentConfigurationParametersAsset : Asset, IComponentConfigurationParametersAsset { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Set of ParameterSets that govern the functionality of the related Component."; diff --git a/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ComponentConfigurationParametersAssetDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ComponentConfigurationParametersAssetDescriptions.g.cs index ae729fee1..2f33da761 100644 --- a/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ComponentConfigurationParametersAssetDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ComponentConfigurationParametersAssetDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.ComponentConfigurationParameters { + /// + /// Description text for each property of ComponentConfigurationParametersAsset as defined by the MTConnect Standard. + /// public static class ComponentConfigurationParametersAssetDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/Parameter.g.cs b/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/Parameter.g.cs index 88962501a..a628a796f 100644 --- a/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/Parameter.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/Parameter.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.ComponentConfigurationParameters /// public class Parameter : IParameter { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Property that determines the characteristic or behavior of an entity."; @@ -17,32 +20,32 @@ public class Parameter : IParameter /// Internal identifier, register, or address. /// public string Identifier { get; set; } - + /// /// Maximum allowed value. /// public double? Maximum { get; set; } - + /// /// Minimal allowed value. /// public double? Minimum { get; set; } - + /// /// Descriptive name. /// public string Name { get; set; } - + /// /// Nominal value. /// public double? Nominal { get; set; } - + /// /// Engineering units.units **SHOULD** be SI or MTConnect Units. /// public string Units { get; set; } - + /// /// Configured value. /// diff --git a/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ParameterDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ParameterDescriptions.g.cs index 189f70aaf..f4ddeabe9 100644 --- a/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ParameterDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ParameterDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.ComponentConfigurationParameters { + /// + /// Description text for each property of Parameter as defined by the MTConnect Standard. + /// public static class ParameterDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ParameterSet.g.cs b/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ParameterSet.g.cs index 33206e622..f5f988461 100644 --- a/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ParameterSet.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ParameterSet.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.ComponentConfigurationParameters /// public class ParameterSet : IParameterSet { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Set of Parameters."; @@ -17,7 +20,7 @@ public class ParameterSet : IParameterSet /// Name of the parameter set if more than one exists. /// public string Name { get; set; } - + /// /// Property that determines the characteristic or behavior of an entity. /// diff --git a/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ParameterSetDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ParameterSetDescriptions.g.cs index c707d8e84..826bfe241 100644 --- a/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ParameterSetDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/ComponentConfigurationParameters/ParameterSetDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.ComponentConfigurationParameters { + /// + /// Description text for each property of ParameterSet as defined by the MTConnect Standard. + /// public static class ParameterSetDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CountDirectionType.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CountDirectionType.g.cs index 7792eb987..ad9086892 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CountDirectionType.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CountDirectionType.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// CountDirectionType controlled vocabulary as defined by the MTConnect Standard. + /// public enum CountDirectionType { /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CountDirectionTypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CountDirectionTypeDescriptions.g.cs index 46209664c..724f3c275 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CountDirectionTypeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CountDirectionTypeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class CountDirectionTypeDescriptions { /// @@ -16,6 +19,9 @@ public static class CountDirectionTypeDescriptions public const string UP = "Tool life counts up from zero to the maximum."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(CountDirectionType value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CutterStatusType.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CutterStatusType.g.cs index 73972bb4a..b0486bc36 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CutterStatusType.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CutterStatusType.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// CutterStatusType controlled vocabulary as defined by the MTConnect Standard. + /// public enum CutterStatusType { /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CutterStatusTypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CutterStatusTypeDescriptions.g.cs index a79f1c232..5ba77a3dd 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CutterStatusTypeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CutterStatusTypeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class CutterStatusTypeDescriptions { /// @@ -66,6 +69,9 @@ public static class CutterStatusTypeDescriptions public const string USED = "Tool is in process and has remaining tool life."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(CutterStatusType value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingItem.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingItem.cs index 227be46e0..ed3343d5a 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingItem.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingItem.cs @@ -7,6 +7,9 @@ namespace MTConnect.Assets.CuttingTools { public partial class CuttingItem { + /// + /// Initializes a new CuttingItem with empty cutter-status and measurement collections. + /// public CuttingItem() { CutterStatus = new List(); @@ -14,6 +17,9 @@ public CuttingItem() } + /// + /// Returns a copy of this cutting item with its measurements rebound to their concrete tooling-measurement subtypes so they serialize with the correct element name. + /// public ICuttingItem Process() { var cuttingItem = new CuttingItem(); @@ -41,6 +47,10 @@ public ICuttingItem Process() return cuttingItem; } + /// + /// Computes a SHA-1 content hash over the cutting item's scalar properties for change detection; returns null for a null item. + /// + /// The cutting item to hash. public static string GenerateHash(ICuttingItem cuttingItem) { if (cuttingItem != null) diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingItem.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingItem.g.cs index f68896d19..575d797f4 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingItem.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingItem.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.CuttingTools /// public partial class CuttingItem : ICuttingItem { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Part of of the tool that physically removes the material from the workpiece by shear deformation."; @@ -17,47 +20,47 @@ public partial class CuttingItem : ICuttingItem /// Status of the cutting tool. /// public System.Collections.Generic.IEnumerable CutterStatus { get; set; } - + /// /// Free-form description of the cutting item. /// public string Description { get; set; } - + /// /// Material composition for this cutting item. /// public string Grade { get; set; } - + /// /// Number or numbers representing the individual cutting item or items on the tool.Indices **SHOULD** start numbering with the inserts or CuttingItem furthest from the gauge line and increasing in value as the items get closer to the gauge line. Items at the same distance **MAY** be arbitrarily numbered.> Note: In XML, the representation **MUST** be a single number ('1') or a comma separated set of individual elements ('1,2,3,4'), or as a inclusive range of values as in ('1-10') or any combination of ranges and numbers as in '1-4,6-10,22'. There **MUST NOT** be spaces or non-integer values in the text representation. /// public string Indices { get; set; } - + /// /// Manufacturer identifier of this cutting item. /// public string ItemId { get; set; } - + /// /// The tool life measured in tool wear. /// public System.Collections.Generic.IEnumerable ItemLife { get; set; } - + /// /// Free form description of the location on the cutting tool.Locus **MAY** be any free form string, but **SHOULD** adhere to the following rules:* The location numbering **SHOULD** start at the furthest CuttingItem and work it’s way back to the CuttingItem closest to the gauge line.* Flutes **SHOULD** be identified as such using the word `FLUTE`:. For example: `FLUTE`: 1, `INSERT`: 2 - would indicate the first flute and the second furthest insert from the end of the tool on that flute.* Other designations such as `CARTRIDGE` **MAY** be included, but should be identified using upper case and followed by a colon (:). /// public string Locus { get; set; } - + /// /// Manufacturers of the cutting item.This will reference the tool item and adaptive items specifically. The cutting itemsmanufacturers’ will be a property of CuttingItem.> Note: In XML, the representation **MUST** be a comma(,) delimited list of manufacturer names. See CuttingItem Schema Diagrams. /// public System.Collections.Generic.IEnumerable Manufacturers { get; set; } - + /// /// A collection of measurements relating to this cutting item. /// public System.Collections.Generic.IEnumerable Measurements { get; set; } - + /// /// Tool group this item is assigned in the part program. /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingItemDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingItemDescriptions.g.cs index 7a22ed642..30a655c7b 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingItemDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingItemDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// Description text for each property of CuttingItem as defined by the MTConnect Standard. + /// public static class CuttingItemDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolArchetypeAsset.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolArchetypeAsset.g.cs index 44661893e..d155fb251 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolArchetypeAsset.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolArchetypeAsset.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.CuttingTools /// public partial class CuttingToolArchetypeAsset : Asset, ICuttingToolArchetypeAsset { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Asset that describes the static cutting tool geometries and nominal values as one would expect from a tool catalog."; @@ -17,17 +20,17 @@ public partial class CuttingToolArchetypeAsset : Asset, ICuttingToolArchetypeAss /// Detailed structure of the cutting tool which is static during its lifecycle. ISO 13399. /// public MTConnect.Assets.CuttingTools.ICuttingToolDefinition CuttingToolDefinition { get; set; } - + /// /// Data regarding the application or use of the tool.This data is provided by various pieces of equipment (i.e. machine tool, presetter) and statistical process control applications. Life cycle data will not remain static, but will change periodically when a tool is used or measured. /// public MTConnect.Assets.CuttingTools.ICuttingToolLifeCycle CuttingToolLifeCycle { get; set; } - + /// /// Unique identifier for this assembly. /// public string SerialNumber { get; set; } - + /// /// Identifier for a class of cutting tools. /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolArchetypeAssetDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolArchetypeAssetDescriptions.g.cs index 7fe3d0508..8573d3f28 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolArchetypeAssetDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolArchetypeAssetDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// Description text for each property of CuttingToolArchetypeAsset as defined by the MTConnect Standard. + /// public static class CuttingToolArchetypeAssetDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolArchetypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolArchetypeDescriptions.g.cs deleted file mode 100644 index 3b16f80c5..000000000 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolArchetypeDescriptions.g.cs +++ /dev/null @@ -1,33 +0,0 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. -// TrakHound Inc. licenses this file to you under the MIT license. - -namespace MTConnect.Assets.CuttingTools -{ - public static class CuttingToolArchetypeDescriptions - { - /// - /// Detailed structure of the cutting tool which is static during its lifecycle. ISO 13399. - /// - public const string CuttingToolDefinition = "Detailed structure of the cutting tool which is static during its lifecycle. ISO 13399."; - - /// - /// Data regarding the application or use of the tool.This data is provided by various pieces of equipment (i.e. machine tool, presetter) and statistical process control applications. Life cycle data will not remain static, but will change periodically when a tool is used or measured. - /// - public const string CuttingToolLifeCycle = "Data regarding the application or use of the tool.This data is provided by various pieces of equipment (i.e. machine tool, presetter) and statistical process control applications. Life cycle data will not remain static, but will change periodically when a tool is used or measured."; - - /// - /// Manufacturers of the cutting tool.This will reference the tool item and adaptive items specifically. The cutting itemsmanufacturers’ will be a property of CuttingItem.> Note: In XML, the representation will be a comma(,) delimited list of manufacturer names. See CuttingTool Schema Diagrams. - /// - public const string Manufacturers = "Manufacturers of the cutting tool.This will reference the tool item and adaptive items specifically. The cutting itemsmanufacturers’ will be a property of CuttingItem.> Note: In XML, the representation will be a comma(,) delimited list of manufacturer names. See CuttingTool Schema Diagrams."; - - /// - /// Unique identifier for this assembly. - /// - public const string SerialNumber = "Unique identifier for this assembly."; - - /// - /// Identifier for a class of cutting tools. - /// - public const string ToolId = "Identifier for a class of cutting tools."; - } -} \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolArchetypeReference.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolArchetypeReference.g.cs index 08060a327..2be636e5a 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolArchetypeReference.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolArchetypeReference.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.CuttingTools /// public class CuttingToolArchetypeReference : ICuttingToolArchetypeReference { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "AssetId and/or the URL of the data source of CuttingToolArchetype."; @@ -17,7 +20,7 @@ public class CuttingToolArchetypeReference : ICuttingToolArchetypeReference /// URL of the CuttingToolArchetype information model. /// public string Source { get; set; } - + /// /// `assetId` of the related CuttingToolArchetype. /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolArchetypeReferenceDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolArchetypeReferenceDescriptions.g.cs index 104ea631c..394e99672 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolArchetypeReferenceDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolArchetypeReferenceDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// Description text for each property of CuttingToolArchetypeReference as defined by the MTConnect Standard. + /// public static class CuttingToolArchetypeReferenceDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolAsset.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolAsset.cs index 1044291bb..ee5730ca6 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolAsset.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolAsset.cs @@ -8,9 +8,15 @@ namespace MTConnect.Assets.CuttingTools { public partial class CuttingToolAsset { + /// + /// The fixed Asset type identifier ("CuttingTool") written to the Type attribute and used to recognize this asset during deserialization. + /// public const string TypeId = "CuttingTool"; + /// + /// Initializes a new CuttingToolAsset, stamping the Asset Type with and allocating an empty life-cycle container. + /// public CuttingToolAsset() { Type = TypeId; @@ -18,6 +24,10 @@ public CuttingToolAsset() } + /// + /// Produces a version-adjusted copy of the asset for inclusion in a response document: excluded entirely before 1.2, the device UUID is dropped at or before 1.3, the serial number defaults to the asset id when absent, and the life cycle is recursively processed. Returns null when the version predates 1.2. + /// + /// The MTConnect version the response document targets. protected override IAsset OnProcess(Version mtconnectVersion) { if (mtconnectVersion != null && mtconnectVersion >= MTConnectVersions.Version12) @@ -46,6 +56,10 @@ protected override IAsset OnProcess(Version mtconnectVersion) return null; } + /// + /// Validates that the required SerialNumber and ToolId are present, reporting the first one missing. + /// + /// The MTConnect version to validate against. public override AssetValidationResult IsValid(Version mtconnectVersion) { var message = ""; @@ -66,11 +80,20 @@ public override AssetValidationResult IsValid(Version mtconnectVersion) } + /// + /// Computes the content hash of this cutting tool asset; see . + /// + /// When true, the asset timestamp is folded into the hash. public override string GenerateHash(bool includeTimestamp = true) { return GenerateHash(this, includeTimestamp); } + /// + /// Computes a SHA-1 content hash combining the asset's scalar properties with the hash of its life cycle; when is false the timestamp and UUID are excluded so equality is independent of when and where the asset was reported. Returns null for a null asset. + /// + /// The cutting tool asset to hash. + /// When true, the asset timestamp is folded into the hash. public static string GenerateHash(CuttingToolAsset asset, bool includeTimestamp = true) { if (asset != null) diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolAsset.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolAsset.g.cs index 80c3f47d5..1b5bd6e63 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolAsset.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolAsset.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.CuttingTools /// public partial class CuttingToolAsset : Asset, ICuttingToolAsset { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Asset that physically removes the material from the workpiece by shear deformation."; @@ -17,22 +20,22 @@ public partial class CuttingToolAsset : Asset, ICuttingToolAsset /// AssetId and/or the URL of the data source of CuttingToolArchetype. /// public MTConnect.Assets.CuttingTools.ICuttingToolArchetypeReference CuttingToolArchetypeReference { get; set; } - + /// /// Detailed structure of the cutting tool which is static during its lifecycle. ISO 13399. /// public MTConnect.Assets.CuttingTools.ICuttingToolDefinition CuttingToolDefinition { get; set; } - + /// /// Data regarding the application or use of the tool.This data is provided by various pieces of equipment (i.e. machine tool, presetter) and statistical process control applications. Life cycle data will not remain static, but will change periodically when a tool is used or measured. /// public MTConnect.Assets.CuttingTools.ICuttingToolLifeCycle CuttingToolLifeCycle { get; set; } - + /// /// Unique identifier for this assembly. /// public string SerialNumber { get; set; } - + /// /// Identifier for a class of cutting tools. /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolAssetDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolAssetDescriptions.g.cs index f572e64d5..ed2288071 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolAssetDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolAssetDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// Description text for each property of CuttingToolAsset as defined by the MTConnect Standard. + /// public static class CuttingToolAssetDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolDefinition.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolDefinition.g.cs index d31c5a785..7c67aec2b 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolDefinition.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolDefinition.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.CuttingTools /// public class CuttingToolDefinition : ICuttingToolDefinition { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Detailed structure of the cutting tool which is static during its lifecycle. ISO 13399."; @@ -17,7 +20,7 @@ public class CuttingToolDefinition : ICuttingToolDefinition /// Identifies the expected representation of the enclosed data. /// public MTConnect.Assets.CuttingTools.FormatType Format { get; set; } - + /// /// Format. /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolDefinitionDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolDefinitionDescriptions.g.cs index 5c8a91aae..8d8d151bb 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolDefinitionDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolDefinitionDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// Description text for each property of CuttingToolDefinition as defined by the MTConnect Standard. + /// public static class CuttingToolDefinitionDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolLifeCycle.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolLifeCycle.cs index cbf7ae7f0..5236d81a0 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolLifeCycle.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolLifeCycle.cs @@ -8,6 +8,9 @@ namespace MTConnect.Assets.CuttingTools { public partial class CuttingToolLifeCycle { + /// + /// Initializes a new CuttingToolLifeCycle with empty cutter-status, measurement, and cutting-item collections. + /// public CuttingToolLifeCycle() { CutterStatus = new List(); @@ -16,6 +19,9 @@ public CuttingToolLifeCycle() } + /// + /// Returns a copy of this life cycle with each cutting item processed and each measurement rebound to its concrete tooling-measurement subtype so they serialize correctly. + /// public ICuttingToolLifeCycle Process() { var lifeCycle = new CuttingToolLifeCycle(); @@ -57,6 +63,10 @@ public ICuttingToolLifeCycle Process() return lifeCycle; } + /// + /// Computes a SHA-1 content hash over the life cycle's scalar properties combined with the cutter statuses and the hashes of each contained cutting item and tool-life entry; returns null for a null life cycle. + /// + /// The life cycle to hash. public static string GenerateHash(ICuttingToolLifeCycle cuttingToolLifeCycle) { if (cuttingToolLifeCycle != null) diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolLifeCycle.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolLifeCycle.g.cs index 96c632cfa..6610a3e69 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolLifeCycle.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolLifeCycle.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.CuttingTools /// public partial class CuttingToolLifeCycle : ICuttingToolLifeCycle { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Data regarding the application or use of the tool.This data is provided by various pieces of equipment (i.e. machine tool, presetter) and statistical process control applications. Life cycle data will not remain static, but will change periodically when a tool is used or measured."; @@ -17,52 +20,52 @@ public partial class CuttingToolLifeCycle : ICuttingToolLifeCycle /// Identifier for the capability to connect any component of the cutting tool together, except Assembly Items, on the machine side. Code: `CCMS` /// public string ConnectionCodeMachineSide { get; set; } - + /// /// Status of the cutting tool. /// public System.Collections.Generic.IEnumerable CutterStatus { get; set; } - + /// /// Part of of the tool that physically removes the material from the workpiece by shear deformation. /// public System.Collections.Generic.IEnumerable CuttingItems { get; set; } - + /// /// Location of the pot or spindle the cutting tool currently resides in.positiveOverlap is provided, the tool reserves additional locations on either side, otherwise if they are not given, no additional locations are required for this tool.positiveOverlap of 1, the first pot **MAY** be occupied as well. /// public MTConnect.Assets.CuttingTools.ILocation Location { get; set; } - + /// /// Constrained scalar value associated with a cutting tool. /// public System.Collections.Generic.IEnumerable Measurements { get; set; } - + /// /// Constrained process feed rate for the tool in mm/s.minimum **MUST** be specified. /// public MTConnect.Assets.CuttingTools.IProcessFeedRate ProcessFeedRate { get; set; } - + /// /// Constrained process spindle speed for the tool in revolutions/minute.minimum **MUST** be specified. /// public MTConnect.Assets.CuttingTools.IProcessSpindleSpeed ProcessSpindleSpeed { get; set; } - + /// /// Tool group this tool is assigned in the part program. /// public string ProgramToolGroup { get; set; } - + /// /// Number of the tool as referenced in the part program. /// public string ProgramToolNumber { get; set; } - + /// /// Number of times the cutter has been reconditioned. /// public MTConnect.Assets.CuttingTools.IReconditionCount ReconditionCount { get; set; } - + /// /// Cutting tool life as related to the assembly. /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolLifeCycleDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolLifeCycleDescriptions.g.cs index d4ff81a09..275a543ed 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolLifeCycleDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/CuttingToolLifeCycleDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// Description text for each property of CuttingToolLifeCycle as defined by the MTConnect Standard. + /// public static class CuttingToolLifeCycleDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/FormatType.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/FormatType.g.cs index e061aa3e1..cdef8ff12 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/FormatType.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/FormatType.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// FormatType controlled vocabulary as defined by the MTConnect Standard. + /// public enum FormatType { /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/FormatTypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/FormatTypeDescriptions.g.cs index 92bc4cea6..ed64e7c9d 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/FormatTypeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/FormatTypeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class FormatTypeDescriptions { /// @@ -26,6 +29,9 @@ public static class FormatTypeDescriptions public const string XML = "Default value for the definition. The content will be an XML document."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(FormatType value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ICuttingItem.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ICuttingItem.cs index 494441d0d..4f0340dcb 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ICuttingItem.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ICuttingItem.cs @@ -8,6 +8,9 @@ namespace MTConnect.Assets.CuttingTools /// public partial interface ICuttingItem { + /// + /// Returns a processed copy of this cutting item with its measurements rebound to their concrete tooling-measurement subtypes for serialization. + /// ICuttingItem Process(); } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ICuttingToolLifeCycle.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ICuttingToolLifeCycle.cs index d2f951df3..d545b8dbb 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ICuttingToolLifeCycle.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ICuttingToolLifeCycle.cs @@ -8,6 +8,9 @@ namespace MTConnect.Assets.CuttingTools /// public partial interface ICuttingToolLifeCycle { + /// + /// Returns a processed copy of this life cycle with its cutting items processed and measurements rebound to their concrete tooling-measurement subtypes for serialization. + /// ICuttingToolLifeCycle Process(); } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/IMeasurement.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/IMeasurement.cs index c94b8c773..1e68ab90f 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/IMeasurement.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/IMeasurement.cs @@ -8,6 +8,9 @@ namespace MTConnect.Assets.CuttingTools /// public partial interface IMeasurement { + /// + /// The measurement type name (e.g. a tooling measurement code), which selects the concrete measurement subtype and its element name in serialized documents. + /// string Type { get; set; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/IMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/IMeasurement.g.cs index 357a7ddeb..bbb622f2d 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/IMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/IMeasurement.g.cs @@ -4,15 +4,10 @@ namespace MTConnect.Assets.CuttingTools { /// - /// Constrained scalar value associated with a cutting tool. + /// Constrained scalar value associated with an Asset /// public partial interface IMeasurement { - ///// - ///// Shop specific code for the measurement. ISO 13399 codes **MAY** be used for these codes as well. code values. - ///// - //string Code { get; } - /// /// Maximum value for the measurement. /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ItemLife.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ItemLife.g.cs index 3bec14c89..2dc1f81f6 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ItemLife.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ItemLife.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.CuttingTools /// public class ItemLife : IItemLife { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Life of a CuttingItem."; @@ -17,27 +20,27 @@ public class ItemLife : IItemLife /// Indicates if the item life counts from zero to maximum or maximum to zero. /// public MTConnect.Assets.CuttingTools.CountDirectionType CountDirection { get; set; } - + /// /// Initial life of the item when it is new. /// public double? Initial { get; set; } - + /// /// End of life limit for this item. /// public double? Limit { get; set; } - + /// /// Type of item life being accumulated. /// public MTConnect.Assets.CuttingTools.ToolLifeType Type { get; set; } - + /// /// Value of ItemLife. /// public double Value { get; set; } - + /// /// Point at which a item life warning will be raised. /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ItemLifeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ItemLifeDescriptions.g.cs index 71d53d6ac..0614bd593 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ItemLifeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ItemLifeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// Description text for each property of ItemLife as defined by the MTConnect Standard. + /// public static class ItemLifeDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Location.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Location.g.cs index d10667feb..97f1ba637 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Location.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Location.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.CuttingTools /// public class Location : ILocation { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Location of the pot or spindle the cutting tool currently resides in.positiveOverlap is provided, the tool reserves additional locations on either side, otherwise if they are not given, no additional locations are required for this tool.positiveOverlap of 1, the first pot **MAY** be occupied as well."; @@ -17,42 +20,42 @@ public class Location : ILocation /// Automatic tool changer associated with a tool. /// public string AutomaticToolChanger { get; set; } - + /// /// Number of locations at lower index values from this location. /// public int? NegativeOverlap { get; set; } - + /// /// Number of locations at higher index value from this location. /// public int? PositiveOverlap { get; set; } - + /// /// Tool bar associated with a tool. /// public string ToolBar { get; set; } - + /// /// Tool magazine associated with a tool. /// public string ToolMagazine { get; set; } - + /// /// Tool rack associated with a tool. /// public string ToolRack { get; set; } - + /// /// Turret associated with a tool. /// public string Turret { get; set; } - + /// /// Type of location being identified. value**MUST** be a numeric value. /// public MTConnect.Assets.CuttingTools.LocationType Type { get; set; } - + /// /// /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/LocationDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/LocationDescriptions.g.cs index 0ec1d1f7a..f59a994fd 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/LocationDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/LocationDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// Description text for each property of Location as defined by the MTConnect Standard. + /// public static class LocationDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/LocationType.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/LocationType.g.cs index 6e20b2ce9..7f6d9036c 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/LocationType.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/LocationType.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// LocationType controlled vocabulary as defined by the MTConnect Standard. + /// public enum LocationType { /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/LocationTypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/LocationTypeDescriptions.g.cs index 5a083554a..8d63e5b2e 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/LocationTypeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/LocationTypeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class LocationTypeDescriptions { /// @@ -56,6 +59,9 @@ public static class LocationTypeDescriptions public const string TRANSFER_POT = "Location for a tool awaiting transfer from a tool magazine to spindle or a turret."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(LocationType value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurement.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurement.cs index 7bc7f81a1..a1b961b26 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurement.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurement.cs @@ -7,11 +7,21 @@ namespace MTConnect.Assets.CuttingTools { public partial class Measurement { + /// + /// The measurement type name, which selects the concrete measurement subtype and its element name in serialized documents. + /// public string Type { get; set; } + /// + /// Initializes an empty measurement, typically for deserialization. + /// public Measurement() { } + /// + /// Initializes a measurement by copying the value, nominal, minimum, maximum, significant digits, and native units from an existing measurement; a null source leaves the fields default. + /// + /// The measurement to copy from. public Measurement(IMeasurement measurement) { if (measurement != null) diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurement.g.cs index 7882a7aec..066116be2 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurement.g.cs @@ -1,53 +1,51 @@ // Copyright (c) 2024 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. -// MTConnect SysML v2.3 : UML ID = EAID_C09F377D_8946_421b_B746_E23C01D97EAC +// MTConnect SysML v2.3 : UML ID = _2024x_68e0225_1727793846441_986747_23754 namespace MTConnect.Assets.CuttingTools { /// - /// Constrained scalar value associated with a cutting tool. + /// Constrained scalar value associated with an Asset /// public partial class Measurement : IMeasurement { - public const string DescriptionText = "Constrained scalar value associated with a cutting tool."; - - /// - /// Shop specific code for the measurement. ISO 13399 codes **MAY** be used for these codes as well. code values. + /// The description of this type as defined by the MTConnect Standard. /// - public string Code { get; set; } - + public const string DescriptionText = "Constrained scalar value associated with an Asset"; + + /// /// Maximum value for the measurement. /// public double? Maximum { get; set; } - + /// /// Minimum value for the measurement. /// public double? Minimum { get; set; } - + /// /// NativeUnits. /// public string NativeUnits { get; set; } - + /// /// As advertised value for the measurement. /// public double? Nominal { get; set; } - + /// /// Number of significant digits in the reported value. /// public int? SignificantDigits { get; set; } - + /// /// Units. /// public string Units { get; set; } - + /// /// /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/MeasurementDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/MeasurementDescriptions.g.cs index 7b307d696..6b6e729fe 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/MeasurementDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/MeasurementDescriptions.g.cs @@ -3,13 +3,11 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// Description text for each property of Measurement as defined by the MTConnect Standard. + /// public static class MeasurementDescriptions { - /// - /// Shop specific code for the measurement. ISO 13399 codes **MAY** be used for these codes as well. code values. - /// - public const string Code = "Shop specific code for the measurement. ISO 13399 codes **MAY** be used for these codes as well. code values."; - /// /// Maximum value for the measurement. /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/BodyDiameterMaxMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/BodyDiameterMaxMeasurement.g.cs index 72e395350..105e877c4 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/BodyDiameterMaxMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/BodyDiameterMaxMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class BodyDiameterMaxMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "BodyDiameterMax"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "BDX"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public BodyDiameterMaxMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public BodyDiameterMaxMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public BodyDiameterMaxMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public BodyDiameterMaxMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public BodyDiameterMaxMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/BodyLengthMaxMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/BodyLengthMaxMeasurement.g.cs index 80b7fb967..2f9bce490 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/BodyLengthMaxMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/BodyLengthMaxMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class BodyLengthMaxMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "BodyLengthMax"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "LBX"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public BodyLengthMaxMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public BodyLengthMaxMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public BodyLengthMaxMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public BodyLengthMaxMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public BodyLengthMaxMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ChamferFlatLengthMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ChamferFlatLengthMeasurement.g.cs index c0a9f58ea..89534ace4 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ChamferFlatLengthMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ChamferFlatLengthMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class ChamferFlatLengthMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "ChamferFlatLength"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "BCH"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public ChamferFlatLengthMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public ChamferFlatLengthMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public ChamferFlatLengthMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public ChamferFlatLengthMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public ChamferFlatLengthMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ChamferWidthMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ChamferWidthMeasurement.g.cs index 1b01e6a6b..f70f6e0c8 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ChamferWidthMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ChamferWidthMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class ChamferWidthMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "ChamferWidth"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "CHW"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public ChamferWidthMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public ChamferWidthMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public ChamferWidthMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public ChamferWidthMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public ChamferWidthMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/Code.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/Code.g.cs deleted file mode 100644 index a012ff8ab..000000000 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/Code.g.cs +++ /dev/null @@ -1,168 +0,0 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. -// TrakHound Inc. licenses this file to you under the MIT license. - -namespace MTConnect.Assets.CuttingTools.Measurements -{ - public enum Code - { - /// - /// Maximum engagement of the cutting edge or edges with the workpiece measured perpendicular to the feed motion. - /// - APMX, - - /// - /// Flat length of a chamfer. - /// - BCH, - - /// - /// Largest diameter of the body of a tool item. - /// - BDX, - - /// - /// Measure of the length of a wiper edge of a cutting item. - /// - BS, - - /// - /// Width of the chamfer. - /// - CHW, - - /// - /// Theoretical sharp point of the cutting tool from which the major functional dimensions are taken. - /// - CRP, - - /// - /// Maximum diameter of a circle on which the defined point Pk of each of the master inserts is located on a tool item. The normal of the machined peripheral surface points towards the axis of the cutting tool. - /// - DC, - - /// - /// Diameter of a circle on which the defined point Pk located on this cutting tool.The normal of the machined peripheral surface points towards the axis of the cutting tool. - /// - D_CX, - - /// - /// Dimension between two parallel tangents on the outside edge of a flange. - /// - DF, - - /// - /// Dimension of the diameter of a cylindrical portion of a tool item or an adaptive item that can participate in a connection. - /// - DMM, - - /// - /// Angle between the driving mechanism locator on a tool item and the main cutting edge. - /// - DRVA, - - /// - /// Dimension of the height of the shank. - /// - H, - - /// - /// Distance from the basal plane of the tool item to the cutting point. - /// - HF, - - /// - /// Diameter of a circle to which all edges of a equilateral and round regular insert are tangential. - /// - IC, - - /// - /// Angle between the tool cutting edge plane and the tool feed plane measured in a plane parallel the xy-plane. - /// - KAPR, - - /// - /// Theoretical length of the cutting edge of a cutting item over sharp corners. - /// - L, - - /// - /// Distance measured along the X axis from that point of the item closest to the workpiece, including the cutting item for a tool item but excluding a protruding locking mechanism for an adaptive item, to either the front of the flange on a flanged body or the beginning of the connection interface feature on the machine side for cylindrical or prismatic shanks. - /// - LBX, - - /// - /// Distance from the gauge plane or from the end of the shank to the furthest point on the tool, if a gauge plane does not exist, to the cutting reference point determined by the main function of the tool. The CuttingTool functional length will be the length of the entire tool, not a single cutting item. Each CuttingItem can have an independent FunctionalLength represented in its measurements. - /// - LF, - - /// - /// Distance from the gauge plane or from the end of the shank of the cutting tool, if a gauge plane does not exist, to the cutting reference point determined by the main function of the tool. This measurement will be with reference to the cutting tool and **MUST NOT** exist without a cutting tool. - /// - L_FX, - - /// - /// Dimension from the yz-plane to the furthest point of the tool item or adaptive item measured in the -X direction. - /// - LPR, - - /// - /// Dimension of the length of the shank. - /// - LS, - - /// - /// Maximum length of a cutting tool that can be used in a particular cutting operation including the non-cutting portions of the tool. - /// - LUX, - - /// - /// Angle of the tool with respect to the workpiece for a given process. The value is application specific. - /// - N_A, - - /// - /// Largest length dimension of the cutting tool including the master insert where applicable. - /// - OAL, - - /// - /// Angle between the tool cutting edge plane and a plane perpendicular to the tool feed plane measured in a plane parallel the xy-plane. - /// - PSIR, - - /// - /// Nominal radius of a rounded corner measured in the X Y-plane. - /// - RE, - - /// - /// Length of a portion of a stepped tool that is related to a corresponding cutting diameter measured from the cutting reference point of that cutting diameter to the point on the next cutting edge at which the diameter starts to change. - /// - S_D_LX, - - /// - /// Angle between the major cutting edge and the same cutting edge rotated by 180 degrees about the tool axis. - /// - SIG, - - /// - /// Angle between a major edge on a step of a stepped tool and the same cutting edge rotated 180 degrees about its tool axis. - /// - S_T_AX, - - /// - /// Insert width when an inscribed circle diameter is not practical. - /// - WONE, - - /// - /// Distance between the cutting reference point and the rear backing surface of a turning tool or the axis of a boring bar. - /// - WF, - - /// - /// Total weight of the cutting tool in grams. The force exerted by the mass of the cutting tool. - /// - WT - } -} \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CodeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CodeDescriptions.g.cs deleted file mode 100644 index 58028a25d..000000000 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CodeDescriptions.g.cs +++ /dev/null @@ -1,210 +0,0 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. -// TrakHound Inc. licenses this file to you under the MIT license. - -namespace MTConnect.Assets.CuttingTools.Measurements -{ - public static class CodeDescriptions - { - /// - /// Maximum engagement of the cutting edge or edges with the workpiece measured perpendicular to the feed motion. - /// - public const string APMX = "Maximum engagement of the cutting edge or edges with the workpiece measured perpendicular to the feed motion."; - - /// - /// Flat length of a chamfer. - /// - public const string BCH = "Flat length of a chamfer."; - - /// - /// Largest diameter of the body of a tool item. - /// - public const string BDX = "Largest diameter of the body of a tool item."; - - /// - /// Measure of the length of a wiper edge of a cutting item. - /// - public const string BS = "Measure of the length of a wiper edge of a cutting item."; - - /// - /// Width of the chamfer. - /// - public const string CHW = "Width of the chamfer."; - - /// - /// Theoretical sharp point of the cutting tool from which the major functional dimensions are taken. - /// - public const string CRP = "Theoretical sharp point of the cutting tool from which the major functional dimensions are taken."; - - /// - /// Maximum diameter of a circle on which the defined point Pk of each of the master inserts is located on a tool item. The normal of the machined peripheral surface points towards the axis of the cutting tool. - /// - public const string DC = "Maximum diameter of a circle on which the defined point Pk of each of the master inserts is located on a tool item. The normal of the machined peripheral surface points towards the axis of the cutting tool."; - - /// - /// Diameter of a circle on which the defined point Pk located on this cutting tool.The normal of the machined peripheral surface points towards the axis of the cutting tool. - /// - public const string D_CX = "Diameter of a circle on which the defined point Pk located on this cutting tool.The normal of the machined peripheral surface points towards the axis of the cutting tool."; - - /// - /// Dimension between two parallel tangents on the outside edge of a flange. - /// - public const string DF = "Dimension between two parallel tangents on the outside edge of a flange."; - - /// - /// Dimension of the diameter of a cylindrical portion of a tool item or an adaptive item that can participate in a connection. - /// - public const string DMM = "Dimension of the diameter of a cylindrical portion of a tool item or an adaptive item that can participate in a connection."; - - /// - /// Angle between the driving mechanism locator on a tool item and the main cutting edge. - /// - public const string DRVA = "Angle between the driving mechanism locator on a tool item and the main cutting edge."; - - /// - /// Dimension of the height of the shank. - /// - public const string H = "Dimension of the height of the shank."; - - /// - /// Distance from the basal plane of the tool item to the cutting point. - /// - public const string HF = "Distance from the basal plane of the tool item to the cutting point."; - - /// - /// Diameter of a circle to which all edges of a equilateral and round regular insert are tangential. - /// - public const string IC = "Diameter of a circle to which all edges of a equilateral and round regular insert are tangential."; - - /// - /// Angle between the tool cutting edge plane and the tool feed plane measured in a plane parallel the xy-plane. - /// - public const string KAPR = "Angle between the tool cutting edge plane and the tool feed plane measured in a plane parallel the xy-plane."; - - /// - /// Theoretical length of the cutting edge of a cutting item over sharp corners. - /// - public const string L = "Theoretical length of the cutting edge of a cutting item over sharp corners."; - - /// - /// Distance measured along the X axis from that point of the item closest to the workpiece, including the cutting item for a tool item but excluding a protruding locking mechanism for an adaptive item, to either the front of the flange on a flanged body or the beginning of the connection interface feature on the machine side for cylindrical or prismatic shanks. - /// - public const string LBX = "Distance measured along the X axis from that point of the item closest to the workpiece, including the cutting item for a tool item but excluding a protruding locking mechanism for an adaptive item, to either the front of the flange on a flanged body or the beginning of the connection interface feature on the machine side for cylindrical or prismatic shanks."; - - /// - /// Distance from the gauge plane or from the end of the shank to the furthest point on the tool, if a gauge plane does not exist, to the cutting reference point determined by the main function of the tool. The CuttingTool functional length will be the length of the entire tool, not a single cutting item. Each CuttingItem can have an independent FunctionalLength represented in its measurements. - /// - public const string LF = "Distance from the gauge plane or from the end of the shank to the furthest point on the tool, if a gauge plane does not exist, to the cutting reference point determined by the main function of the tool. The CuttingTool functional length will be the length of the entire tool, not a single cutting item. Each CuttingItem can have an independent FunctionalLength represented in its measurements."; - - /// - /// Distance from the gauge plane or from the end of the shank of the cutting tool, if a gauge plane does not exist, to the cutting reference point determined by the main function of the tool. This measurement will be with reference to the cutting tool and **MUST NOT** exist without a cutting tool. - /// - public const string L_FX = "Distance from the gauge plane or from the end of the shank of the cutting tool, if a gauge plane does not exist, to the cutting reference point determined by the main function of the tool. This measurement will be with reference to the cutting tool and **MUST NOT** exist without a cutting tool."; - - /// - /// Dimension from the yz-plane to the furthest point of the tool item or adaptive item measured in the -X direction. - /// - public const string LPR = "Dimension from the yz-plane to the furthest point of the tool item or adaptive item measured in the -X direction."; - - /// - /// Dimension of the length of the shank. - /// - public const string LS = "Dimension of the length of the shank."; - - /// - /// Maximum length of a cutting tool that can be used in a particular cutting operation including the non-cutting portions of the tool. - /// - public const string LUX = "Maximum length of a cutting tool that can be used in a particular cutting operation including the non-cutting portions of the tool."; - - /// - /// Angle of the tool with respect to the workpiece for a given process. The value is application specific. - /// - public const string N_A = "Angle of the tool with respect to the workpiece for a given process. The value is application specific."; - - /// - /// Largest length dimension of the cutting tool including the master insert where applicable. - /// - public const string OAL = "Largest length dimension of the cutting tool including the master insert where applicable."; - - /// - /// Angle between the tool cutting edge plane and a plane perpendicular to the tool feed plane measured in a plane parallel the xy-plane. - /// - public const string PSIR = "Angle between the tool cutting edge plane and a plane perpendicular to the tool feed plane measured in a plane parallel the xy-plane."; - - /// - /// Nominal radius of a rounded corner measured in the X Y-plane. - /// - public const string RE = "Nominal radius of a rounded corner measured in the X Y-plane."; - - /// - /// Length of a portion of a stepped tool that is related to a corresponding cutting diameter measured from the cutting reference point of that cutting diameter to the point on the next cutting edge at which the diameter starts to change. - /// - public const string S_D_LX = "Length of a portion of a stepped tool that is related to a corresponding cutting diameter measured from the cutting reference point of that cutting diameter to the point on the next cutting edge at which the diameter starts to change."; - - /// - /// Angle between the major cutting edge and the same cutting edge rotated by 180 degrees about the tool axis. - /// - public const string SIG = "Angle between the major cutting edge and the same cutting edge rotated by 180 degrees about the tool axis."; - - /// - /// Angle between a major edge on a step of a stepped tool and the same cutting edge rotated 180 degrees about its tool axis. - /// - public const string S_T_AX = "Angle between a major edge on a step of a stepped tool and the same cutting edge rotated 180 degrees about its tool axis."; - - /// - /// Insert width when an inscribed circle diameter is not practical. - /// - public const string WONE = "Insert width when an inscribed circle diameter is not practical."; - - /// - /// Distance between the cutting reference point and the rear backing surface of a turning tool or the axis of a boring bar. - /// - public const string WF = "Distance between the cutting reference point and the rear backing surface of a turning tool or the axis of a boring bar."; - - /// - /// Total weight of the cutting tool in grams. The force exerted by the mass of the cutting tool. - /// - public const string WT = "Total weight of the cutting tool in grams. The force exerted by the mass of the cutting tool."; - - - public static string Get(Code value) - { - switch (value) - { - case Code.APMX: return "Maximum engagement of the cutting edge or edges with the workpiece measured perpendicular to the feed motion."; - case Code.BCH: return "Flat length of a chamfer."; - case Code.BDX: return "Largest diameter of the body of a tool item."; - case Code.BS: return "Measure of the length of a wiper edge of a cutting item."; - case Code.CHW: return "Width of the chamfer."; - case Code.CRP: return "Theoretical sharp point of the cutting tool from which the major functional dimensions are taken."; - case Code.DC: return "Maximum diameter of a circle on which the defined point Pk of each of the master inserts is located on a tool item. The normal of the machined peripheral surface points towards the axis of the cutting tool."; - case Code.D_CX: return "Diameter of a circle on which the defined point Pk located on this cutting tool.The normal of the machined peripheral surface points towards the axis of the cutting tool."; - case Code.DF: return "Dimension between two parallel tangents on the outside edge of a flange."; - case Code.DMM: return "Dimension of the diameter of a cylindrical portion of a tool item or an adaptive item that can participate in a connection."; - case Code.DRVA: return "Angle between the driving mechanism locator on a tool item and the main cutting edge."; - case Code.H: return "Dimension of the height of the shank."; - case Code.HF: return "Distance from the basal plane of the tool item to the cutting point."; - case Code.IC: return "Diameter of a circle to which all edges of a equilateral and round regular insert are tangential."; - case Code.KAPR: return "Angle between the tool cutting edge plane and the tool feed plane measured in a plane parallel the xy-plane."; - case Code.L: return "Theoretical length of the cutting edge of a cutting item over sharp corners."; - case Code.LBX: return "Distance measured along the X axis from that point of the item closest to the workpiece, including the cutting item for a tool item but excluding a protruding locking mechanism for an adaptive item, to either the front of the flange on a flanged body or the beginning of the connection interface feature on the machine side for cylindrical or prismatic shanks."; - case Code.LF: return "Distance from the gauge plane or from the end of the shank to the furthest point on the tool, if a gauge plane does not exist, to the cutting reference point determined by the main function of the tool. The CuttingTool functional length will be the length of the entire tool, not a single cutting item. Each CuttingItem can have an independent FunctionalLength represented in its measurements."; - case Code.L_FX: return "Distance from the gauge plane or from the end of the shank of the cutting tool, if a gauge plane does not exist, to the cutting reference point determined by the main function of the tool. This measurement will be with reference to the cutting tool and **MUST NOT** exist without a cutting tool."; - case Code.LPR: return "Dimension from the yz-plane to the furthest point of the tool item or adaptive item measured in the -X direction."; - case Code.LS: return "Dimension of the length of the shank."; - case Code.LUX: return "Maximum length of a cutting tool that can be used in a particular cutting operation including the non-cutting portions of the tool."; - case Code.N_A: return "Angle of the tool with respect to the workpiece for a given process. The value is application specific."; - case Code.OAL: return "Largest length dimension of the cutting tool including the master insert where applicable."; - case Code.PSIR: return "Angle between the tool cutting edge plane and a plane perpendicular to the tool feed plane measured in a plane parallel the xy-plane."; - case Code.RE: return "Nominal radius of a rounded corner measured in the X Y-plane."; - case Code.S_D_LX: return "Length of a portion of a stepped tool that is related to a corresponding cutting diameter measured from the cutting reference point of that cutting diameter to the point on the next cutting edge at which the diameter starts to change."; - case Code.SIG: return "Angle between the major cutting edge and the same cutting edge rotated by 180 degrees about the tool axis."; - case Code.S_T_AX: return "Angle between a major edge on a step of a stepped tool and the same cutting edge rotated 180 degrees about its tool axis."; - case Code.WONE: return "Insert width when an inscribed circle diameter is not practical."; - case Code.WF: return "Distance between the cutting reference point and the rear backing surface of a turning tool or the axis of a boring bar."; - case Code.WT: return "Total weight of the cutting tool in grams. The force exerted by the mass of the cutting tool."; - } - - return null; - } - } -} \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CornerRadiusMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CornerRadiusMeasurement.g.cs index 80f978e92..1e5157f3b 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CornerRadiusMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CornerRadiusMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class CornerRadiusMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "CornerRadius"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "RE"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public CornerRadiusMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public CornerRadiusMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public CornerRadiusMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public CornerRadiusMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public CornerRadiusMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CuttingDiameterMaxMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CuttingDiameterMaxMeasurement.g.cs index e2d69697b..596958d45 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CuttingDiameterMaxMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CuttingDiameterMaxMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class CuttingDiameterMaxMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "CuttingDiameterMax"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "DC"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public CuttingDiameterMaxMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public CuttingDiameterMaxMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public CuttingDiameterMaxMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public CuttingDiameterMaxMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public CuttingDiameterMaxMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CuttingDiameterMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CuttingDiameterMeasurement.g.cs index d5ed8ba39..1f765dad6 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CuttingDiameterMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CuttingDiameterMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class CuttingDiameterMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "CuttingDiameter"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "DCx"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public CuttingDiameterMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public CuttingDiameterMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public CuttingDiameterMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public CuttingDiameterMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public CuttingDiameterMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CuttingEdgeLengthMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CuttingEdgeLengthMeasurement.g.cs index 85ec1d3ea..e2c468ca3 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CuttingEdgeLengthMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CuttingEdgeLengthMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class CuttingEdgeLengthMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "CuttingEdgeLength"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "L"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public CuttingEdgeLengthMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public CuttingEdgeLengthMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public CuttingEdgeLengthMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public CuttingEdgeLengthMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public CuttingEdgeLengthMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CuttingHeightMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CuttingHeightMeasurement.g.cs index f70c2a69c..a3a3638c5 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CuttingHeightMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CuttingHeightMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class CuttingHeightMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "CuttingHeight"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "HF"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public CuttingHeightMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public CuttingHeightMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public CuttingHeightMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public CuttingHeightMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public CuttingHeightMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CuttingReferencePointMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CuttingReferencePointMeasurement.g.cs index be894744e..33d40ea47 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CuttingReferencePointMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/CuttingReferencePointMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class CuttingReferencePointMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "CuttingReferencePoint"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "CRP"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public CuttingReferencePointMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public CuttingReferencePointMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public CuttingReferencePointMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public CuttingReferencePointMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public CuttingReferencePointMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/DepthOfCutMaxMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/DepthOfCutMaxMeasurement.g.cs index c05391db3..55f50da88 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/DepthOfCutMaxMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/DepthOfCutMaxMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class DepthOfCutMaxMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "DepthOfCutMax"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "APMX"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public DepthOfCutMaxMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public DepthOfCutMaxMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public DepthOfCutMaxMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public DepthOfCutMaxMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public DepthOfCutMaxMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/DriveAngleMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/DriveAngleMeasurement.g.cs index 2edd717ee..f5cf2bbf7 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/DriveAngleMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/DriveAngleMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class DriveAngleMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "DriveAngle"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "DRVA"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public DriveAngleMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public DriveAngleMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public DriveAngleMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public DriveAngleMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public DriveAngleMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/FlangeDiameterMaxMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/FlangeDiameterMaxMeasurement.g.cs index 24bcb6187..48948356a 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/FlangeDiameterMaxMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/FlangeDiameterMaxMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class FlangeDiameterMaxMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "FlangeDiameterMax"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "DF"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public FlangeDiameterMaxMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public FlangeDiameterMaxMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public FlangeDiameterMaxMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public FlangeDiameterMaxMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public FlangeDiameterMaxMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/FlangeDiameterMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/FlangeDiameterMeasurement.g.cs index ce7a20e43..39f28cc84 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/FlangeDiameterMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/FlangeDiameterMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class FlangeDiameterMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "FlangeDiameter"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "DF"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public FlangeDiameterMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public FlangeDiameterMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public FlangeDiameterMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public FlangeDiameterMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public FlangeDiameterMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/FunctionalLengthMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/FunctionalLengthMeasurement.g.cs index 5ffc6e580..d094f403d 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/FunctionalLengthMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/FunctionalLengthMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class FunctionalLengthMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "FunctionalLength"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "LF"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public FunctionalLengthMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public FunctionalLengthMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public FunctionalLengthMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public FunctionalLengthMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public FunctionalLengthMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/FunctionalWidthMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/FunctionalWidthMeasurement.g.cs index cd0a3a77b..e3e02e7df 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/FunctionalWidthMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/FunctionalWidthMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class FunctionalWidthMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "FunctionalWidth"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "WF"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public FunctionalWidthMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public FunctionalWidthMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public FunctionalWidthMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public FunctionalWidthMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public FunctionalWidthMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/IncribedCircleDiameterMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/IncribedCircleDiameterMeasurement.g.cs index 7db51f27e..64943a596 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/IncribedCircleDiameterMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/IncribedCircleDiameterMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class IncribedCircleDiameterMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "IncribedCircleDiameter"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "IC"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public IncribedCircleDiameterMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public IncribedCircleDiameterMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public IncribedCircleDiameterMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public IncribedCircleDiameterMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public IncribedCircleDiameterMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/InsertWidthMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/InsertWidthMeasurement.g.cs index 03d1a4aec..5f79f495c 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/InsertWidthMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/InsertWidthMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class InsertWidthMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "InsertWidth"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "W1"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public InsertWidthMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public InsertWidthMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public InsertWidthMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public InsertWidthMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public InsertWidthMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/MeasurementCode.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/MeasurementCode.g.cs index 30bd9d76f..11fcbfc55 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/MeasurementCode.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/MeasurementCode.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools.Measurements { + /// + /// MeasurementCode string constants as defined by the MTConnect Standard. + /// public static class MeasurementCode { /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/MeasurementCodeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/MeasurementCodeDescriptions.g.cs index c62ed660e..885cbd122 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/MeasurementCodeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/MeasurementCodeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools.Measurements { + /// + /// Description text for each string constant as defined by the MTConnect Standard. + /// public static class MeasurementCodeDescriptions { /// @@ -166,6 +169,9 @@ public static class MeasurementCodeDescriptions public const string WT = "Total weight of the cutting tool in grams. The force exerted by the mass of the cutting tool."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(string value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/OverallToolLengthMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/OverallToolLengthMeasurement.g.cs index 06ca01d0a..d8982e963 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/OverallToolLengthMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/OverallToolLengthMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class OverallToolLengthMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "OverallToolLength"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "OAL"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public OverallToolLengthMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public OverallToolLengthMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public OverallToolLengthMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public OverallToolLengthMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public OverallToolLengthMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/PointAngleMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/PointAngleMeasurement.g.cs index 20e705379..b435905fe 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/PointAngleMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/PointAngleMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class PointAngleMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "PointAngle"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "SIG"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public PointAngleMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public PointAngleMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public PointAngleMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public PointAngleMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public PointAngleMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ProtrudingLengthMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ProtrudingLengthMeasurement.g.cs index eaf67d9eb..a371da03e 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ProtrudingLengthMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ProtrudingLengthMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class ProtrudingLengthMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "ProtrudingLength"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "LPR"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public ProtrudingLengthMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public ProtrudingLengthMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public ProtrudingLengthMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public ProtrudingLengthMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public ProtrudingLengthMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ShankDiameterMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ShankDiameterMeasurement.g.cs index cebfeca49..edc6ad222 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ShankDiameterMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ShankDiameterMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class ShankDiameterMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "ShankDiameter"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "DMM"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public ShankDiameterMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public ShankDiameterMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public ShankDiameterMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public ShankDiameterMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public ShankDiameterMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ShankHeightMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ShankHeightMeasurement.g.cs index 997dbe6d8..fa7ea4bc5 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ShankHeightMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ShankHeightMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class ShankHeightMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "ShankHeight"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "H"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public ShankHeightMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public ShankHeightMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public ShankHeightMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public ShankHeightMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public ShankHeightMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ShankLengthMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ShankLengthMeasurement.g.cs index e912f58b5..f2d845bb8 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ShankLengthMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ShankLengthMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class ShankLengthMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "ShankLength"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "LS"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public ShankLengthMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public ShankLengthMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public ShankLengthMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public ShankLengthMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public ShankLengthMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/StepDiameterLengthMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/StepDiameterLengthMeasurement.g.cs index 1da587cbf..1e23b30b4 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/StepDiameterLengthMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/StepDiameterLengthMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class StepDiameterLengthMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "StepDiameterLength"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "SDLx"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public StepDiameterLengthMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public StepDiameterLengthMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public StepDiameterLengthMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public StepDiameterLengthMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public StepDiameterLengthMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/StepIncludedAngleMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/StepIncludedAngleMeasurement.g.cs index 3d734aa52..981c1d479 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/StepIncludedAngleMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/StepIncludedAngleMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class StepIncludedAngleMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "StepIncludedAngle"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "STAx"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public StepIncludedAngleMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public StepIncludedAngleMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public StepIncludedAngleMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public StepIncludedAngleMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public StepIncludedAngleMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ToolCuttingEdgeAngleMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ToolCuttingEdgeAngleMeasurement.g.cs index fa4af5daf..fdcbce892 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ToolCuttingEdgeAngleMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ToolCuttingEdgeAngleMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class ToolCuttingEdgeAngleMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "ToolCuttingEdgeAngle"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "KAPR"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public ToolCuttingEdgeAngleMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public ToolCuttingEdgeAngleMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public ToolCuttingEdgeAngleMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public ToolCuttingEdgeAngleMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public ToolCuttingEdgeAngleMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ToolLeadAngleMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ToolLeadAngleMeasurement.g.cs index 3e477fd1f..304296dac 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ToolLeadAngleMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ToolLeadAngleMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class ToolLeadAngleMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "ToolLeadAngle"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "PSIR"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public ToolLeadAngleMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public ToolLeadAngleMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public ToolLeadAngleMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public ToolLeadAngleMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public ToolLeadAngleMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ToolOrientationMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ToolOrientationMeasurement.g.cs index 5dd627ed8..d8c16c893 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ToolOrientationMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/ToolOrientationMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class ToolOrientationMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "ToolOrientation"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "N/A"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public ToolOrientationMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public ToolOrientationMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public ToolOrientationMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public ToolOrientationMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public ToolOrientationMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/UsableLengthMaxMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/UsableLengthMaxMeasurement.g.cs index 011144a6e..3ea92cc67 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/UsableLengthMaxMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/UsableLengthMaxMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class UsableLengthMaxMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "UsableLengthMax"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "LUX"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public UsableLengthMaxMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public UsableLengthMaxMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public UsableLengthMaxMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public UsableLengthMaxMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public UsableLengthMaxMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/WeightMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/WeightMeasurement.g.cs index e54ff3520..b9a5140e0 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/WeightMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/WeightMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class WeightMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "Weight"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "WT"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public WeightMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public WeightMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public WeightMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public WeightMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public WeightMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/WiperEdgeLengthMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/WiperEdgeLengthMeasurement.g.cs index 307c8aeaa..3601f243b 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/WiperEdgeLengthMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/Measurements/WiperEdgeLengthMeasurement.g.cs @@ -8,10 +8,20 @@ namespace MTConnect.Assets.CuttingTools.Measurements /// public class WiperEdgeLengthMeasurement : ToolingMeasurement { + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "WiperEdgeLength"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = "BS"; + /// + /// Initializes a new instance with its type and code set to the defaults for this Measurement. + /// public WiperEdgeLengthMeasurement() { Type = TypeId; @@ -19,6 +29,10 @@ public WiperEdgeLengthMeasurement() } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public WiperEdgeLengthMeasurement(double value) { Type = TypeId; @@ -27,6 +41,10 @@ public WiperEdgeLengthMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public WiperEdgeLengthMeasurement(IToolingMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ProcessFeedRate.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ProcessFeedRate.g.cs index b8c82a81d..6ed1b3c8e 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ProcessFeedRate.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ProcessFeedRate.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.CuttingTools /// public class ProcessFeedRate : IProcessFeedRate { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Constrained process feed rate for the tool in mm/s.minimum **MUST** be specified."; @@ -17,17 +20,17 @@ public class ProcessFeedRate : IProcessFeedRate /// Upper bound for the tool’s process target feedrate. /// public double? Maximum { get; set; } - + /// /// Lower bound for the tool's feedrate. /// public double? Minimum { get; set; } - + /// /// Nominal feedrate the tool is designed to operate at. /// public double? Nominal { get; set; } - + /// /// /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ProcessFeedRateDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ProcessFeedRateDescriptions.g.cs index 588d81fbc..1307f595c 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ProcessFeedRateDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ProcessFeedRateDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// Description text for each property of ProcessFeedRate as defined by the MTConnect Standard. + /// public static class ProcessFeedRateDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ProcessSpindleSpeed.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ProcessSpindleSpeed.g.cs index 37739dff8..2ad2bc015 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ProcessSpindleSpeed.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ProcessSpindleSpeed.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.CuttingTools /// public class ProcessSpindleSpeed : IProcessSpindleSpeed { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Constrained process spindle speed for the tool in revolutions/minute.minimum **MUST** be specified."; @@ -17,17 +20,17 @@ public class ProcessSpindleSpeed : IProcessSpindleSpeed /// Upper bound for the tool’s target spindle speed. /// public double? Maximum { get; set; } - + /// /// Lower bound for the tools spindle speed. /// public double? Minimum { get; set; } - + /// /// Nominal speed the tool is designed to operate at. /// public double? Nominal { get; set; } - + /// /// /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ProcessSpindleSpeedDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ProcessSpindleSpeedDescriptions.g.cs index 35734d27d..a7f77eb99 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ProcessSpindleSpeedDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ProcessSpindleSpeedDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// Description text for each property of ProcessSpindleSpeed as defined by the MTConnect Standard. + /// public static class ProcessSpindleSpeedDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ReconditionCount.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ReconditionCount.g.cs index a5c5f01b4..e0e56122b 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ReconditionCount.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ReconditionCount.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.CuttingTools /// public class ReconditionCount : IReconditionCount { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Number of times the cutter has been reconditioned."; @@ -17,7 +20,7 @@ public class ReconditionCount : IReconditionCount /// Maximum number of times the tool may be reconditioned. /// public int? MaximumCount { get; set; } - + /// /// CuttingToolLifeCycle. /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ReconditionCountDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ReconditionCountDescriptions.g.cs index e295b678b..61953d4da 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ReconditionCountDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ReconditionCountDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// Description text for each property of ReconditionCount as defined by the MTConnect Standard. + /// public static class ReconditionCountDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolLife.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolLife.cs index cb81bda75..028dbfae3 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolLife.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolLife.cs @@ -12,6 +12,10 @@ namespace MTConnect.Assets.CuttingTools /// public partial class ToolLife { + /// + /// Computes a SHA-1 content hash over the tool-life entry's scalar properties for change detection; returns null for a null entry. + /// + /// The tool-life entry to hash. public static string GenerateHash(IToolLife toolLife) { if (toolLife != null) diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolLife.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolLife.g.cs index 4226152a2..4cc0b9479 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolLife.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolLife.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.CuttingTools /// public partial class ToolLife : IToolLife { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Cutting tool life as related to the assembly."; @@ -17,27 +20,27 @@ public partial class ToolLife : IToolLife /// Indicates if the tool life counts from zero to maximum or maximum to zero. /// public MTConnect.Assets.CuttingTools.CountDirectionType CountDirection { get; set; } - + /// /// Initial life of the tool when it is new. /// public double? Initial { get; set; } - + /// /// End of life limit for the tool. /// public double? Limit { get; set; } - + /// /// Type of tool life being accumulated. /// public MTConnect.Assets.CuttingTools.ToolLifeType Type { get; set; } - + /// /// Value of ToolLife. /// public double Value { get; set; } - + /// /// Point at which a tool life warning will be raised. /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolLifeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolLifeDescriptions.g.cs index dd6ccdb9e..42df8840f 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolLifeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolLifeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// Description text for each property of ToolLife as defined by the MTConnect Standard. + /// public static class ToolLifeDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolLifeType.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolLifeType.g.cs index 1ba5efced..8118bc136 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolLifeType.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolLifeType.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// ToolLifeType controlled vocabulary as defined by the MTConnect Standard. + /// public enum ToolLifeType { /// diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolLifeTypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolLifeTypeDescriptions.g.cs index c7b4c644a..20219f4aa 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolLifeTypeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolLifeTypeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class ToolLifeTypeDescriptions { /// @@ -21,6 +24,9 @@ public static class ToolLifeTypeDescriptions public const string WEAR = "Tool life measured in tool wear. Wear **MUST** be provided in millimeters as an offset to nominal. All units for minimum, maximum, and nominal **MUST** be given as millimeter offsets aswell. The standard will only consider dimensional wear at this time."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(ToolLifeType value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolingMeasurement.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolingMeasurement.cs index 33def40c3..973ad40e3 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolingMeasurement.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolingMeasurement.cs @@ -7,8 +7,15 @@ namespace MTConnect.Assets.CuttingTools { public partial class ToolingMeasurement { + /// + /// Initializes an empty tooling measurement, typically for deserialization. + /// public ToolingMeasurement() { } + /// + /// Initializes a tooling measurement by copying the value, nominal, minimum, maximum, significant digits, and native units from an existing measurement; a null source leaves the fields default. + /// + /// The measurement to copy from. public ToolingMeasurement(IToolingMeasurement measurement) { if (measurement != null) @@ -22,6 +29,11 @@ public ToolingMeasurement(IToolingMeasurement measurement) } } + /// + /// Factory that maps a tooling measurement type code to its strongly-typed measurement subclass so the measurement serializes under the correct element name; falls back to a generic ToolingMeasurement when the type is empty or unrecognized. + /// + /// The measurement type code (a measurement TypeId). + /// The source measurement whose values are copied into the created instance. public static ToolingMeasurement Create(string type, IToolingMeasurement measurement) { if (!string.IsNullOrEmpty(type)) diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolingMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolingMeasurement.g.cs index 19e10658b..e0292917b 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolingMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolingMeasurement.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.CuttingTools /// public partial class ToolingMeasurement : Measurement, IToolingMeasurement { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Constrained scalar value associated with a cutting tool."; diff --git a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolingMeasurementDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolingMeasurementDescriptions.g.cs index 5d224cec9..462c9f5ba 100644 --- a/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolingMeasurementDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/CuttingTools/ToolingMeasurementDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.CuttingTools { + /// + /// Description text for each property of ToolingMeasurement as defined by the MTConnect Standard. + /// public static class ToolingMeasurementDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/Files/AbstractFileAsset.cs b/libraries/MTConnect.NET-Common/Assets/Files/AbstractFileAsset.cs index df17c34ee..1d25afc41 100644 --- a/libraries/MTConnect.NET-Common/Assets/Files/AbstractFileAsset.cs +++ b/libraries/MTConnect.NET-Common/Assets/Files/AbstractFileAsset.cs @@ -5,9 +5,15 @@ namespace MTConnect.Assets.Files { public partial class AbstractFileAsset { + /// + /// The shared Asset type identifier ("File") used by the file asset family written to the Type attribute and used to recognize these assets during deserialization. + /// public const string TypeId = "File"; + /// + /// Initializes a new AbstractFileAsset, stamping the Asset Type with . + /// public AbstractFileAsset() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/Files/AbstractFileAsset.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/AbstractFileAsset.g.cs index 8a6362f41..68daf0fa5 100644 --- a/libraries/MTConnect.NET-Common/Assets/Files/AbstractFileAsset.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Files/AbstractFileAsset.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.Files /// public abstract partial class AbstractFileAsset : Asset, IAbstractFileAsset { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Abstract Asset that contains the common properties of the File and FileArchetype types."; @@ -17,27 +20,27 @@ public abstract partial class AbstractFileAsset : Asset, IAbstractFileAsset /// Category of application that will use this file. /// public MTConnect.Assets.Files.ApplicationCategory ApplicationCategory { get; set; } - + /// /// Type of application that will use this file. /// public MTConnect.Assets.Files.ApplicationType ApplicationType { get; set; } - + /// /// Remark or interpretation for human interpretation associated with a File or FileArchetype. /// public System.Collections.Generic.IEnumerable FileComments { get; set; } - + /// /// Key-value pair providing additional metadata about a File. /// public System.Collections.Generic.IEnumerable FileProperties { get; set; } - + /// /// Mime type of the file. /// public string MediaType { get; set; } - + /// /// Name of the file. /// diff --git a/libraries/MTConnect.NET-Common/Assets/Files/AbstractFileAssetDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/AbstractFileAssetDescriptions.g.cs index 50175a043..e2449881a 100644 --- a/libraries/MTConnect.NET-Common/Assets/Files/AbstractFileAssetDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Files/AbstractFileAssetDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.Files { + /// + /// Description text for each property of AbstractFileAsset as defined by the MTConnect Standard. + /// public static class AbstractFileAssetDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/Files/AbstractFileDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/AbstractFileDescriptions.g.cs deleted file mode 100644 index 7885dfcf6..000000000 --- a/libraries/MTConnect.NET-Common/Assets/Files/AbstractFileDescriptions.g.cs +++ /dev/null @@ -1,38 +0,0 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. -// TrakHound Inc. licenses this file to you under the MIT license. - -namespace MTConnect.Assets.Files -{ - public static class AbstractFileDescriptions - { - /// - /// Category of application that will use this file. - /// - public const string ApplicationCategory = "Category of application that will use this file."; - - /// - /// Type of application that will use this file. - /// - public const string ApplicationType = "Type of application that will use this file."; - - /// - /// Remark or interpretation for human interpretation associated with a File or FileArchetype. - /// - public const string FileComments = "Remark or interpretation for human interpretation associated with a File or FileArchetype."; - - /// - /// Key-value pair providing additional metadata about a File. - /// - public const string FileProperties = "Key-value pair providing additional metadata about a File."; - - /// - /// Mime type of the file. - /// - public const string MediaType = "Mime type of the file."; - - /// - /// Name of the file. - /// - public const string Name = "Name of the file."; - } -} \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Assets/Files/ApplicationCategory.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/ApplicationCategory.g.cs index b211f7e59..18a1fe178 100644 --- a/libraries/MTConnect.NET-Common/Assets/Files/ApplicationCategory.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Files/ApplicationCategory.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.Files { + /// + /// ApplicationCategory controlled vocabulary as defined by the MTConnect Standard. + /// public enum ApplicationCategory { /// diff --git a/libraries/MTConnect.NET-Common/Assets/Files/ApplicationCategoryDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/ApplicationCategoryDescriptions.g.cs index 09ae18aa8..eb3cd9418 100644 --- a/libraries/MTConnect.NET-Common/Assets/Files/ApplicationCategoryDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Files/ApplicationCategoryDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.Files { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class ApplicationCategoryDescriptions { /// @@ -46,6 +49,9 @@ public static class ApplicationCategoryDescriptions public const string SETUP = "Files related to the setup of a process."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(ApplicationCategory value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Assets/Files/ApplicationType.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/ApplicationType.g.cs index 40f16a65f..967e1f8fe 100644 --- a/libraries/MTConnect.NET-Common/Assets/Files/ApplicationType.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Files/ApplicationType.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.Files { + /// + /// ApplicationType controlled vocabulary as defined by the MTConnect Standard. + /// public enum ApplicationType { /// diff --git a/libraries/MTConnect.NET-Common/Assets/Files/ApplicationTypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/ApplicationTypeDescriptions.g.cs index c64206b0f..05dbf9569 100644 --- a/libraries/MTConnect.NET-Common/Assets/Files/ApplicationTypeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Files/ApplicationTypeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.Files { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class ApplicationTypeDescriptions { /// @@ -36,6 +39,9 @@ public static class ApplicationTypeDescriptions public const string PRODUCTION_PROGRAM = "Machine instructions to perform a process."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(ApplicationType value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Assets/Files/Destination.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/Destination.g.cs index b9159f013..3c4845aaf 100644 --- a/libraries/MTConnect.NET-Common/Assets/Files/Destination.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Files/Destination.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.Files /// public class Destination : IDestination { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Reference to the target Device for this File."; diff --git a/libraries/MTConnect.NET-Common/Assets/Files/DestinationDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/DestinationDescriptions.g.cs index 219be16a5..a0cdadad3 100644 --- a/libraries/MTConnect.NET-Common/Assets/Files/DestinationDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Files/DestinationDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.Files { + /// + /// Description text for each property of Destination as defined by the MTConnect Standard. + /// public static class DestinationDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/Files/FileArchetypeAsset.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/FileArchetypeAsset.g.cs index b68f6eda9..5d73ca051 100644 --- a/libraries/MTConnect.NET-Common/Assets/Files/FileArchetypeAsset.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Files/FileArchetypeAsset.g.cs @@ -10,8 +10,10 @@ namespace MTConnect.Assets.Files /// public partial class FileArchetypeAsset : AbstractFileAsset, IFileArchetypeAsset { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "AbstractFile type that provides information common to all versions of a file."; - } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Assets/Files/FileArchetypeAssetDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/FileArchetypeAssetDescriptions.g.cs deleted file mode 100644 index 1236ca670..000000000 --- a/libraries/MTConnect.NET-Common/Assets/Files/FileArchetypeAssetDescriptions.g.cs +++ /dev/null @@ -1,9 +0,0 @@ -// Copyright (c) 2024 TrakHound Inc., All Rights Reserved. -// TrakHound Inc. licenses this file to you under the MIT license. - -namespace MTConnect.Assets.Files -{ - public static class FileArchetypeAssetDescriptions - { - } -} \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Assets/Files/FileArchetypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/FileArchetypeDescriptions.g.cs deleted file mode 100644 index 4289da057..000000000 --- a/libraries/MTConnect.NET-Common/Assets/Files/FileArchetypeDescriptions.g.cs +++ /dev/null @@ -1,9 +0,0 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. -// TrakHound Inc. licenses this file to you under the MIT license. - -namespace MTConnect.Assets.Files -{ - public static class FileArchetypeDescriptions - { - } -} \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Assets/Files/FileAsset.cs b/libraries/MTConnect.NET-Common/Assets/Files/FileAsset.cs index a07746b82..afd8ecd87 100644 --- a/libraries/MTConnect.NET-Common/Assets/Files/FileAsset.cs +++ b/libraries/MTConnect.NET-Common/Assets/Files/FileAsset.cs @@ -8,15 +8,25 @@ namespace MTConnect.Assets.Files { public partial class FileAsset { + /// + /// The fixed Asset type identifier ("File") written to the Type attribute and used to recognize this asset during deserialization. + /// public const string TypeId = "File"; + /// + /// Initializes a new FileAsset, stamping the Asset Type with . + /// public FileAsset() { Type = TypeId; } + /// + /// Excludes the asset from a response document when its required Size or VersionId are missing; otherwise defers to the base version processing. + /// + /// The MTConnect version the response document targets. protected override IAsset OnProcess(Version mtconnectVersion) { if (Size <= 0) return null; @@ -25,6 +35,10 @@ protected override IAsset OnProcess(Version mtconnectVersion) return base.OnProcess(mtconnectVersion); } + /// + /// Validates that the required File properties are present: a positive Size, a VersionId, a CreationTime, and a Location with an Href; reports the first missing field. + /// + /// The MTConnect version to validate against. public override AssetValidationResult IsValid(Version mtconnectVersion) { var baseResult = base.IsValid(mtconnectVersion); @@ -66,11 +80,20 @@ public override AssetValidationResult IsValid(Version mtconnectVersion) return new AssetValidationResult(result, message); } + /// + /// Computes the content hash of this file asset; see . + /// + /// When true, the asset timestamp is folded into the hash. public override string GenerateHash(bool includeTimestamp = true) { return GenerateHash(this); } + /// + /// Computes a SHA-1 content hash over the asset's scalar properties, optionally excluding the timestamp so equality can be tested independently of when the asset was reported; returns null for a null asset. + /// + /// The file asset to hash. + /// When true, the asset timestamp is folded into the hash. public static string GenerateHash(FileAsset asset, bool includeTimestamp = true) { if (asset != null) diff --git a/libraries/MTConnect.NET-Common/Assets/Files/FileAsset.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/FileAsset.g.cs index ca9522323..c738c5d11 100644 --- a/libraries/MTConnect.NET-Common/Assets/Files/FileAsset.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Files/FileAsset.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.Files /// public partial class FileAsset : AbstractFileAsset, IFileAsset { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "AbstractFile type that provides information about the File instance and its URL."; @@ -17,42 +20,42 @@ public partial class FileAsset : AbstractFileAsset, IFileAsset /// Time the file was created. /// public System.DateTime CreationTime { get; set; } - + /// /// Reference to the target Device for this File. /// public System.Collections.Generic.IEnumerable Destinations { get; set; } - + /// /// URL reference to the file location. /// public MTConnect.Assets.Files.IFileLocation Location { get; set; } - + /// /// Time the file was modified. /// public System.DateTime? ModificationTime { get; set; } - + /// /// Public key used to verify the signature. /// public string PublicKey { get; set; } - + /// /// Secure hash of the file. /// public string Signature { get; set; } - + /// /// Size of the file in bytes. /// public int Size { get; set; } - + /// /// State of the file. /// public MTConnect.Assets.Files.FileState State { get; set; } - + /// /// Version identifier of the file. /// diff --git a/libraries/MTConnect.NET-Common/Assets/Files/FileAssetDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/FileAssetDescriptions.g.cs index fcb9857b2..9a47c106e 100644 --- a/libraries/MTConnect.NET-Common/Assets/Files/FileAssetDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Files/FileAssetDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.Files { + /// + /// Description text for each property of FileAsset as defined by the MTConnect Standard. + /// public static class FileAssetDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/Files/FileComment.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/FileComment.g.cs index 9ab84b96d..a5e91f1cf 100644 --- a/libraries/MTConnect.NET-Common/Assets/Files/FileComment.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Files/FileComment.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.Files /// public class FileComment : IFileComment { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Remark or interpretation for human interpretation associated with a File or FileArchetype."; @@ -17,7 +20,7 @@ public class FileComment : IFileComment /// Time the comment was made. /// public System.DateTime Timestamp { get; set; } - + /// /// Text of the comment about the file. /// diff --git a/libraries/MTConnect.NET-Common/Assets/Files/FileCommentDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/FileCommentDescriptions.g.cs index 436ddbc8c..ee7db8b24 100644 --- a/libraries/MTConnect.NET-Common/Assets/Files/FileCommentDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Files/FileCommentDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.Files { + /// + /// Description text for each property of FileComment as defined by the MTConnect Standard. + /// public static class FileCommentDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/Files/FileDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/FileDescriptions.g.cs deleted file mode 100644 index 825ecc344..000000000 --- a/libraries/MTConnect.NET-Common/Assets/Files/FileDescriptions.g.cs +++ /dev/null @@ -1,53 +0,0 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. -// TrakHound Inc. licenses this file to you under the MIT license. - -namespace MTConnect.Assets.Files -{ - public static class FileDescriptions - { - /// - /// Time the file was created. - /// - public const string CreationTime = "Time the file was created."; - - /// - /// Reference to the target Device for this File. - /// - public const string Destinations = "Reference to the target Device for this File."; - - /// - /// URL reference to the file location. - /// - public const string Location = "URL reference to the file location."; - - /// - /// Time the file was modified. - /// - public const string ModificationTime = "Time the file was modified."; - - /// - /// Public key used to verify the signature. - /// - public const string PublicKey = "Public key used to verify the signature."; - - /// - /// Secure hash of the file. - /// - public const string Signature = "Secure hash of the file."; - - /// - /// Size of the file in bytes. - /// - public const string Size = "Size of the file in bytes."; - - /// - /// State of the file. - /// - public const string State = "State of the file."; - - /// - /// Version identifier of the file. - /// - public const string VersionId = "Version identifier of the file."; - } -} \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Assets/Files/FileLocation.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/FileLocation.g.cs index 46d801c3e..02f6cfcfa 100644 --- a/libraries/MTConnect.NET-Common/Assets/Files/FileLocation.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Files/FileLocation.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.Files /// public class FileLocation : IFileLocation { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "URL reference to the file location."; @@ -17,7 +20,7 @@ public class FileLocation : IFileLocation /// URL reference to the file.`href` is of type `xlink:href` from the W3C XLink specification. /// public string Href { get; set; } - + /// /// Type of href for the xlink href type. **MUST** be `locator` referring to a URL. /// diff --git a/libraries/MTConnect.NET-Common/Assets/Files/FileLocationDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/FileLocationDescriptions.g.cs index cf3f72e8a..284543478 100644 --- a/libraries/MTConnect.NET-Common/Assets/Files/FileLocationDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Files/FileLocationDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.Files { + /// + /// Description text for each property of FileLocation as defined by the MTConnect Standard. + /// public static class FileLocationDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/Files/FileProperty.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/FileProperty.g.cs index eefa6a11c..afd944148 100644 --- a/libraries/MTConnect.NET-Common/Assets/Files/FileProperty.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Files/FileProperty.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.Files /// public class FileProperty : IFileProperty { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Key-value pair providing additional metadata about a File."; @@ -17,7 +20,7 @@ public class FileProperty : IFileProperty /// Name of the FileProperty. /// public string Name { get; set; } - + /// /// The value of the FileProperty. /// diff --git a/libraries/MTConnect.NET-Common/Assets/Files/FilePropertyDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/FilePropertyDescriptions.g.cs index e26c732e1..deefa7e41 100644 --- a/libraries/MTConnect.NET-Common/Assets/Files/FilePropertyDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Files/FilePropertyDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.Files { + /// + /// Description text for each property of FileProperty as defined by the MTConnect Standard. + /// public static class FilePropertyDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/Files/FileState.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/FileState.g.cs index 295cf9987..64c281c74 100644 --- a/libraries/MTConnect.NET-Common/Assets/Files/FileState.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Files/FileState.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.Files { + /// + /// FileState controlled vocabulary as defined by the MTConnect Standard. + /// public enum FileState { /// diff --git a/libraries/MTConnect.NET-Common/Assets/Files/FileStateDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/Files/FileStateDescriptions.g.cs index 01cc0d0c9..f6f3930ad 100644 --- a/libraries/MTConnect.NET-Common/Assets/Files/FileStateDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Files/FileStateDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.Files { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class FileStateDescriptions { /// @@ -21,6 +24,9 @@ public static class FileStateDescriptions public const string REVISION = "Content is modified from `PRODUCTION` or `EXPERIMENTAL`."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(FileState value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Assets/Fixture/FixtureAsset.g.cs b/libraries/MTConnect.NET-Common/Assets/Fixture/FixtureAsset.g.cs index 021c845a3..e6895c1e5 100644 --- a/libraries/MTConnect.NET-Common/Assets/Fixture/FixtureAsset.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Fixture/FixtureAsset.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.Fixture /// public partial class FixtureAsset : PhysicalAsset, IFixtureAsset { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = ""; @@ -17,17 +20,17 @@ public partial class FixtureAsset : PhysicalAsset, IFixtureAsset /// Actuation type of the Fixture's clamping mechanism. /// public string ClampingMethod { get; set; } - + /// /// Identifier of the Pallet. /// public string FixtureId { get; set; } - + /// /// Number or sequence assigned to the Fixture in a group of Fixtures. /// public int FixtureNumber { get; set; } - + /// /// Actuation type of the Fixture's mounting mechanism. /// diff --git a/libraries/MTConnect.NET-Common/Assets/Fixture/FixtureAssetDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/Fixture/FixtureAssetDescriptions.g.cs index a52c7fd69..bdda9a3df 100644 --- a/libraries/MTConnect.NET-Common/Assets/Fixture/FixtureAssetDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Fixture/FixtureAssetDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.Fixture { + /// + /// Description text for each property of FixtureAsset as defined by the MTConnect Standard. + /// public static class FixtureAssetDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/IAsset.cs b/libraries/MTConnect.NET-Common/Assets/IAsset.cs index 609f331cc..93c913f29 100644 --- a/libraries/MTConnect.NET-Common/Assets/IAsset.cs +++ b/libraries/MTConnect.NET-Common/Assets/IAsset.cs @@ -18,10 +18,22 @@ public partial interface IAsset : IMTConnectEntity ulong InstanceId { get; set; } + /// + /// Prepares the asset for inclusion in a response document for the given MTConnect version, returning the version-adjusted asset or null to exclude it. + /// + /// The MTConnect version the response document targets. IAsset Process(Version mtconnectVersion); + /// + /// Validates the asset against the given MTConnect version, reporting whether it satisfies that version's constraints. + /// + /// The MTConnect version to validate against. AssetValidationResult IsValid(Version mtconnectVersion); + /// + /// Computes a content hash used to detect changes to the asset. + /// + /// When true, the asset timestamp is folded into the hash. string GenerateHash(bool includeTimestamp = true); } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Assets/IPhysicalAsset.g.cs b/libraries/MTConnect.NET-Common/Assets/IPhysicalAsset.g.cs index 032261dba..c448ce6a3 100644 --- a/libraries/MTConnect.NET-Common/Assets/IPhysicalAsset.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/IPhysicalAsset.g.cs @@ -26,7 +26,7 @@ public partial interface IPhysicalAsset /// /// Constrained scalar value associated with an Asset /// - MTConnect.Assets.Pallet.IMeasurement Measurement { get; } + MTConnect.Assets.CuttingTools.IMeasurement Measurement { get; } /// /// Date of next inspection of the Asset. diff --git a/libraries/MTConnect.NET-Common/Assets/Pallet/HeightMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/Pallet/HeightMeasurement.g.cs index 5370fef58..0c636f07e 100644 --- a/libraries/MTConnect.NET-Common/Assets/Pallet/HeightMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Pallet/HeightMeasurement.g.cs @@ -8,17 +8,30 @@ namespace MTConnect.Assets.Pallet /// public class HeightMeasurement : Measurement, IHeightMeasurement { - public new const string DescriptionText = "Height of the PhysicalAsset"; + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "Height"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = ""; + /// + /// Initializes a new instance with its type set to the default for this Measurement. + /// public HeightMeasurement() { Type = TypeId; } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public HeightMeasurement(double value) { Type = TypeId; @@ -26,6 +39,10 @@ public HeightMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public HeightMeasurement(IMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/Pallet/LengthMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/Pallet/LengthMeasurement.g.cs index 92cac40b2..1ef911452 100644 --- a/libraries/MTConnect.NET-Common/Assets/Pallet/LengthMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Pallet/LengthMeasurement.g.cs @@ -8,17 +8,30 @@ namespace MTConnect.Assets.Pallet /// public class LengthMeasurement : Measurement, ILengthMeasurement { - public new const string DescriptionText = "Length of the PhysicalAsset"; + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "Length"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = ""; + /// + /// Initializes a new instance with its type set to the default for this Measurement. + /// public LengthMeasurement() { Type = TypeId; } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public LengthMeasurement(double value) { Type = TypeId; @@ -26,6 +39,10 @@ public LengthMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public LengthMeasurement(IMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/Pallet/LoadedHeightMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/Pallet/LoadedHeightMeasurement.g.cs index 68ca5111b..3d021ab73 100644 --- a/libraries/MTConnect.NET-Common/Assets/Pallet/LoadedHeightMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Pallet/LoadedHeightMeasurement.g.cs @@ -8,17 +8,30 @@ namespace MTConnect.Assets.Pallet /// public class LoadedHeightMeasurement : Measurement, ILoadedHeightMeasurement { - public new const string DescriptionText = "Loaded height of the PhysicalAsset"; + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "LoadedHeight"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = ""; + /// + /// Initializes a new instance with its type set to the default for this Measurement. + /// public LoadedHeightMeasurement() { Type = TypeId; } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public LoadedHeightMeasurement(double value) { Type = TypeId; @@ -26,6 +39,10 @@ public LoadedHeightMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public LoadedHeightMeasurement(IMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/Pallet/LoadedLengthMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/Pallet/LoadedLengthMeasurement.g.cs index 5aff580bf..8aac54cbe 100644 --- a/libraries/MTConnect.NET-Common/Assets/Pallet/LoadedLengthMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Pallet/LoadedLengthMeasurement.g.cs @@ -8,17 +8,30 @@ namespace MTConnect.Assets.Pallet /// public class LoadedLengthMeasurement : Measurement, ILoadedLengthMeasurement { - public new const string DescriptionText = "Loaded length of the PhysicalAsset"; + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "LoadedLength"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = ""; + /// + /// Initializes a new instance with its type set to the default for this Measurement. + /// public LoadedLengthMeasurement() { Type = TypeId; } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public LoadedLengthMeasurement(double value) { Type = TypeId; @@ -26,6 +39,10 @@ public LoadedLengthMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public LoadedLengthMeasurement(IMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/Pallet/LoadedSwingMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/Pallet/LoadedSwingMeasurement.g.cs index c270fb137..0381715f4 100644 --- a/libraries/MTConnect.NET-Common/Assets/Pallet/LoadedSwingMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Pallet/LoadedSwingMeasurement.g.cs @@ -8,17 +8,30 @@ namespace MTConnect.Assets.Pallet /// public class LoadedSwingMeasurement : Measurement, ILoadedSwingMeasurement { - public new const string DescriptionText = "Loaded swing of the PhysicalAsset"; + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "LoadedSwing"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = ""; + /// + /// Initializes a new instance with its type set to the default for this Measurement. + /// public LoadedSwingMeasurement() { Type = TypeId; } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public LoadedSwingMeasurement(double value) { Type = TypeId; @@ -26,6 +39,10 @@ public LoadedSwingMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public LoadedSwingMeasurement(IMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/Pallet/LoadedWeightMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/Pallet/LoadedWeightMeasurement.g.cs index db15ecc9e..f968db596 100644 --- a/libraries/MTConnect.NET-Common/Assets/Pallet/LoadedWeightMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Pallet/LoadedWeightMeasurement.g.cs @@ -8,17 +8,30 @@ namespace MTConnect.Assets.Pallet /// public class LoadedWeightMeasurement : Measurement, ILoadedWeightMeasurement { - public new const string DescriptionText = "Loaded weight of the PhysicalAsset"; + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "LoadedWeight"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = ""; + /// + /// Initializes a new instance with its type set to the default for this Measurement. + /// public LoadedWeightMeasurement() { Type = TypeId; } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public LoadedWeightMeasurement(double value) { Type = TypeId; @@ -26,6 +39,10 @@ public LoadedWeightMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public LoadedWeightMeasurement(IMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/Pallet/LoadedWidthMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/Pallet/LoadedWidthMeasurement.g.cs index c82b3f08e..cf1da8d65 100644 --- a/libraries/MTConnect.NET-Common/Assets/Pallet/LoadedWidthMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Pallet/LoadedWidthMeasurement.g.cs @@ -8,17 +8,30 @@ namespace MTConnect.Assets.Pallet /// public class LoadedWidthMeasurement : Measurement, ILoadedWidthMeasurement { - public new const string DescriptionText = "Loaded width of the PhysicalAsset"; + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "LoadedWidth"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = ""; + /// + /// Initializes a new instance with its type set to the default for this Measurement. + /// public LoadedWidthMeasurement() { Type = TypeId; } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public LoadedWidthMeasurement(double value) { Type = TypeId; @@ -26,6 +39,10 @@ public LoadedWidthMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public LoadedWidthMeasurement(IMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/Pallet/Measurement.cs b/libraries/MTConnect.NET-Common/Assets/Pallet/Measurement.cs index c1d8e71c9..4e1f216fc 100644 --- a/libraries/MTConnect.NET-Common/Assets/Pallet/Measurement.cs +++ b/libraries/MTConnect.NET-Common/Assets/Pallet/Measurement.cs @@ -5,11 +5,21 @@ namespace MTConnect.Assets.Pallet { public partial class Measurement { + /// + /// The measurement type name, which selects the concrete measurement subtype and its element name in serialized documents. + /// public string Type { get; set; } + /// + /// Initializes an empty pallet measurement, typically for deserialization. + /// public Measurement() { } + /// + /// Initializes a pallet measurement by copying the value, nominal, minimum, maximum, significant digits, native units, and units from an existing measurement; a null source leaves the fields default. + /// + /// The measurement to copy from. public Measurement(IMeasurement measurement) { if (measurement != null) diff --git a/libraries/MTConnect.NET-Common/Assets/Pallet/Measurement.g.cs b/libraries/MTConnect.NET-Common/Assets/Pallet/Measurement.g.cs index 2b8f5ee24..ebb607274 100644 --- a/libraries/MTConnect.NET-Common/Assets/Pallet/Measurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Pallet/Measurement.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.Pallet /// public partial class Measurement : IMeasurement { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Constrained scalar value associated with an Asset"; @@ -17,32 +20,32 @@ public partial class Measurement : IMeasurement /// Maximum value for the measurement. /// public double? Maximum { get; set; } - + /// /// Minimum value for the measurement. /// public double? Minimum { get; set; } - + /// /// NativeUnits. /// public string NativeUnits { get; set; } - + /// /// As advertised value for the measurement. /// public double? Nominal { get; set; } - + /// /// Number of significant digits in the reported value. /// public int? SignificantDigits { get; set; } - + /// /// Units. /// public string Units { get; set; } - + /// /// /// diff --git a/libraries/MTConnect.NET-Common/Assets/Pallet/MeasurementDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/Pallet/MeasurementDescriptions.g.cs index d10e12328..d88c506c6 100644 --- a/libraries/MTConnect.NET-Common/Assets/Pallet/MeasurementDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Pallet/MeasurementDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.Pallet { + /// + /// Description text for each property of Measurement as defined by the MTConnect Standard. + /// public static class MeasurementDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/Pallet/PalletAsset.g.cs b/libraries/MTConnect.NET-Common/Assets/Pallet/PalletAsset.g.cs index 4e3532b4c..eec208381 100644 --- a/libraries/MTConnect.NET-Common/Assets/Pallet/PalletAsset.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Pallet/PalletAsset.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.Pallet /// public partial class PalletAsset : PhysicalAsset, IPalletAsset { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "PhysicalAsset that has a portable platform for handling, storing, or moving materials, parts, blanks etc."; @@ -17,22 +20,22 @@ public partial class PalletAsset : PhysicalAsset, IPalletAsset /// Actuation type of the Pallet's clamping mechanism. /// public string ClampingMethod { get; set; } - + /// /// Actuation type of the Pallet's mounting mechanism. /// public string MountingMethod { get; set; } - + /// /// Identifier of the Pallet. /// public string PalletId { get; set; } - + /// /// Number or sequence assigned to the Pallet in a group of Pallets. /// public int PalletNumber { get; set; } - + /// /// Type of Pallet. Common types of pallet include: Process, Warehouse, Shipping, Fixture and Machine. /// diff --git a/libraries/MTConnect.NET-Common/Assets/Pallet/PalletAssetDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/Pallet/PalletAssetDescriptions.g.cs index bd9c0860c..401932e7e 100644 --- a/libraries/MTConnect.NET-Common/Assets/Pallet/PalletAssetDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Pallet/PalletAssetDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.Pallet { + /// + /// Description text for each property of PalletAsset as defined by the MTConnect Standard. + /// public static class PalletAssetDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/Pallet/SwingMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/Pallet/SwingMeasurement.g.cs index 3c7fc0f64..de92348d8 100644 --- a/libraries/MTConnect.NET-Common/Assets/Pallet/SwingMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Pallet/SwingMeasurement.g.cs @@ -8,17 +8,30 @@ namespace MTConnect.Assets.Pallet /// public class SwingMeasurement : Measurement, ISwingMeasurement { - public new const string DescriptionText = "Swing of the PhysicalAsset"; + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "Swing"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = ""; + /// + /// Initializes a new instance with its type set to the default for this Measurement. + /// public SwingMeasurement() { Type = TypeId; } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public SwingMeasurement(double value) { Type = TypeId; @@ -26,6 +39,10 @@ public SwingMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public SwingMeasurement(IMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/Pallet/WeightMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/Pallet/WeightMeasurement.g.cs index 06b8b0954..7f212ad8f 100644 --- a/libraries/MTConnect.NET-Common/Assets/Pallet/WeightMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Pallet/WeightMeasurement.g.cs @@ -8,17 +8,30 @@ namespace MTConnect.Assets.Pallet /// public class WeightMeasurement : Measurement, IWeightMeasurement { - public new const string DescriptionText = "Weight of the PhysicalAsset"; + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "Weight"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = ""; + /// + /// Initializes a new instance with its type set to the default for this Measurement. + /// public WeightMeasurement() { Type = TypeId; } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public WeightMeasurement(double value) { Type = TypeId; @@ -26,6 +39,10 @@ public WeightMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public WeightMeasurement(IMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/Pallet/WidthMeasurement.g.cs b/libraries/MTConnect.NET-Common/Assets/Pallet/WidthMeasurement.g.cs index e00685d10..d83b723ba 100644 --- a/libraries/MTConnect.NET-Common/Assets/Pallet/WidthMeasurement.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/Pallet/WidthMeasurement.g.cs @@ -8,17 +8,30 @@ namespace MTConnect.Assets.Pallet /// public class WidthMeasurement : Measurement, IWidthMeasurement { - public new const string DescriptionText = "Width of the PhysicalAsset"; + /// + /// The MTConnect type value that identifies this Measurement. + /// public const string TypeId = "Width"; + + /// + /// The MTConnect code value that identifies this Measurement. + /// public const string CodeId = ""; + /// + /// Initializes a new instance with its type set to the default for this Measurement. + /// public WidthMeasurement() { Type = TypeId; } + /// + /// Initializes a new instance with the specified measured value. + /// + /// The measured value. public WidthMeasurement(double value) { Type = TypeId; @@ -26,6 +39,10 @@ public WidthMeasurement(double value) } + /// + /// Initializes a new instance by copying the specified measurement. + /// + /// The measurement to copy. public WidthMeasurement(IMeasurement measurement) : base(measurement) { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/PhysicalAsset.g.cs b/libraries/MTConnect.NET-Common/Assets/PhysicalAsset.g.cs index 53a91eef0..a348806ce 100644 --- a/libraries/MTConnect.NET-Common/Assets/PhysicalAsset.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/PhysicalAsset.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets /// public partial class PhysicalAsset : IPhysicalAsset { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Abstract physical Asset."; @@ -17,22 +20,22 @@ public partial class PhysicalAsset : IPhysicalAsset /// Date of calibration of the Asset. /// public System.DateTime CalibrationDate { get; set; } - + /// /// Date of last inspection of the Asset. /// public System.DateTime InspectionDate { get; set; } - + /// /// Date of creation or built of the Asset. /// public System.DateTime ManufactureDate { get; set; } - + /// /// Constrained scalar value associated with an Asset /// - public MTConnect.Assets.Pallet.IMeasurement Measurement { get; set; } - + public MTConnect.Assets.CuttingTools.IMeasurement Measurement { get; set; } + /// /// Date of next inspection of the Asset. /// diff --git a/libraries/MTConnect.NET-Common/Assets/PhysicalAssetDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/PhysicalAssetDescriptions.g.cs index a02affa10..3b4684f4e 100644 --- a/libraries/MTConnect.NET-Common/Assets/PhysicalAssetDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/PhysicalAssetDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets { + /// + /// Description text for each property of PhysicalAsset as defined by the MTConnect Standard. + /// public static class PhysicalAssetDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocument.g.cs b/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocument.g.cs index 29a74878d..6ee2955c6 100644 --- a/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocument.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocument.g.cs @@ -10,8 +10,10 @@ namespace MTConnect.Assets.QIF /// public class QIFDocument : IQIFDocument { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "QIF Document as given by the QIF standard."; - } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentDescriptions.g.cs deleted file mode 100644 index 4d9f5daa2..000000000 --- a/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentDescriptions.g.cs +++ /dev/null @@ -1,9 +0,0 @@ -// Copyright (c) 2024 TrakHound Inc., All Rights Reserved. -// TrakHound Inc. licenses this file to you under the MIT license. - -namespace MTConnect.Assets.QIF -{ - public static class QIFDocumentDescriptions - { - } -} \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentType.g.cs b/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentType.g.cs index 41e4bbad5..2dde41622 100644 --- a/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentType.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentType.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.QIF { + /// + /// QIFDocumentType controlled vocabulary as defined by the MTConnect Standard. + /// public enum QIFDocumentType { /// diff --git a/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentTypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentTypeDescriptions.g.cs index cfb3bcf52..b9bda4d7a 100644 --- a/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentTypeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentTypeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.QIF { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class QIFDocumentTypeDescriptions { /// @@ -36,6 +39,9 @@ public static class QIFDocumentTypeDescriptions public const string STATISTICS = ""; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(QIFDocumentType value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentWrapperAsset.cs b/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentWrapperAsset.cs index fedf49044..d71d2bd2d 100644 --- a/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentWrapperAsset.cs +++ b/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentWrapperAsset.cs @@ -8,9 +8,15 @@ namespace MTConnect.Assets.QIF { public partial class QIFDocumentWrapperAsset { + /// + /// The fixed Asset type identifier ("QIFDocumentWrapper") written to the Type attribute and used to recognize this asset during deserialization. + /// public const string TypeId = "QIFDocumentWrapper"; + /// + /// Initializes a new QIFDocumentWrapperAsset, stamping the Asset Type with . + /// public QIFDocumentWrapperAsset() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentWrapperAsset.g.cs b/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentWrapperAsset.g.cs index 3a59c775d..a3e53bcb9 100644 --- a/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentWrapperAsset.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentWrapperAsset.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.QIF /// public partial class QIFDocumentWrapperAsset : Asset, IQIFDocumentWrapperAsset { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Asset that carries the QIF Document."; @@ -17,7 +20,7 @@ public partial class QIFDocumentWrapperAsset : Asset, IQIFDocumentWrapperAsset /// QIF Document as given by the QIF standard. /// public string QIFDocument { get; set; } - + /// /// Contained QIF Document type as defined in the QIF Standard. /// diff --git a/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentWrapperAssetDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentWrapperAssetDescriptions.g.cs index 2b35c9221..0bcc736e8 100644 --- a/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentWrapperAssetDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/QIF/QIFDocumentWrapperAssetDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.QIF { + /// + /// Description text for each property of QIFDocumentWrapperAsset as defined by the MTConnect Standard. + /// public static class QIFDocumentWrapperAssetDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/RawMaterials/Form.g.cs b/libraries/MTConnect.NET-Common/Assets/RawMaterials/Form.g.cs index 954049d64..cdd463124 100644 --- a/libraries/MTConnect.NET-Common/Assets/RawMaterials/Form.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/RawMaterials/Form.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.RawMaterials { + /// + /// Form controlled vocabulary as defined by the MTConnect Standard. + /// public enum Form { /// diff --git a/libraries/MTConnect.NET-Common/Assets/RawMaterials/FormDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/RawMaterials/FormDescriptions.g.cs index b5f63adf7..887ffa449 100644 --- a/libraries/MTConnect.NET-Common/Assets/RawMaterials/FormDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/RawMaterials/FormDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.RawMaterials { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class FormDescriptions { /// @@ -51,6 +54,9 @@ public static class FormDescriptions public const string SHEET = ""; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(Form value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Assets/RawMaterials/Material.g.cs b/libraries/MTConnect.NET-Common/Assets/RawMaterials/Material.g.cs index ce7e8c407..44dc746cd 100644 --- a/libraries/MTConnect.NET-Common/Assets/RawMaterials/Material.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/RawMaterials/Material.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.RawMaterials /// public class Material : IMaterial { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Material used as the RawMaterial."; @@ -17,37 +20,37 @@ public class Material : IMaterial /// Unique identifier for the material. /// public string Id { get; set; } - + /// /// Manufacturer's lot code of the material. /// public string Lot { get; set; } - + /// /// Name of the material manufacturer. /// public string Manufacturer { get; set; } - + /// /// Lot code of the raw feed stock for the material, from the feed stock manufacturer. /// public string ManufacturingCode { get; set; } - + /// /// Manufacturing date of the material from the material manufacturer. /// public System.DateTime? ManufacturingDate { get; set; } - + /// /// ASTM standard code that the material complies with. /// public string MaterialCode { get; set; } - + /// /// Name of the material. Examples: `ULTM9085`, `ABS`, `4140`. /// public string Name { get; set; } - + /// /// Type of material. Examples: `Metal`, `Polymer`, `Wood`, `4140`, `Recycled`, `Prestine` and `Used`. /// diff --git a/libraries/MTConnect.NET-Common/Assets/RawMaterials/MaterialDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/RawMaterials/MaterialDescriptions.g.cs index a1ffe2c43..c8b8df01b 100644 --- a/libraries/MTConnect.NET-Common/Assets/RawMaterials/MaterialDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/RawMaterials/MaterialDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.RawMaterials { + /// + /// Description text for each property of Material as defined by the MTConnect Standard. + /// public static class MaterialDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Assets/RawMaterials/RawMaterialAsset.cs b/libraries/MTConnect.NET-Common/Assets/RawMaterials/RawMaterialAsset.cs index a727cc49f..5daf4b639 100644 --- a/libraries/MTConnect.NET-Common/Assets/RawMaterials/RawMaterialAsset.cs +++ b/libraries/MTConnect.NET-Common/Assets/RawMaterials/RawMaterialAsset.cs @@ -8,9 +8,15 @@ namespace MTConnect.Assets.RawMaterials { public partial class RawMaterialAsset { + /// + /// The fixed Asset type identifier ("RawMaterial") written to the Type attribute and used to recognize this asset during deserialization. + /// public const string TypeId = "RawMaterial"; + /// + /// Initializes a new RawMaterialAsset, stamping the Asset Type with . + /// public RawMaterialAsset() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Assets/RawMaterials/RawMaterialAsset.g.cs b/libraries/MTConnect.NET-Common/Assets/RawMaterials/RawMaterialAsset.g.cs index 7774ee1e2..2659a0d19 100644 --- a/libraries/MTConnect.NET-Common/Assets/RawMaterials/RawMaterialAsset.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/RawMaterials/RawMaterialAsset.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Assets.RawMaterials /// public partial class RawMaterialAsset : Asset, IRawMaterialAsset { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Asset that represents raw material."; @@ -17,77 +20,77 @@ public partial class RawMaterialAsset : Asset, IRawMaterialAsset /// Type of container holding the raw material. Examples: `Pallet`, `Canister`, `Cartridge`, `Tank`, `Bin`, `Roll`, and `Spool`. /// public string ContainerType { get; set; } - + /// /// Dimension of material currently in raw material. /// public MTConnect.Millimeter3D CurrentDimension { get; set; } - + /// /// Quantity of material currently in raw material. /// public int? CurrentQuantity { get; set; } - + /// /// Amount of material currently in raw material. /// public double? CurrentVolume { get; set; } - + /// /// Date raw material was first used. /// public System.DateTime? FirstUseDate { get; set; } - + /// /// Form of the raw material. /// public MTConnect.Assets.RawMaterials.Form Form { get; set; } - + /// /// Material has existing usable volume. /// public bool? HasMaterial { get; set; } - + /// /// Dimension of material initially placed in raw material when manufactured. /// public MTConnect.Millimeter3D InitialDimension { get; set; } - + /// /// Quantity of material initially placed in raw material when manufactured. /// public int? InitialQuantity { get; set; } - + /// /// Amount of material initially placed in raw material when manufactured. /// public double? InitialVolume { get; set; } - + /// /// Date raw material was last used. /// public System.DateTime? LastUseDate { get; set; } - + /// /// Date the raw material was created. /// public System.DateTime? ManufacturingDate { get; set; } - + /// /// Material used as the RawMaterial. /// public MTConnect.Assets.RawMaterials.IMaterial Material { get; set; } - + /// /// Name of the raw material.Examples: `Container1` and `AcrylicContainer`. /// public string Name { get; set; } - + /// /// ISO process type supported by this raw material. Examples include: `VAT_POLYMERIZATION`, `BINDER_JETTING`, `MATERIAL_EXTRUSION`, `MATERIAL_JETTING`, `SHEET_LAMINATION`, `POWDER_BED_FUSION` and `DIRECTED_ENERGY_DEPOSITION`. /// public string ProcessKind { get; set; } - + /// /// Serial number of the raw material. /// diff --git a/libraries/MTConnect.NET-Common/Assets/RawMaterials/RawMaterialAssetDescriptions.g.cs b/libraries/MTConnect.NET-Common/Assets/RawMaterials/RawMaterialAssetDescriptions.g.cs index 26d2458bb..5578fe83e 100644 --- a/libraries/MTConnect.NET-Common/Assets/RawMaterials/RawMaterialAssetDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Assets/RawMaterials/RawMaterialAssetDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Assets.RawMaterials { + /// + /// Description text for each property of RawMaterialAsset as defined by the MTConnect Standard. + /// public static class RawMaterialAssetDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Buffers/AssetBufferLoadArgs.cs b/libraries/MTConnect.NET-Common/Buffers/AssetBufferLoadArgs.cs index 0e1fc9784..8ad168e62 100644 --- a/libraries/MTConnect.NET-Common/Buffers/AssetBufferLoadArgs.cs +++ b/libraries/MTConnect.NET-Common/Buffers/AssetBufferLoadArgs.cs @@ -3,17 +3,31 @@ namespace MTConnect.Buffers { + /// + /// Reports the outcome of restoring a durable asset buffer from disk: how many assets were loaded and how long the load took. + /// public struct AssetBufferLoadArgs { + /// + /// The number of assets recovered from the durable buffer. + /// public long Count { get; } + /// + /// The elapsed time of the load operation, in milliseconds. + /// public long Duration { get; } + /// + /// Initializes the load result with the recovered asset count and elapsed duration. + /// + /// The number of assets recovered. + /// The elapsed load time in milliseconds. public AssetBufferLoadArgs(long count, long duration) { Count = count; Duration = duration; } } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-Common/Buffers/BufferObservation.cs b/libraries/MTConnect.NET-Common/Buffers/BufferObservation.cs index 752358abd..24930c90e 100644 --- a/libraries/MTConnect.NET-Common/Buffers/BufferObservation.cs +++ b/libraries/MTConnect.NET-Common/Buffers/BufferObservation.cs @@ -8,6 +8,9 @@ namespace MTConnect.Buffers { + /// + /// A compact value-type representation of an observation as stored inside an MTConnect buffer, packing the device/data-item identity, values, sequence, timestamp, and metadata into byte-coded fields for memory efficiency. + /// public struct BufferObservation { internal int _key; @@ -20,34 +23,55 @@ public struct BufferObservation internal bool _deprecated; internal bool _extended; + /// + /// The packed buffer key encoding both the device and data-item slot indices for this observation. + /// public int Key { get => _key; set => _key = value; } + /// + /// The device slot index decoded from . + /// public int DeviceIndex => GetDeviceIndexFromBufferKey(_key); + /// + /// The data-item slot index decoded from . + /// public int DataItemIndex => GetDataItemIndexFromBufferKey(_key); + /// + /// The observation's value components, kept sorted by value key. + /// public ObservationValue[] Values { get => _values; set => _values = value; } + /// + /// The buffer sequence number assigned to this observation. + /// public ulong Sequence { get => _sequence; set => _sequence = value; } + /// + /// The observation timestamp expressed as Unix time. + /// public long Timestamp { get => _timestamp; set => _timestamp = value; } + /// + /// The data-item category, decoded from and stored as a single byte. + /// public DataItemCategory Category { get @@ -65,6 +89,9 @@ public DataItemCategory Category } } + /// + /// The data-item representation, decoded from and stored as a single byte. + /// public DataItemRepresentation Representation { get @@ -84,6 +111,9 @@ public DataItemRepresentation Representation } } + /// + /// The observation quality, decoded from and stored as a single byte. + /// public Quality Quality { get @@ -101,12 +131,18 @@ public Quality Quality } } + /// + /// Indicates whether the originating data item has been deprecated. + /// public bool Deprecated { get => _deprecated; set => _deprecated = value; } + /// + /// Indicates whether the observation carries extended (vendor or non-standard) data. + /// public bool Extended { get => _extended; @@ -114,14 +150,22 @@ public bool Extended } + /// + /// Indicates whether the entry is well-formed: a non-negative key, at least one value, and positive sequence and timestamp. + /// public bool IsValid => Key >= 0 && Values != null && Values.Length > 0 && - Sequence > 0 && + Sequence > 0 && Timestamp > 0; + /// + /// Captures an observation under the given buffer key with no sequence yet assigned; values are copied and sorted by value key. + /// + /// The packed device/data-item buffer key. + /// The source observation to capture. public BufferObservation(int bufferKey, IObservation observation) { _key = bufferKey; @@ -141,6 +185,12 @@ public BufferObservation(int bufferKey, IObservation observation) else _values = null; } + /// + /// Captures an observation under the given buffer key with an explicit sequence number; values are copied and sorted by value key. + /// + /// The packed device/data-item buffer key. + /// The buffer sequence number to assign. + /// The source observation to capture. public BufferObservation(int bufferKey, ulong sequence, IObservation observation) { _key = bufferKey; @@ -160,10 +210,22 @@ public BufferObservation(int bufferKey, ulong sequence, IObservation observation else _values = null; } + /// + /// Constructs a buffer observation directly from its constituent fields, without an originating ; values are copied and sorted by value key. + /// + /// The packed device/data-item buffer key. + /// The data-item category. + /// The data-item representation. + /// The observation value components. + /// The buffer sequence number. + /// The observation timestamp as Unix time. + /// The observation quality. + /// Whether the originating data item is deprecated. + /// Whether the observation carries extended data. public BufferObservation( int bufferKey, DataItemCategory category, - DataItemRepresentation representation, + DataItemRepresentation representation, IEnumerable values, ulong sequence, long timestamp, @@ -190,8 +252,16 @@ bool extended } + /// + /// Computes a stable hash combining this observation's key and sequence, used to deduplicate and index entries. + /// public ulong CreateHash() => CreateHash(Key, Sequence); + /// + /// Computes the combined key/sequence hash for an arbitrary key and sequence by interleaving the buffer key with the 12-digit sequence space. + /// + /// The packed buffer key. + /// The buffer sequence number. public static ulong CreateHash(int key, ulong sequence) { // [DeviceIndex] [DataItemIndex] [Sequence] @@ -211,6 +281,10 @@ public static ulong CreateHash(int key, ulong sequence) } + /// + /// Returns the string value of the value component matching the given value key, or null when no such component exists. + /// + /// The value-component key to look up. public string GetValue(string valueKey) { if (valueKey != null && _values != null && _values.Length > 0) @@ -228,11 +302,19 @@ public string GetValue(string valueKey) } + /// + /// Extracts the device slot index from a packed buffer key. + /// + /// The packed buffer key. public static int GetDeviceIndexFromBufferKey(int bufferKey) { return bufferKey / 10000; } + /// + /// Extracts the data-item slot index from a packed buffer key. + /// + /// The packed buffer key. public static int GetDataItemIndexFromBufferKey(int bufferKey) { return bufferKey % 10000; diff --git a/libraries/MTConnect.NET-Common/Buffers/FileIndex.cs b/libraries/MTConnect.NET-Common/Buffers/FileIndex.cs index 5e9b7ae0c..bc0a86c99 100644 --- a/libraries/MTConnect.NET-Common/Buffers/FileIndex.cs +++ b/libraries/MTConnect.NET-Common/Buffers/FileIndex.cs @@ -7,20 +7,44 @@ namespace MTConnect.Buffers { + /// + /// Maps a stable string identifier (such as a Device UUID or DataItem Id) to the integer slot number used to name its file within a durable buffer's on-disk index. + /// public struct FileIndex { + /// + /// The index file name holding the Device UUID to slot mapping. + /// public const string DevicesFileName = "devices"; + + /// + /// The index file name holding the DataItem Id to slot mapping. + /// public const string DataItemsFileName = "dataItems"; + /// + /// The integer slot number assigned to the identifier; slots are one-based. + /// public int Index { get; set; } + /// + /// The stable string identifier mapped to . + /// public string Id { get; set; } + /// + /// Indicates whether the entry is usable, requiring a positive slot number and a non-null identifier. + /// public bool IsValid => Index > 0 && Id != null; + /// + /// Initializes a mapping entry pairing the given slot number with the given identifier. + /// + /// The integer slot number. + /// The stable string identifier. public FileIndex(int index, string id) { Index = index; @@ -28,11 +52,18 @@ public FileIndex(int index, string id) } + /// + /// Returns the entry serialized as a single index,id line, the on-disk representation used in index files. + /// public override string ToString() { return $"{Index},{Id}"; } + /// + /// Parses an index,id line back into a ; returns a default (invalid) entry when the input is empty or malformed. + /// + /// The serialized line to parse. public static FileIndex FromString(string s) { if (!string.IsNullOrEmpty(s)) @@ -48,6 +79,10 @@ public static FileIndex FromString(string s) } + /// + /// Builds a sequence of entries from an identifier-to-slot dictionary. + /// + /// The map of identifiers to slot numbers. public static IEnumerable Create(IDictionary indexes) { var fileIndexes = new List(); @@ -63,6 +98,10 @@ public static IEnumerable Create(IDictionary indexes) return fileIndexes; } + /// + /// Collapses a sequence of entries back into an identifier-to-slot dictionary. + /// + /// The entries to convert. public static IDictionary ToDictionary(IEnumerable fileIndexes) { var indexes = new Dictionary(); @@ -84,6 +123,11 @@ public static IDictionary ToDictionary(IEnumerable fileI // return FromFile(Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "buffer"), filePath); //} + /// + /// Reads and parses the index file at {basePath}/index/{filePath}, skipping malformed lines. Returns an empty sequence when the file is absent or unreadable. A relative or empty base path resolves under the application base directory's buffer folder. + /// + /// The buffer root directory; when empty defaults to the buffer folder under the application base directory. + /// The index file name to read. public static IEnumerable FromFile(string basePath, string filePath) { var fileIndexes = new List(); @@ -128,6 +172,12 @@ public static IEnumerable FromFile(string basePath, string filePath) // return ToFile(Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "buffer"), filePath, fileIndexes); //} + /// + /// Writes the given entries to {basePath}/index/{filePath}, creating the index directory if needed and overwriting any existing file. Returns true on success, false on failure or empty input. + /// + /// The buffer root directory; when empty defaults to the buffer folder under the application base directory. + /// The index file name to write. + /// The entries to persist. public static bool ToFile(string basePath, string filePath, IEnumerable fileIndexes) { if (!string.IsNullOrEmpty(filePath) && !fileIndexes.IsNullOrEmpty()) @@ -166,6 +216,10 @@ public static bool ToFile(string basePath, string filePath, IEnumerable + /// Deletes the entire index directory under the given buffer root. WARNING: this clears all identifier-to-slot mappings and can leave the buffered data files unrecoverable. + /// + /// The buffer root directory; when empty defaults to the buffer folder under the application base directory. public static void Reset(string basePath) { var baseDir = basePath; diff --git a/libraries/MTConnect.NET-Common/Buffers/IMTConnectObservationBuffer.cs b/libraries/MTConnect.NET-Common/Buffers/IMTConnectObservationBuffer.cs index b1ec393ef..2962fff03 100644 --- a/libraries/MTConnect.NET-Common/Buffers/IMTConnectObservationBuffer.cs +++ b/libraries/MTConnect.NET-Common/Buffers/IMTConnectObservationBuffer.cs @@ -37,8 +37,14 @@ public interface IMTConnectObservationBuffer : IDisposable ulong NextSequence { get; } + /// + /// The most recent observation for each non-condition buffer key, indexed by the buffer key hash. + /// IDictionary CurrentObservations { get; } + /// + /// The current set of active condition observations for each condition buffer key, indexed by the buffer key hash. + /// IDictionary> CurrentConditions { get; } diff --git a/libraries/MTConnect.NET-Common/Buffers/IObservationBufferResults.cs b/libraries/MTConnect.NET-Common/Buffers/IObservationBufferResults.cs index b65857cd7..513a75f0a 100644 --- a/libraries/MTConnect.NET-Common/Buffers/IObservationBufferResults.cs +++ b/libraries/MTConnect.NET-Common/Buffers/IObservationBufferResults.cs @@ -28,12 +28,24 @@ public interface IObservationBufferResults /// BufferObservation[] Observations { get; } + /// + /// Gets the sequence number of the first observation actually included in this result set. + /// ulong FirstObservationSequence { get; } + /// + /// Gets the sequence number of the last observation actually included in this result set. + /// ulong LastObservationSequence { get; } + /// + /// Gets the number of observations contained in this result set. + /// uint ObservationCount { get; } + /// + /// Indicates whether the requested range could be satisfied; false when the buffer no longer holds the requested sequences. + /// bool IsValid { get; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Buffers/MTConnectAssetBuffer.cs b/libraries/MTConnect.NET-Common/Buffers/MTConnectAssetBuffer.cs index 48c913323..9e97f7bc0 100644 --- a/libraries/MTConnect.NET-Common/Buffers/MTConnectAssetBuffer.cs +++ b/libraries/MTConnect.NET-Common/Buffers/MTConnectAssetBuffer.cs @@ -13,7 +13,7 @@ namespace MTConnect.Buffers /// Buffer used to store Assets /// public class MTConnectAssetBuffer : IMTConnectAssetBuffer - { + { private readonly string _id = Guid.NewGuid().ToString(); private readonly IAsset[] _storedAssets; private readonly Dictionary _assetIds = new Dictionary(); @@ -47,14 +47,24 @@ public IEnumerable AssetIds get { return _assetIds.Keys.ToList(); } } + /// + /// Raised when an asset is evicted from the buffer, either because capacity was exceeded or it was explicitly removed. + /// public event EventHandler AssetRemoved; - public MTConnectAssetBuffer() + /// + /// Initializes the buffer with the default asset capacity. + /// + public MTConnectAssetBuffer() { _storedAssets = new IAsset[BufferSize]; } + /// + /// Initializes the buffer, taking its asset capacity from the supplied agent configuration when provided. + /// + /// The agent configuration whose asset buffer size is applied; ignored when null. public MTConnectAssetBuffer(IAgentConfiguration configuration) { if (configuration != null) @@ -66,8 +76,18 @@ public MTConnectAssetBuffer(IAgentConfiguration configuration) } + /// + /// Extension point invoked after an asset is stored at a buffer slot; overridden by durable buffers to persist the change. The base implementation does nothing. + /// + /// The slot the asset was stored at. + /// The asset that was added. + /// The slot the asset previously occupied when it was an update rather than a new addition. protected virtual void OnAssetAdd(uint bufferIndex, IAsset asset, uint originalIndex) { } + /// + /// Extension point invoked after an asset is evicted; overridden by durable buffers to remove the persisted copy. The base implementation does nothing. + /// + /// The asset that was removed. protected virtual void OnAssetRemoved(IAsset asset) { } @@ -136,7 +156,7 @@ public IEnumerable GetAssets(IEnumerable assetIds) } return assets; - } + } return null; } diff --git a/libraries/MTConnect.NET-Common/Buffers/MTConnectAssetFileBuffer.cs b/libraries/MTConnect.NET-Common/Buffers/MTConnectAssetFileBuffer.cs index 7130981f8..b89d1c84e 100644 --- a/libraries/MTConnect.NET-Common/Buffers/MTConnectAssetFileBuffer.cs +++ b/libraries/MTConnect.NET-Common/Buffers/MTConnectAssetFileBuffer.cs @@ -16,10 +16,24 @@ namespace MTConnect.Buffers { + /// + /// A durable that persists assets to disk so the buffer survives restarts, writing changes on a background thread and reloading them on startup. + /// public class MTConnectAssetFileBuffer : MTConnectAssetBuffer, IDisposable { + /// + /// The default number of assets read or written per page during load and flush operations. + /// public const int DefaultPageSize = 100; + + /// + /// The root directory name under the application base directory that holds all durable buffer data. + /// public const string DirectoryBuffer = "buffer"; + + /// + /// The subdirectory name under the buffer root that holds persisted asset files. + /// public const string DirectoryAssets = "assets"; private readonly string _basePath; @@ -31,21 +45,45 @@ public class MTConnectAssetFileBuffer : MTConnectAssetBuffer, IDisposable private bool _isLoading; private ulong _pageIndex = 0; + /// + /// The interval, in milliseconds, between background flushes of queued asset changes to disk. + /// public int WriteInterval { get; set; } = 1000; + /// + /// The interval, in milliseconds, between retention passes that prune persisted assets no longer in the buffer. + /// public int RetentionInterval { get; set; } = 10000; + /// + /// The maximum number of queued asset changes written to disk in a single flush. + /// public uint MaxItemsPerWrite { get; set; } = 1000; + /// + /// The number of asset changes currently queued and awaiting a flush to disk. + /// public long QueuedItemCount => _items.Count; + /// + /// Indicates whether persisted asset files are GZip-compressed. + /// public bool UseCompression { get; set; } = true; + /// + /// Raised when the buffer begins reloading persisted assets from disk on startup. + /// public event EventHandler BufferLoadStarted; + /// + /// Raised when the startup reload completes, reporting the number of assets recovered and the elapsed time. + /// public event EventHandler BufferLoadCompleted; + /// + /// Initializes the durable asset buffer with default settings and starts the background write worker. + /// public MTConnectAssetFileBuffer() { _items = new MTConnectAssetQueue(); @@ -53,6 +91,11 @@ public MTConnectAssetFileBuffer() Start(); } + /// + /// Initializes the durable asset buffer from the supplied agent configuration, optionally rooting persistence at a custom base path, and starts the background write worker. + /// + /// The agent configuration controlling buffer capacity. + /// An optional custom buffer root directory; when null the default location is used. public MTConnectAssetFileBuffer(IAgentConfiguration configuration, string basePath = null) : base(configuration) { _basePath = basePath; @@ -61,6 +104,12 @@ public MTConnectAssetFileBuffer(IAgentConfiguration configuration, string basePa Start(); } + /// + /// Queues the added asset for persistence, unless the addition originated from the startup reload itself. + /// + /// The slot the asset was stored at. + /// The asset that was added. + /// The slot the asset previously occupied when it replaced an existing asset. protected override void OnAssetAdd(uint bufferIndex, IAsset asset, uint originalIndex) { if (!_isLoading) @@ -100,12 +149,19 @@ private void Stop() } } + /// + /// Stops the background write worker, flushing any queued asset changes to disk before releasing resources. + /// public void Dispose() { Stop(); GC.SuppressFinalize(this); } + /// + /// Deletes the entire durable asset directory under the given buffer root. WARNING: this permanently clears all persisted assets. + /// + /// The buffer root directory; when null the default location is used. public static void Reset(string basePath) { var dir = GetDirectory(basePath, false); @@ -122,6 +178,13 @@ public static void Reset(string basePath) } + /// + /// Enqueues an asset change to be flushed to disk by the background write worker. + /// + /// The buffer slot the asset occupies. + /// The asset to persist. + /// The slot the asset previously occupied when it replaced an existing asset. + /// True if the change was queued. public bool Add(uint index, IAsset asset, uint originalIndex) { // Add to internal Queue @@ -131,6 +194,10 @@ public bool Add(uint index, IAsset asset, uint originalIndex) #region "Load" + /// + /// Reloads all persisted assets from disk back into the in-memory buffer, raising and around the operation. + /// + /// True if at least one asset was recovered. public bool Load() { var found = false; @@ -268,6 +335,9 @@ private async Task WriteWorker(CancellationToken cancellationToken) } } + /// + /// Flushes every queued asset change to disk immediately, bypassing the timed write interval. + /// public void WriteAllItems() { _ = Task.Run(async () => @@ -424,7 +494,7 @@ private static string GetDirectory(string basePath, bool createIfNotExists = tru else { baseDir = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, DirectoryBuffer); - } + } string dir = Path.Combine(baseDir, DirectoryAssets); if (createIfNotExists && !Directory.Exists(dir)) Directory.CreateDirectory(dir); diff --git a/libraries/MTConnect.NET-Common/Buffers/MTConnectObservationBuffer.cs b/libraries/MTConnect.NET-Common/Buffers/MTConnectObservationBuffer.cs index d2d5119f9..a61a6b743 100644 --- a/libraries/MTConnect.NET-Common/Buffers/MTConnectObservationBuffer.cs +++ b/libraries/MTConnect.NET-Common/Buffers/MTConnectObservationBuffer.cs @@ -16,6 +16,9 @@ namespace MTConnect.Buffers /// public class MTConnectObservationBuffer : IMTConnectObservationBuffer { + /// + /// The minimum number of observations a single request must ask for before a high-priority garbage collection is forced after serving it. + /// public const int HighPriorityGC = 5000; // Minimum number of Observations requested that will trigger a High Priority Garbage Collection private readonly string _id = Guid.NewGuid().ToString(); @@ -70,6 +73,9 @@ public ulong NextSequence } + /// + /// A snapshot copy of the latest non-condition observation for each buffer key, indexed by the buffer key hash. + /// public IDictionary CurrentObservations { get @@ -78,6 +84,9 @@ public IDictionary CurrentObservations } } + /// + /// A snapshot copy of the active condition observations for each condition buffer key, indexed by the buffer key hash. + /// public IDictionary> CurrentConditions { get @@ -87,11 +96,18 @@ public IDictionary> CurrentConditions } + /// + /// Initializes the buffer with the default observation capacity. + /// public MTConnectObservationBuffer() { _archiveObservations = new CircularBuffer(BufferSize); } + /// + /// Initializes the buffer, taking its observation capacity from the supplied agent configuration when provided. + /// + /// The agent configuration whose observation buffer size is applied; ignored when null. public MTConnectObservationBuffer(IAgentConfiguration configuration) { if (configuration != null) @@ -102,6 +118,9 @@ public MTConnectObservationBuffer(IAgentConfiguration configuration) _archiveObservations = new CircularBuffer(BufferSize); } + /// + /// Releases the circular archive and clears the current observation and condition snapshots. + /// public void Dispose() { _archiveObservations = null; @@ -110,12 +129,28 @@ public void Dispose() } + /// + /// Extension point invoked when the active condition set for a key changes; overridden by durable buffers to persist the change. The base implementation does nothing. + /// + /// The new active condition set. protected virtual void OnCurrentConditionChange(IEnumerable observations) { } + /// + /// Extension point invoked after the current observation for a key is updated; overridden by durable buffers to persist the change. The base implementation does nothing. + /// + /// The observation that became current. protected virtual void OnCurrentObservationAdd(ref BufferObservation observation) { } + /// + /// Extension point invoked after the active condition set for a key is established; overridden by durable buffers to persist the change. The base implementation does nothing. + /// + /// The active condition set. protected virtual void OnCurrentConditionAdd(ref IEnumerable observations) { } + /// + /// Extension point invoked after an observation is appended to the archive; overridden by durable buffers to persist the entry. The base implementation does nothing. + /// + /// The observation appended to the archive. protected virtual void OnBufferObservationAdd(ref BufferObservation observation) { } @@ -158,11 +193,17 @@ public void IncrementSequence(uint count) #region "Internal" + /// + /// Returns a flat copy of every current non-condition observation held in the buffer. + /// protected IEnumerable GetCurrentObservations() { return new List(_currentObservations.Values); } + /// + /// Returns a flat copy of every active condition observation held in the buffer, flattening the per-key condition sets. + /// protected IEnumerable GetCurrentConditions() { var x = new List(); @@ -554,12 +595,22 @@ public IObservationBufferResults GetObservations(IEnumerable bufferKeys, ul #region "Internal" + /// + /// Wraps an observation as a and records it as the current value for its buffer key. + /// + /// The packed device/data-item buffer key. + /// The buffer sequence number to assign. + /// The observation to make current. protected void AddCurrentObservation(int bufferKey, ulong sequence, IObservation observation) { var bufferObservation = new BufferObservation(bufferKey, sequence, observation); AddCurrentObservation(bufferObservation); } + /// + /// Records the given buffer observation as the current value for its key, replacing any previous current value and notifying durable subclasses. + /// + /// The buffer observation to make current. protected void AddCurrentObservation(BufferObservation observation) { if (!observation.Values.IsNullOrEmpty()) @@ -572,7 +623,7 @@ protected void AddCurrentObservation(BufferObservation observation) _currentObservations.TryGetValue(observation._key, out var existingObservation); _currentObservations.Remove(observation._key); - + if (existingObservation.IsValid && !isUnavailable) { if (resetTriggered == ResetTriggered.NOT_SPECIFIED) @@ -611,12 +662,22 @@ protected void AddCurrentObservation(BufferObservation observation) } } + /// + /// Wraps a condition observation as a and updates the active condition set for its buffer key. + /// + /// The packed device/data-item buffer key. + /// The buffer sequence number to assign. + /// The condition observation to record. protected void AddCurrentCondition(int bufferKey, ulong sequence, IObservation observation) { var bufferObservation = new BufferObservation(bufferKey, sequence, observation); AddCurrentCondition(bufferObservation); } + /// + /// Updates the active condition set for the observation's key, applying normal/fault accumulation semantics and notifying durable subclasses. + /// + /// The condition buffer observation to record. protected void AddCurrentCondition(BufferObservation observation) { if (!observation.Values.IsNullOrEmpty()) @@ -777,12 +838,22 @@ private static ObservationValue[] GetTableValues(ref BufferObservation observati } + /// + /// Wraps an observation as a and appends it to the circular archive. + /// + /// The packed device/data-item buffer key. + /// The buffer sequence number to assign. + /// The observation to archive. protected void AddBufferObservation(int bufferKey, ulong sequence, IObservation observation) { var bufferObservation = new BufferObservation(bufferKey, sequence, observation); AddBufferObservation(ref bufferObservation); } + /// + /// Appends a single buffer observation to the circular archive and notifies durable subclasses. + /// + /// The buffer observation to archive, passed by reference to avoid copying. protected void AddBufferObservation(ref BufferObservation observation) { WriteObservation(ref observation); @@ -791,6 +862,10 @@ protected void AddBufferObservation(ref BufferObservation observation) OnBufferObservationAdd(ref observation); } + /// + /// Appends a batch of buffer observations to the circular archive in order, notifying durable subclasses for each. + /// + /// The buffer observations to archive, passed by reference to avoid copying. protected void AddBufferObservations(ref BufferObservation[] observations) { if (observations != null && observations.Length > 0) diff --git a/libraries/MTConnect.NET-Common/Buffers/MTConnectObservationFileBuffer.cs b/libraries/MTConnect.NET-Common/Buffers/MTConnectObservationFileBuffer.cs index bf53d37bd..d1bd55942 100644 --- a/libraries/MTConnect.NET-Common/Buffers/MTConnectObservationFileBuffer.cs +++ b/libraries/MTConnect.NET-Common/Buffers/MTConnectObservationFileBuffer.cs @@ -36,25 +36,55 @@ public class MTConnectObservationFileBuffer : MTConnectObservationBuffer, IDispo private bool _currentConditionUpdated; + /// + /// The interval, in milliseconds, between background flushes of queued observation changes to disk. + /// public int WriteInterval { get; set; } = 5000; + /// + /// The interval, in milliseconds, between retention passes that prune persisted observations that have aged out of the buffer. + /// public int RetentionInterval { get; set; } = 10000; + /// + /// The number of observations grouped into a single on-disk page during load and flush operations. + /// public uint PageSize { get; set; } = DefaultPageSize; + /// + /// The maximum number of queued observation changes written to disk in a single flush. + /// public int MaxItemsPerWrite { get; set; } = 50000; + /// + /// The number of observation changes currently queued and awaiting a flush to disk. + /// public long QueuedItemCount => _items.Count; + /// + /// Indicates whether persisted observation pages are GZip-compressed. + /// public bool UseCompression { get; set; } = true; + /// + /// Raised when the buffer begins reloading persisted observations from disk on startup. + /// public event EventHandler BufferLoadStarted; + /// + /// Raised when the startup reload completes, reporting the number of observations recovered and the elapsed time. + /// public event EventHandler BufferLoadCompleted; + /// + /// Raised when a retention pass completes, reporting the purged sequence range, count, and elapsed time. + /// public event EventHandler BufferRetentionCompleted; + /// + /// Initializes the durable observation buffer with default settings and starts the background write and retention workers. + /// public MTConnectObservationFileBuffer() { _items = new MTConnectObservationQueue(); @@ -62,6 +92,11 @@ public MTConnectObservationFileBuffer() Start(); } + /// + /// Initializes the durable observation buffer from the supplied agent configuration, optionally rooting persistence at a custom base path, and starts the background workers. + /// + /// The agent configuration controlling buffer capacity. + /// An optional custom buffer root directory; when null the default location is used. public MTConnectObservationFileBuffer(IAgentConfiguration configuration, string basePath = null) : base(configuration) { _basePath = basePath; @@ -71,6 +106,10 @@ public MTConnectObservationFileBuffer(IAgentConfiguration configuration, string } + /// + /// Flags the current-observation snapshot as dirty so it is rewritten on the next flush, unless the change originated from the startup reload. + /// + /// The observation that became current. protected override void OnCurrentObservationAdd(ref BufferObservation observation) { if (!_isLoading) @@ -79,6 +118,10 @@ protected override void OnCurrentObservationAdd(ref BufferObservation observatio } } + /// + /// Flags the current-condition snapshot as dirty so it is rewritten on the next flush, unless the change originated from the startup reload. + /// + /// The active condition set. protected override void OnCurrentConditionAdd(ref IEnumerable observations) { if (!_isLoading) @@ -87,6 +130,10 @@ protected override void OnCurrentConditionAdd(ref IEnumerable } } + /// + /// Queues the archived observation for persistence, unless the addition originated from the startup reload itself. + /// + /// The observation appended to the archive. protected override void OnBufferObservationAdd(ref BufferObservation observation) { if (!_isLoading) @@ -127,6 +174,9 @@ private void Stop() } } + /// + /// Stops the background workers, flushing queued observation changes to disk, then releases the base buffer resources. + /// public void Dispose() { Stop(); @@ -134,6 +184,10 @@ public void Dispose() } + /// + /// Deletes the entire durable observation directory under the given buffer root. WARNING: this permanently clears all persisted observations. + /// + /// The buffer root directory; when null the default location is used. public static void Reset(string basePath) { var dir = GetDirectory(basePath, false); @@ -152,12 +206,21 @@ public static void Reset(string basePath) #region "Add" + /// + /// Enqueues a single observation to be flushed to disk by the background write worker. + /// + /// The observation to persist. + /// True if the observation was queued. public bool Add(BufferObservation observation) { // Add to internal Queue return _items.Add(observation); } + /// + /// Enqueues a batch of observations to be flushed to disk; returns true only if every observation was queued. + /// + /// The observations to persist. public bool Add(IEnumerable observations) { if (!observations.IsNullOrEmpty()) @@ -180,6 +243,10 @@ public bool Add(IEnumerable observations) #region "Load" + /// + /// Reloads all persisted observations and current snapshots from disk back into the in-memory buffer, raising and around the operation. + /// + /// True if at least one observation was recovered. public bool Load() { var found = false; @@ -433,7 +500,7 @@ private IEnumerable ReadCurrentFile(string path) private string[] ReadFileLines(string path) { if (!string.IsNullOrEmpty(path)) - { + { try { if (File.Exists(path)) @@ -459,7 +526,7 @@ private string[] ReadFileLines(string path) { return File.ReadAllLines(path); } - } + } } catch { } } @@ -595,6 +662,9 @@ private async Task WriteWorker() } } + /// + /// Flushes every queued observation change to disk immediately, bypassing the timed write interval. + /// public void WriteAllItems() { _ = Task.Run(async () => @@ -639,7 +709,7 @@ private async Task WriteCurrentConditionItems() update = _currentConditionUpdated; _currentConditionUpdated = false; } - + if (update) { var writeItems = GetCurrentConditions(); diff --git a/libraries/MTConnect.NET-Common/Buffers/ObservationBufferLoadArgs.cs b/libraries/MTConnect.NET-Common/Buffers/ObservationBufferLoadArgs.cs index 17fcaf549..05148e54e 100644 --- a/libraries/MTConnect.NET-Common/Buffers/ObservationBufferLoadArgs.cs +++ b/libraries/MTConnect.NET-Common/Buffers/ObservationBufferLoadArgs.cs @@ -3,17 +3,31 @@ namespace MTConnect.Buffers { + /// + /// Reports the outcome of restoring a durable observation buffer from disk: how many observations were loaded and how long the load took. + /// public struct ObservationBufferLoadArgs { + /// + /// The number of observations recovered from the durable buffer. + /// public long Count { get; } + /// + /// The elapsed time of the load operation, in milliseconds. + /// public long Duration { get; } + /// + /// Initializes the load result with the recovered observation count and elapsed duration. + /// + /// The number of observations recovered. + /// The elapsed load time in milliseconds. public ObservationBufferLoadArgs(long count, long duration) { Count = count; Duration = duration; } } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-Common/Buffers/ObservationBufferResults.cs b/libraries/MTConnect.NET-Common/Buffers/ObservationBufferResults.cs index 38efe4bf0..c47234ead 100644 --- a/libraries/MTConnect.NET-Common/Buffers/ObservationBufferResults.cs +++ b/libraries/MTConnect.NET-Common/Buffers/ObservationBufferResults.cs @@ -28,15 +28,30 @@ public struct ObservationBufferResults : IObservationBufferResults /// public BufferObservation[] Observations { get; set; } + /// + /// Gets the sequence number of the first observation actually included in this result set. + /// public ulong FirstObservationSequence { get; set; } + /// + /// Gets the sequence number of the last observation actually included in this result set. + /// public ulong LastObservationSequence { get; set; } + /// + /// Gets the number of observations contained in this result set. + /// public uint ObservationCount { get; set; } + /// + /// Indicates whether the requested range could be satisfied; false when the buffer no longer holds the requested sequences. + /// public bool IsValid { get; set; } + /// + /// Creates an empty result set flagged as invalid, used to signal that the requested range could not be served. + /// public static ObservationBufferResults Invalid() { var x = new ObservationBufferResults(); diff --git a/libraries/MTConnect.NET-Common/Buffers/ObservationBufferRetentionArgs.cs b/libraries/MTConnect.NET-Common/Buffers/ObservationBufferRetentionArgs.cs index 78e82ab68..1462a5d51 100644 --- a/libraries/MTConnect.NET-Common/Buffers/ObservationBufferRetentionArgs.cs +++ b/libraries/MTConnect.NET-Common/Buffers/ObservationBufferRetentionArgs.cs @@ -3,17 +3,39 @@ namespace MTConnect.Buffers { + /// + /// Reports the outcome of a buffer retention pass, identifying the range of sequence numbers purged, how many entries were removed, and how long the pass took. + /// public struct ObservationBufferRetentionArgs { + /// + /// The first sequence number (inclusive) removed by the retention pass. + /// public ulong From { get; } + /// + /// The last sequence number (inclusive) removed by the retention pass. + /// public ulong To { get; } + /// + /// The number of observations evicted from the buffer. + /// public ulong Count { get; } + /// + /// The elapsed time of the retention pass, in milliseconds. + /// public long Duration { get; } + /// + /// Initializes the retention result with the evicted sequence range, count, and elapsed duration. + /// + /// The first sequence number removed. + /// The last sequence number removed. + /// The number of observations evicted. + /// The elapsed retention time in milliseconds. public ObservationBufferRetentionArgs(ulong from, ulong to, ulong count, long duration) { From = from; @@ -22,4 +44,4 @@ public ObservationBufferRetentionArgs(ulong from, ulong to, ulong count, long du Duration = duration; } } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-Common/Clients/IMTConnectEntityClient.cs b/libraries/MTConnect.NET-Common/Clients/IMTConnectEntityClient.cs index e0cc86c53..472a1aba5 100644 --- a/libraries/MTConnect.NET-Common/Clients/IMTConnectEntityClient.cs +++ b/libraries/MTConnect.NET-Common/Clients/IMTConnectEntityClient.cs @@ -8,12 +8,24 @@ namespace MTConnect.Clients { + /// + /// Abstraction for a client that streams MTConnect entities from an Agent, surfacing each decoded device, asset, and observation through events as it arrives. + /// public interface IMTConnectEntityClient { + /// + /// Raised when a Device entity is received from the Agent. + /// event EventHandler DeviceReceived; + /// + /// Raised when an Asset entity is received from the Agent. + /// event EventHandler AssetReceived; + /// + /// Raised when an Observation is received from the Agent. + /// event EventHandler ObservationReceived; } } diff --git a/libraries/MTConnect.NET-Common/Clients/MTConnectClientInformation.cs b/libraries/MTConnect.NET-Common/Clients/MTConnectClientInformation.cs index 5ac1da286..81bfe9e50 100644 --- a/libraries/MTConnect.NET-Common/Clients/MTConnectClientInformation.cs +++ b/libraries/MTConnect.NET-Common/Clients/MTConnectClientInformation.cs @@ -13,30 +13,62 @@ namespace MTConnect.Clients /// public class MTConnectClientInformation { + /// + /// The filename prefix ("client.information.") used to persist this state per device under the "clients" directory. + /// public const string FilenamePrefix = "client.information."; + + /// + /// The filename extension (".json") used for persisted client information. + /// public const string FilenameExtension = ".json"; + /// + /// A token regenerated on every save, used to detect that the persisted state has changed since it was last loaded. + /// [JsonPropertyName("changeToken")] public string ChangeToken { get; set; } + /// + /// The device key (UUID) this connection state belongs to. + /// [JsonPropertyName("deviceKey")] public string DeviceKey { get; set; } + /// + /// The Agent buffer instance the last sequence was read against; a change here signals the Agent restarted and the sequence is no longer valid. + /// [JsonPropertyName("instanceId")] public long InstanceId { get; set; } + /// + /// The sequence number of the last observation successfully read, so a reconnecting client can resume without gaps or duplicates. + /// [JsonPropertyName("lastSequence")] public long LastSequence { get; set; } + /// + /// Initializes empty client information, typically for deserialization. + /// public MTConnectClientInformation() { } + /// + /// Initializes client information bound to the given device, with no instance or sequence recorded yet. + /// + /// The device UUID this state tracks. public MTConnectClientInformation(string deviceUuid) { DeviceKey = deviceUuid; } + /// + /// Initializes client information bound to the given device with a known Agent instance and resume sequence. + /// + /// The device UUID this state tracks. + /// The Agent buffer instance the sequence was read against. + /// The last sequence number successfully read. public MTConnectClientInformation(string deviceUuid, long instanceId, long lastSequence = 0) { DeviceKey = deviceUuid; @@ -45,6 +77,11 @@ public MTConnectClientInformation(string deviceUuid, long instanceId, long lastS } + /// + /// Loads persisted client information for the given device, defaulting to the per-device file under the "clients" directory or an explicit (optionally relative) path; returns null when the file is missing, empty, or cannot be read. + /// + /// The device key whose state to load. + /// An optional override path; relative paths are resolved against the application base directory. public static MTConnectClientInformation Read(string deviceKey, string path = null) { var configurationPath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "clients", GenerateFilename(deviceKey)); @@ -73,6 +110,10 @@ public static MTConnectClientInformation Read(string deviceKey, string path = nu return null; } + /// + /// Persists this client information as indented JSON, regenerating first; writes to the per-device file under the "clients" directory (created if absent) unless an explicit path is given. Failures are swallowed. + /// + /// An optional override path for the saved file. public void Save(string path = null) { // Update ChangeToken diff --git a/libraries/MTConnect.NET-Common/Configurations/AdapterApplicationConfiguration.cs b/libraries/MTConnect.NET-Common/Configurations/AdapterApplicationConfiguration.cs index e10737d17..647873396 100644 --- a/libraries/MTConnect.NET-Common/Configurations/AdapterApplicationConfiguration.cs +++ b/libraries/MTConnect.NET-Common/Configurations/AdapterApplicationConfiguration.cs @@ -19,19 +19,37 @@ public class AdapterApplicationConfiguration : IAdapterApplicationConfiguration private const string BackupDirectoryName = "backup"; + /// + /// The conventional file name for a user-supplied JSON adapter configuration. + /// public const string JsonFilename = "adapter.config.json"; + /// + /// The file name of the shipped JSON configuration used as a fallback when no user JSON configuration is present. + /// public const string DefaultJsonFilename = "adapter.config.default.json"; + /// + /// The conventional file name for a user-supplied YAML adapter configuration. + /// public const string YamlFilename = "adapter.config.yaml"; + /// + /// The file name of the shipped YAML configuration used as a fallback when no user YAML configuration is present. + /// public const string DefaultYamlFilename = "adapter.config.default.yaml"; + /// + /// An opaque token regenerated each time the configuration is saved, allowing consumers to detect that the configuration has changed. + /// [JsonPropertyName("changeToken")] public string ChangeToken { get; set; } + /// + /// The file system path the configuration was loaded from; not serialized, and used as the default target when the configuration is saved. + /// [JsonIgnore] [YamlIgnore] public string Path { get; set; } @@ -106,14 +124,23 @@ public class AdapterApplicationConfiguration : IAdapterApplicationConfiguration public int ConfigurationFileRestartInterval { get; set; } + /// + /// Free-form key/value settings consumed by the adapter engine; keys correspond to engine property names with loosely typed values. + /// [JsonPropertyName("engine")] public Dictionary Engine { get; set; } + /// + /// The raw, untyped module configuration sections declared for the adapter, each later resolved to a strongly typed configuration on demand. + /// [JsonPropertyName("modules")] public IEnumerable Modules { get; set; } + /// + /// Initializes a new instance with adapter defaults (random 6-character id, 100 ms read/write intervals, duplicate filtering and timestamp output enabled, auto-start service, configuration file monitoring on). + /// public AdapterApplicationConfiguration() { Id = StringFunctions.RandomString(6); @@ -129,6 +156,10 @@ public AdapterApplicationConfiguration() } + /// + /// Returns the value of the named engine property, or null when no engine settings are present or the property is undefined. + /// + /// The engine property key to look up. public object GetEngineProperty(string propertyName) { if (!Engine.IsNullOrEmpty() && !string.IsNullOrEmpty(propertyName)) @@ -143,6 +174,9 @@ public object GetEngineProperty(string propertyName) } + /// + /// Flattens every declared module section into a single map keyed by module identifier, or null when no modules are configured. + /// public Dictionary GetModules() { if (!Modules.IsNullOrEmpty()) @@ -168,6 +202,10 @@ public Dictionary GetModules() return null; } + /// + /// Returns every module section declared under the given key as untyped objects, or null when the key is empty or no modules are configured. + /// + /// The module identifier whose sections are requested. public IEnumerable GetModules(string key) { if (!string.IsNullOrEmpty(key) && !Modules.IsNullOrEmpty()) @@ -197,6 +235,11 @@ public IEnumerable GetModules(string key) return null; } + /// + /// Returns every module section declared under the given key, round-tripped through YAML to bind each to . Sections that fail to bind are skipped. + /// + /// The strongly typed configuration the module sections are bound to. + /// The module identifier whose sections are requested. public IEnumerable GetModules(string key) { if (!string.IsNullOrEmpty(key) && !Modules.IsNullOrEmpty()) @@ -245,14 +288,31 @@ public IEnumerable GetModules(string key) } + /// + /// Loads an , preferring a JSON file in the base directory before falling back to YAML. + /// + /// An explicit configuration path, or null to auto-detect. public static AdapterApplicationConfiguration Read(string path = null) => Read(path); + /// + /// Loads an from a JSON file. + /// + /// An explicit JSON path, or null to use the conventional file in the base directory. public static AdapterApplicationConfiguration ReadJson(string path = null) => ReadJson(path); + /// + /// Loads an from a YAML file. + /// + /// An explicit YAML path, or null to use the conventional file in the base directory. public static AdapterApplicationConfiguration ReadYaml(string path = null) => ReadYaml(path); + /// + /// Loads a derived configuration, preferring the conventional JSON file in the base directory and falling back to YAML. + /// + /// The concrete configuration type to deserialize. + /// Reserved; resolution always uses the conventional file names in the base directory. public static T Read(string path = null) where T : AdapterApplicationConfiguration { var jsonPath = System.IO.Path.Combine(AppDomain.CurrentDomain.BaseDirectory, JsonFilename); @@ -267,6 +327,11 @@ public static T Read(string path = null) where T : AdapterApplicationConfigur } } + /// + /// Loads a configuration of the given runtime type, preferring the conventional JSON file in the base directory and falling back to YAML. + /// + /// The concrete configuration type to deserialize into. + /// Reserved; resolution always uses the conventional file names in the base directory. public static AdapterApplicationConfiguration Read(Type type, string path = null) { var jsonPath = System.IO.Path.Combine(AppDomain.CurrentDomain.BaseDirectory, JsonFilename); @@ -282,6 +347,11 @@ public static AdapterApplicationConfiguration Read(Type type, string path = null } + /// + /// Deserializes a derived configuration from a JSON file, ignoring comments and recording the source path. Returns null when the file is missing, empty, or cannot be parsed. + /// + /// The concrete configuration type to deserialize. + /// An explicit JSON path (resolved relative to the base directory when not rooted), or null to use the conventional file. public static T ReadJson(string path = null) where T : AdapterApplicationConfiguration { var configurationPath = System.IO.Path.Combine(AppDomain.CurrentDomain.BaseDirectory, JsonFilename); @@ -317,6 +387,11 @@ public static T ReadJson(string path = null) where T : AdapterApplicationConf return null; } + /// + /// Deserializes a configuration of the given runtime type from a JSON file, ignoring comments and recording the source path. Returns null when the file is missing, empty, or cannot be parsed. + /// + /// The concrete configuration type to deserialize into. + /// An explicit JSON path (resolved relative to the base directory when not rooted), or null to use the conventional file. public static AdapterApplicationConfiguration ReadJson(Type type, string path = null) { var configurationPath = System.IO.Path.Combine(AppDomain.CurrentDomain.BaseDirectory, JsonFilename); @@ -353,6 +428,11 @@ public static AdapterApplicationConfiguration ReadJson(Type type, string path = } + /// + /// Deserializes a derived configuration from a YAML file using camelCase naming, ignoring unmatched properties and recording the source path. Returns null when the file is missing, empty, or cannot be parsed. + /// + /// The concrete configuration type to deserialize. + /// An explicit YAML path (resolved relative to the base directory when not rooted), or null to use the conventional file. public static T ReadYaml(string path = null) where T : AdapterApplicationConfiguration { var configurationPath = System.IO.Path.Combine(AppDomain.CurrentDomain.BaseDirectory, YamlFilename); @@ -388,6 +468,11 @@ public static T ReadYaml(string path = null) where T : AdapterApplicationConf return null; } + /// + /// Deserializes a configuration of the given runtime type from a YAML file using camelCase naming, ignoring unmatched properties and recording the source path. Returns null when the file is missing, empty, or cannot be parsed. + /// + /// The concrete configuration type to deserialize into. + /// An explicit YAML path (resolved relative to the base directory when not rooted), or null to use the conventional file. public static AdapterApplicationConfiguration ReadYaml(Type type, string path = null) { var configurationPath = System.IO.Path.Combine(AppDomain.CurrentDomain.BaseDirectory, YamlFilename); @@ -425,6 +510,11 @@ public static AdapterApplicationConfiguration ReadYaml(Type type, string path = + /// + /// Serializes this configuration to JSON and writes it to disk, regenerating and optionally backing up any existing file. Write failures are swallowed. + /// + /// The destination path; when null the conventional JSON file in the base directory is used. + /// When true, an existing file is copied into a timestamped backup before being overwritten. public void SaveJson(string path = null, bool createBackup = true) { var configurationPath = System.IO.Path.Combine(AppDomain.CurrentDomain.BaseDirectory, JsonFilename); @@ -454,6 +544,11 @@ public void SaveJson(string path = null, bool createBackup = true) catch { } } + /// + /// Serializes this configuration to YAML and writes it to disk, regenerating and optionally backing up any existing file. Write failures are swallowed. + /// + /// The destination path; when null the conventional YAML file in the base directory is used. + /// When true, an existing file is copied into a timestamped backup before being overwritten. public void SaveYaml(string path = null, bool createBackup = true) { var configurationPath = System.IO.Path.Combine(AppDomain.CurrentDomain.BaseDirectory, YamlFilename); @@ -487,6 +582,11 @@ public void SaveYaml(string path = null, bool createBackup = true) } + /// + /// Binds an arbitrary configuration object to by round-tripping it through YAML, tolerating a leading sequence marker. Returns the type default when the input is null or cannot be bound. + /// + /// The target configuration type. + /// The loosely typed configuration object to convert. public static TConfiguration GetConfiguration(object controllerConfiguration) { if (controllerConfiguration != null) diff --git a/libraries/MTConnect.NET-Common/Configurations/AgentApplicationConfiguration.cs b/libraries/MTConnect.NET-Common/Configurations/AgentApplicationConfiguration.cs index 2f712959b..4540ddbee 100644 --- a/libraries/MTConnect.NET-Common/Configurations/AgentApplicationConfiguration.cs +++ b/libraries/MTConnect.NET-Common/Configurations/AgentApplicationConfiguration.cs @@ -80,13 +80,22 @@ public class AgentApplicationConfiguration : AgentConfiguration, IAgentApplicati public int ConfigurationFileRestartInterval { get; set; } + /// + /// The raw, untyped module configuration sections declared for the agent, each later resolved to a strongly typed configuration on demand. + /// [JsonPropertyName("modules")] public IEnumerable Modules { get; set; } + /// + /// The raw, untyped processor configuration sections declared for the agent's observation/asset processing pipeline. + /// [JsonPropertyName("processors")] public IEnumerable Processors { get; set; } + /// + /// Initializes a new instance on top of the base agent defaults, with no device path or service identity and configuration file monitoring enabled. + /// public AgentApplicationConfiguration() : base() { Devices = null; @@ -99,6 +108,9 @@ public AgentApplicationConfiguration() : base() } + /// + /// Flattens every declared module section into a single map keyed by module identifier, or null when no modules are configured. + /// public Dictionary GetModules() { if (!Modules.IsNullOrEmpty()) @@ -124,6 +136,10 @@ public Dictionary GetModules() return null; } + /// + /// Returns every module section declared under the given key as untyped objects, or null when the key is empty or no modules are configured. + /// + /// The module identifier whose sections are requested. public IEnumerable GetModules(string key) { if (!string.IsNullOrEmpty(key) && !Modules.IsNullOrEmpty()) @@ -153,6 +169,10 @@ public IEnumerable GetModules(string key) return null; } + /// + /// Counts the module sections declared under the given key; returns zero when the key is empty or no modules are configured. + /// + /// The module identifier to count sections for. public int GetModuleCount(string key) { if (!string.IsNullOrEmpty(key) && !Modules.IsNullOrEmpty()) @@ -178,6 +198,11 @@ public int GetModuleCount(string key) return 0; } + /// + /// Returns every module section declared under the given key bound to ; sections present with no body yield a default-constructed instance, and sections that fail to bind are skipped. + /// + /// The strongly typed configuration the module sections are bound to. + /// The module identifier whose sections are requested. public IEnumerable GetModules(string key) { if (!string.IsNullOrEmpty(key) && !Modules.IsNullOrEmpty()) @@ -234,6 +259,11 @@ public IEnumerable GetModules(string key) return null; } + /// + /// Appends a new module section under the given key to the existing module list, creating the list if necessary. No-ops when the key is empty. + /// + /// The module identifier the section is registered under. + /// The module configuration object to store. public void AddModule(string key, object moduleConfiguration) { if (!string.IsNullOrEmpty(key)) @@ -248,26 +278,33 @@ public void AddModule(string key, object moduleConfiguration) } } + /// + /// Indicates whether at least one module section is declared under the given key. + /// + /// The module identifier to test. public bool IsModuleConfigured(string key) - { - if (!string.IsNullOrEmpty(key) && !Modules.IsNullOrEmpty()) - { - foreach (var configurationObj in Modules) - { - try - { - var rootDictionary = (Dictionary)configurationObj; + { + if (!string.IsNullOrEmpty(key) && !Modules.IsNullOrEmpty()) + { + foreach (var configurationObj in Modules) + { + try + { + var rootDictionary = (Dictionary)configurationObj; if (rootDictionary.ContainsKey(key)) return true; - } - catch { } - } - } + } + catch { } + } + } - return false; - } + return false; + } + /// + /// Flattens every declared processor section into a single map keyed by processor identifier, or null when no processors are configured. + /// public Dictionary GetProcessors() { if (!Processors.IsNullOrEmpty()) @@ -293,6 +330,10 @@ public Dictionary GetProcessors() return null; } + /// + /// Returns every processor section declared under the given key as untyped objects, or null when the key is empty or no processors are configured. + /// + /// The processor identifier whose sections are requested. public IEnumerable GetProcessors(string key) { if (!string.IsNullOrEmpty(key) && !Processors.IsNullOrEmpty()) @@ -322,6 +363,11 @@ public IEnumerable GetProcessors(string key) return null; } + /// + /// Returns every processor section declared under the given key, round-tripped through YAML to bind each to . Sections that fail to bind are skipped. + /// + /// The strongly typed configuration the processor sections are bound to. + /// The processor identifier whose sections are requested. public IEnumerable GetProcessors(string key) { if (!string.IsNullOrEmpty(key) && !Processors.IsNullOrEmpty()) @@ -370,6 +416,11 @@ public IEnumerable GetProcessors(string key) } + /// + /// Binds an arbitrary configuration object to by round-tripping it through YAML; when the input is null a default-constructed instance is returned. Yields the type default when binding fails. + /// + /// The target configuration type. + /// The loosely typed configuration object to convert, or null to construct a default. public static TConfiguration GetConfiguration(object controllerConfiguration) { if (controllerConfiguration != null) diff --git a/libraries/MTConnect.NET-Common/Configurations/AgentConfiguration.cs b/libraries/MTConnect.NET-Common/Configurations/AgentConfiguration.cs index fb586993d..a27e8e4f0 100644 --- a/libraries/MTConnect.NET-Common/Configurations/AgentConfiguration.cs +++ b/libraries/MTConnect.NET-Common/Configurations/AgentConfiguration.cs @@ -19,19 +19,37 @@ public class AgentConfiguration : IAgentConfiguration private const string BackupDirectoryName = "backup"; + /// + /// The conventional file name for a user-supplied JSON agent configuration. + /// public const string JsonFilename = "agent.config.json"; + /// + /// The file name of the shipped JSON configuration used as a fallback when no user JSON configuration is present. + /// public const string DefaultJsonFilename = "agent.config.default.json"; + /// + /// The conventional file name for a user-supplied YAML agent configuration. + /// public const string YamlFilename = "agent.config.yaml"; + /// + /// The file name of the shipped YAML configuration used as a fallback when no user YAML configuration is present. + /// public const string DefaultYamlFilename = "agent.config.default.yaml"; + /// + /// An opaque token regenerated each time the configuration is saved, allowing consumers to detect that the configuration has changed. + /// [JsonPropertyName("changeToken")] public string ChangeToken { get; set; } + /// + /// The file system path the configuration was loaded from; not serialized, and used as the default target when the configuration is saved. + /// [JsonIgnore] [YamlIgnore] public string Path { get; set; } @@ -71,6 +89,9 @@ public class AgentConfiguration : IAgentConfiguration [YamlIgnore] public Version DefaultVersion { get; set; } + /// + /// The string form of used for serialization; assigning a parseable version string updates . + /// [JsonPropertyName("defaultVersion")] [YamlMember(Alias = "defaultVersion")] public string DefaultVersionValue @@ -126,6 +147,9 @@ public string DefaultVersionValue public bool EnableMetrics { get; set; } + /// + /// Initializes a new instance with the default agent settings (128K observation buffer, 1K asset buffer, latest MTConnect version, warning-level validation, unit conversion and metrics enabled). + /// public AgentConfiguration() { ObservationBufferSize = 131072; @@ -139,13 +163,30 @@ public AgentConfiguration() } + /// + /// Loads an , auto-detecting JSON or YAML; see for the resolution rules. + /// + /// An explicit configuration path, or null to probe the base directory for the conventional files. public static AgentConfiguration Read(string path = null) => Read(path); + /// + /// Loads an from a JSON file. + /// + /// An explicit JSON path, or null to use the conventional file in the base directory. public static AgentConfiguration ReadJson(string path = null) => ReadJson(path); + /// + /// Loads an from a YAML file. + /// + /// An explicit YAML path, or null to use the conventional file in the base directory. public static AgentConfiguration ReadYaml(string path = null) => ReadYaml(path); + /// + /// Loads a derived configuration, treating an explicit path as YAML and otherwise preferring a JSON file in the base directory before falling back to YAML. Returns null when no file can be read. + /// + /// The concrete configuration type to deserialize. + /// An explicit configuration path (resolved relative to the base directory when not rooted), or null to auto-detect. public static T Read(string path = null) where T : AgentConfiguration { if (!string.IsNullOrEmpty(path)) @@ -173,6 +214,11 @@ public static T Read(string path = null) where T : AgentConfiguration } } + /// + /// Loads a configuration of the given runtime type, preferring a JSON file in the base directory before falling back to YAML. + /// + /// The concrete configuration type to deserialize into. + /// An explicit configuration path, or null to auto-detect. public static AgentConfiguration Read(Type type, string path = null) { var jsonPath = System.IO.Path.Combine(AppDomain.CurrentDomain.BaseDirectory, JsonFilename); @@ -188,6 +234,11 @@ public static AgentConfiguration Read(Type type, string path = null) } + /// + /// Deserializes a derived configuration from a JSON file, ignoring comments. Returns null when the file is missing, empty, or cannot be parsed. + /// + /// The concrete configuration type to deserialize. + /// An explicit JSON path (resolved relative to the base directory when not rooted), or null to use the conventional file. public static T ReadJson(string path = null) where T : AgentConfiguration { var configurationPath = System.IO.Path.Combine(AppDomain.CurrentDomain.BaseDirectory, JsonFilename); @@ -223,6 +274,11 @@ public static T ReadJson(string path = null) where T : AgentConfiguration return null; } + /// + /// Deserializes a configuration of the given runtime type from a JSON file, ignoring comments. Returns null when the file is missing, empty, or cannot be parsed. + /// + /// The concrete configuration type to deserialize into. + /// An explicit JSON path (resolved relative to the base directory when not rooted), or null to use the conventional file. public static AgentConfiguration ReadJson(Type type, string path = null) { var configurationPath = System.IO.Path.Combine(AppDomain.CurrentDomain.BaseDirectory, JsonFilename); @@ -259,6 +315,11 @@ public static AgentConfiguration ReadJson(Type type, string path = null) } + /// + /// Deserializes a derived configuration from a YAML file using camelCase naming, ignoring unmatched properties. Returns null when the file is missing, empty, or cannot be parsed. + /// + /// The concrete configuration type to deserialize. + /// An explicit YAML path (resolved relative to the base directory when not rooted), or null to use the conventional file. public static T ReadYaml(string path = null) where T : AgentConfiguration { var configurationPath = System.IO.Path.Combine(AppDomain.CurrentDomain.BaseDirectory, YamlFilename); @@ -294,6 +355,11 @@ public static T ReadYaml(string path = null) where T : AgentConfiguration return null; } + /// + /// Deserializes a configuration of the given runtime type from a YAML file using camelCase naming, ignoring unmatched properties. Returns null when the file is missing, empty, or cannot be parsed. + /// + /// The concrete configuration type to deserialize into. + /// An explicit YAML path (resolved relative to the base directory when not rooted), or null to use the conventional file. public static AgentConfiguration ReadYaml(Type type, string path = null) { var configurationPath = System.IO.Path.Combine(AppDomain.CurrentDomain.BaseDirectory, YamlFilename); @@ -331,6 +397,11 @@ public static AgentConfiguration ReadYaml(Type type, string path = null) + /// + /// Serializes this configuration to JSON and writes it to disk, regenerating and optionally backing up any existing file. Write failures are swallowed. + /// + /// The destination path; when null the conventional JSON file in the base directory is used. + /// When true, an existing file is copied into a timestamped backup before being overwritten. public void SaveJson(string path = null, bool createBackup = true) { var configurationPath = System.IO.Path.Combine(AppDomain.CurrentDomain.BaseDirectory, JsonFilename); @@ -360,6 +431,11 @@ public void SaveJson(string path = null, bool createBackup = true) catch { } } + /// + /// Serializes this configuration to YAML and writes it to disk, regenerating and optionally backing up any existing file. Write failures are swallowed. + /// + /// The destination path; when null the conventional YAML file in the base directory is used. + /// When true, an existing file is copied into a timestamped backup before being overwritten. public void SaveYaml(string path = null, bool createBackup = true) { var configurationPath = System.IO.Path.Combine(AppDomain.CurrentDomain.BaseDirectory, YamlFilename); diff --git a/libraries/MTConnect.NET-Common/Configurations/ConfigurationFileWatcher.cs b/libraries/MTConnect.NET-Common/Configurations/ConfigurationFileWatcher.cs index fda2d3a20..b39c7389d 100644 --- a/libraries/MTConnect.NET-Common/Configurations/ConfigurationFileWatcher.cs +++ b/libraries/MTConnect.NET-Common/Configurations/ConfigurationFileWatcher.cs @@ -12,6 +12,9 @@ namespace MTConnect.Configurations /// The type of Configuration file to read public class ConfigurationFileWatcher : IConfigurationFileWatcher { + /// + /// The default polling interval, in milliseconds, used to debounce file change notifications when none is supplied. + /// protected const int DefaultInterval = 2000; private readonly string _path; @@ -21,11 +24,22 @@ public class ConfigurationFileWatcher : IConfigurationFileWatcher private bool _update = false; + /// + /// Raised when the watched file changes and is successfully re-read, supplying the freshly deserialized configuration of type . + /// public event EventHandler ConfigurationUpdated; + /// + /// Raised when a change is detected but the file cannot be read or deserialized; the event argument carries the error message. + /// public event EventHandler ErrorReceived; + /// + /// Initializes the watcher for the given file and begins monitoring it for changes. + /// + /// The full path of the configuration file to watch. + /// The debounce interval, in milliseconds, between detecting a change and re-reading the file. public ConfigurationFileWatcher(string path, int interval = DefaultInterval) { _path = path; @@ -83,6 +97,10 @@ private void ChangeReceived(object sender, FileSystemEventArgs args) } } + /// + /// Reads and deserializes the configuration from the given path. Derived classes override this to supply format-specific parsing; the base implementation returns the default value. + /// + /// The full path of the configuration file to read. protected virtual T OnRead(string path) { return default; @@ -103,6 +121,9 @@ private T ReadFile() } + /// + /// Stops monitoring and releases the underlying file system watcher and polling timer. + /// public void Dispose() { if (_watcher != null) _watcher.Dispose(); diff --git a/libraries/MTConnect.NET-Common/Configurations/DataSourceConfiguration.cs b/libraries/MTConnect.NET-Common/Configurations/DataSourceConfiguration.cs index ec7ca00f6..c0c7245d2 100644 --- a/libraries/MTConnect.NET-Common/Configurations/DataSourceConfiguration.cs +++ b/libraries/MTConnect.NET-Common/Configurations/DataSourceConfiguration.cs @@ -17,6 +17,9 @@ public class DataSourceConfiguration : IDataSourceConfiguration public int ReadInterval { get; set; } + /// + /// Initializes a new instance with the default read interval of 1000 milliseconds. + /// public DataSourceConfiguration() { ReadInterval = 1000; diff --git a/libraries/MTConnect.NET-Common/Configurations/DeviceConfiguration.cs b/libraries/MTConnect.NET-Common/Configurations/DeviceConfiguration.cs index 5dc3cb7e4..cc2e70743 100644 --- a/libraries/MTConnect.NET-Common/Configurations/DeviceConfiguration.cs +++ b/libraries/MTConnect.NET-Common/Configurations/DeviceConfiguration.cs @@ -15,6 +15,9 @@ namespace MTConnect.Configurations /// public class DeviceConfiguration : Device { + /// + /// The conventional file name (devices.xml) used when no explicit device configuration path is supplied. + /// public const string DefaultFilename = "devices.xml"; @@ -24,8 +27,16 @@ public class DeviceConfiguration : Device public string Path { get; set; } + /// + /// Initializes an empty device configuration, typically populated by a deserializer. + /// public DeviceConfiguration() { } + /// + /// Initializes a device configuration by copying the model of an existing device and recording the path it originated from. + /// + /// The source device whose information model is copied; when null no properties are copied. + /// The file path the device was read from, retained for later save operations. public DeviceConfiguration(IDevice device, string path = null) { if (device != null) diff --git a/libraries/MTConnect.NET-Common/Configurations/DeviceConfigurationFileWatcher.cs b/libraries/MTConnect.NET-Common/Configurations/DeviceConfigurationFileWatcher.cs index 0d3f8d9bd..cc09dfc74 100644 --- a/libraries/MTConnect.NET-Common/Configurations/DeviceConfigurationFileWatcher.cs +++ b/libraries/MTConnect.NET-Common/Configurations/DeviceConfigurationFileWatcher.cs @@ -21,11 +21,23 @@ public class DeviceConfigurationFileWatcher : IDisposable private bool _update = false; + /// + /// Raised once per device whenever the watched file changes and is successfully re-parsed into one or more device configurations. + /// public event EventHandler ConfigurationUpdated; + /// + /// Raised when a change is detected but the file cannot be read or parsed; the event argument carries the error message. + /// public event EventHandler ErrorReceived; + /// + /// Initializes the watcher for the given device configuration file and begins monitoring it for changes. + /// + /// The full path of the device configuration file to watch. + /// The debounce interval, in milliseconds, between detecting a change and re-reading the file. + /// The document format used to parse the file, defaulting to XML. public DeviceConfigurationFileWatcher(string path, int interval = DefaultInterval, string documentFormatter = DocumentFormat.XML) { _path = path; @@ -88,6 +100,9 @@ private void ChangeReceived(object sender, FileSystemEventArgs args) } + /// + /// Stops monitoring and releases the underlying file system watcher and polling timer. + /// public void Dispose() { if (_watcher != null) _watcher.Dispose(); diff --git a/libraries/MTConnect.NET-Common/Configurations/IAdapterApplicationConfiguration.cs b/libraries/MTConnect.NET-Common/Configurations/IAdapterApplicationConfiguration.cs index e0f6bc34d..bcd482763 100644 --- a/libraries/MTConnect.NET-Common/Configurations/IAdapterApplicationConfiguration.cs +++ b/libraries/MTConnect.NET-Common/Configurations/IAdapterApplicationConfiguration.cs @@ -10,8 +10,14 @@ namespace MTConnect.Configurations /// public interface IAdapterApplicationConfiguration : IDataSourceConfiguration { + /// + /// An opaque token that changes whenever the underlying configuration source is reloaded, allowing consumers to detect that the configuration has been replaced. + /// string ChangeToken { get; } + /// + /// The file system path the configuration was loaded from, used as the default target when the configuration is saved back to disk. + /// string Path { get; } @@ -71,18 +77,40 @@ public interface IAdapterApplicationConfiguration : IDataSourceConfiguration int ConfigurationFileRestartInterval { get; set; } + /// + /// Free-form key/value settings consumed by the adapter engine; keys correspond to engine property names with loosely typed values. + /// Dictionary Engine { get; set; } + /// + /// The raw, untyped module configuration sections declared for the adapter, each later resolved to a strongly typed configuration on demand. + /// IEnumerable Modules { get; set; } + /// + /// Returns the value of the named engine property, or null when the property is not present. + /// + /// The engine property key to look up. object GetEngineProperty(string propertyName); + /// + /// Returns every configured module section keyed by its declared module identifier. + /// Dictionary GetModules(); + /// + /// Returns the configured module sections registered under the given module key as untyped objects. + /// + /// The module identifier whose sections are requested. IEnumerable GetModules(string key); + /// + /// Returns the configured module sections registered under the given module key, each deserialized to . + /// + /// The strongly typed configuration the module sections are bound to. + /// The module identifier whose sections are requested. IEnumerable GetModules(string key); } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Configurations/IAgentApplicationConfiguration.cs b/libraries/MTConnect.NET-Common/Configurations/IAgentApplicationConfiguration.cs index e40526ed5..b13c78a65 100644 --- a/libraries/MTConnect.NET-Common/Configurations/IAgentApplicationConfiguration.cs +++ b/libraries/MTConnect.NET-Common/Configurations/IAgentApplicationConfiguration.cs @@ -66,26 +66,64 @@ public interface IAgentApplicationConfiguration : IAgentConfiguration int ConfigurationFileRestartInterval { get; set; } + /// + /// The raw, untyped module configuration sections declared for the agent, each later resolved to a strongly typed configuration on demand. + /// IEnumerable Modules { get; set; } + /// + /// The raw, untyped processor configuration sections declared for the agent's observation/asset processing pipeline. + /// IEnumerable Processors { get; set; } + /// + /// Returns every configured module section keyed by its declared module identifier. + /// Dictionary GetModules(); + /// + /// Returns the configured module sections registered under the given module key as untyped objects. + /// + /// The module identifier whose sections are requested. IEnumerable GetModules(string key); + /// + /// Returns the number of module sections configured under the given module key. + /// + /// The module identifier to count sections for. int GetModuleCount(string key); + /// + /// Returns the configured module sections registered under the given module key, each deserialized to . + /// + /// The strongly typed configuration the module sections are bound to. + /// The module identifier whose sections are requested. IEnumerable GetModules(string key); + /// + /// Indicates whether at least one module section is configured under the given module key. + /// + /// The module identifier to test. bool IsModuleConfigured(string key); - Dictionary GetProcessors(); + /// + /// Returns every configured processor section keyed by its declared processor identifier. + /// + Dictionary GetProcessors(); + /// + /// Returns the configured processor sections registered under the given processor key as untyped objects. + /// + /// The processor identifier whose sections are requested. IEnumerable GetProcessors(string key); + /// + /// Returns the configured processor sections registered under the given processor key, each deserialized to . + /// + /// The strongly typed configuration the processor sections are bound to. + /// The processor identifier whose sections are requested. IEnumerable GetProcessors(string key); } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Configurations/IAgentConfiguration.cs b/libraries/MTConnect.NET-Common/Configurations/IAgentConfiguration.cs index 059643cfa..7136d971d 100644 --- a/libraries/MTConnect.NET-Common/Configurations/IAgentConfiguration.cs +++ b/libraries/MTConnect.NET-Common/Configurations/IAgentConfiguration.cs @@ -11,8 +11,14 @@ namespace MTConnect.Configurations /// public interface IAgentConfiguration { + /// + /// An opaque token that changes whenever the underlying configuration source is reloaded, allowing consumers to detect that the configuration has been replaced. + /// string ChangeToken { get; } + /// + /// The file system path the configuration was loaded from, used as the default target when the configuration is saved back to disk. + /// string Path { get; } @@ -76,8 +82,18 @@ public interface IAgentConfiguration bool EnableMetrics { get; } + /// + /// Serializes this configuration to JSON and writes it to disk. + /// + /// The destination path; when null the path the configuration was loaded from is used. + /// When true, an existing file at the destination is preserved as a backup before being overwritten. void SaveJson(string path = null, bool createBackup = true); + /// + /// Serializes this configuration to YAML and writes it to disk. + /// + /// The destination path; when null the path the configuration was loaded from is used. + /// When true, an existing file at the destination is preserved as a backup before being overwritten. void SaveYaml(string path = null, bool createBackup = true); } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Configurations/IConfigurationFileWatcher.cs b/libraries/MTConnect.NET-Common/Configurations/IConfigurationFileWatcher.cs index 0a3e07e17..a057ff0a9 100644 --- a/libraries/MTConnect.NET-Common/Configurations/IConfigurationFileWatcher.cs +++ b/libraries/MTConnect.NET-Common/Configurations/IConfigurationFileWatcher.cs @@ -10,8 +10,14 @@ namespace MTConnect.Configurations /// public interface IConfigurationFileWatcher : IDisposable { + /// + /// Raised when the watched file changes and is successfully re-read, supplying the freshly deserialized configuration of type . + /// event EventHandler ConfigurationUpdated; + /// + /// Raised when a change is detected but the file cannot be read or deserialized; the event argument carries the error message. + /// event EventHandler ErrorReceived; } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Degree3D.cs b/libraries/MTConnect.NET-Common/Degree3D.cs index 0706ac1e3..f0e10401b 100644 --- a/libraries/MTConnect.NET-Common/Degree3D.cs +++ b/libraries/MTConnect.NET-Common/Degree3D.cs @@ -14,25 +14,47 @@ public class Degree3D private static readonly Regex _regex = new Regex(@"([0-9\.]*) ([0-9\.]*) ([0-9\.]*)"); + /// + /// The rotation in degrees about the X axis. + /// public double A { get; set; } + /// + /// The rotation in degrees about the Y axis. + /// public double B { get; set; } + /// + /// The rotation in degrees about the Z axis. + /// public double C { get; set; } + /// + /// Initializes an angular rotation from its three axis components in degrees. + /// + /// The rotation about the X axis. + /// The rotation about the Y axis. + /// The rotation about the Z axis. public Degree3D(double a, double b, double c) { A = a; - B = b; + B = b; C = c; } + /// + /// Renders the rotation in the MTConnect space-separated "A B C" form. + /// public override string ToString() { return $"{A} {B} {C}"; } + /// + /// Parses a space-separated "A B C" string into an angular rotation; returns null when the input is empty or does not match the expected form. + /// + /// The space-separated rotation triple. public static Degree3D FromString(string input) { if (!string.IsNullOrEmpty(input)) diff --git a/libraries/MTConnect.NET-Common/Delegates.cs b/libraries/MTConnect.NET-Common/Delegates.cs index 40b2fc87a..0ed5696fe 100644 --- a/libraries/MTConnect.NET-Common/Delegates.cs +++ b/libraries/MTConnect.NET-Common/Delegates.cs @@ -10,36 +10,56 @@ namespace MTConnect { + /// Handles a received MTConnectDevices response document. public delegate void MTConnectDevicesHandler(IDevicesResponseDocument document); + /// Handles a request for the Devices of the given device UUID. public delegate void MTConnectDevicesRequestedHandler(string deviceUuid); + /// Handles a received MTConnectStreams document, identified by its document ID. public delegate void MTConnectStreamsHandler(string documentId); + /// Handles a request for the Streams of the given device UUID. public delegate void MTConnectStreamsRequestedHandler(string deviceUuid); + /// Handles a received MTConnectAssets response document. public delegate void MTConnectAssetsHandler(IAssetsResponseDocument document); + /// Handles a request for the assets with the given asset IDs. public delegate void MTConnectAssetsRequestedHandler(IEnumerable assetIds); + /// Handles a request for all assets belonging to the given device UUID. public delegate void MTConnectDeviceAssetsRequestedHandler(string deviceUuid); + /// Handles a received MTConnectError response document. public delegate void MTConnectErrorHandler(IErrorResponseDocument errorDocument); + /// Handles the validation result for a Component of the given device. public delegate void MTConnectComponentValidationHandler(string deviceUuid, IComponent component, ValidationResult validationResults); + /// Handles the validation result for a Composition of the given device. public delegate void MTConnectCompositionValidationHandler(string deviceUuid, IComposition composition, ValidationResult validationResults); + /// Handles the validation result for a DataItem of the given device. public delegate void MTConnectDataItemValidationHandler(string deviceUuid, IDataItem dataItem, ValidationResult validationResults); + /// Handles the validation result for an observation of the given device DataItem. public delegate void MTConnectObservationValidationHandler(string deviceUuid, string dataItemKey, ValidationResult validationResults); + /// Handles the validation result for an Asset. public delegate void MTConnectAssetValidationHandler(IAsset asset, AssetValidationResult validationResults); + /// Handles a raw XML payload. public delegate void XmlHandler(string xml); + /// Handles a connection-level error. public delegate void ConnectionErrorHandler(Exception ex); + /// Handles an internal (non-connection) error. public delegate void InternalErrorHandler(Exception ex); + /// Handles a client status change for the given endpoint URL. public delegate void ClientStatusHandler(string url); + /// Handles a stream status change for the given endpoint URL. public delegate void StreamStatusHandler(string url); + /// Handles a DataItem value received from an adapter, including its key components and timestamp. public delegate void AdapterDataItemHandler(string deviceKey, string dataItemKey, string valueKey, string value, long timestamp); + /// Handles an Asset received from an adapter for the given device. public delegate void AdapterAssetHandler(string deviceKey, IAsset asset); } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/AbstractDataItemRelationship.cs b/libraries/MTConnect.NET-Common/Devices/AbstractDataItemRelationship.cs index 0e6f73b33..aa7288452 100644 --- a/libraries/MTConnect.NET-Common/Devices/AbstractDataItemRelationship.cs +++ b/libraries/MTConnect.NET-Common/Devices/AbstractDataItemRelationship.cs @@ -19,11 +19,20 @@ public string Hash } + /// + /// Computes a content hash for this relationship that changes whenever its hashed properties change. + /// + /// A SHA-1 hash string identifying the current state of this relationship. public string GenerateHash() { return GenerateHash(this); } + /// + /// Computes a content hash for the specified DataItem relationship. + /// + /// The relationship to hash. + /// A SHA-1 hash string, or null when is null. public static string GenerateHash(IAbstractDataItemRelationship relationship) { if (relationship != null) diff --git a/libraries/MTConnect.NET-Common/Devices/AbstractDataItemRelationship.g.cs b/libraries/MTConnect.NET-Common/Devices/AbstractDataItemRelationship.g.cs index c7ba24485..d4be03ddb 100644 --- a/libraries/MTConnect.NET-Common/Devices/AbstractDataItemRelationship.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/AbstractDataItemRelationship.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices /// public abstract partial class AbstractDataItemRelationship : IAbstractDataItemRelationship { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Association between a DataItem and another entity."; @@ -17,7 +20,7 @@ public abstract partial class AbstractDataItemRelationship : IAbstractDataItemRe /// Reference to the related entity's `id`. /// public string IdRef { get; set; } - + /// /// Descriptive name associated with this AbstractDataItemRelationship. /// diff --git a/libraries/MTConnect.NET-Common/Devices/AbstractDataItemRelationshipDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/AbstractDataItemRelationshipDescriptions.g.cs index 49a994d04..d04a40d9d 100644 --- a/libraries/MTConnect.NET-Common/Devices/AbstractDataItemRelationshipDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/AbstractDataItemRelationshipDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each property of AbstractDataItemRelationship as defined by the MTConnect Standard. + /// public static class AbstractDataItemRelationshipDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Agent.cs b/libraries/MTConnect.NET-Common/Devices/Agent.cs index 36ded829f..580d287e0 100644 --- a/libraries/MTConnect.NET-Common/Devices/Agent.cs +++ b/libraries/MTConnect.NET-Common/Devices/Agent.cs @@ -16,9 +16,16 @@ namespace MTConnect.Devices /// /// Agent is a Device representing the MTConnect Agent and all its connected data sources. /// - public class Agent : Device + public class Agent : Device { + /// + /// The MTConnect type identifier for the Agent Device. + /// public new const string TypeId = "Agent"; + + /// + /// The standard description text shown for the Agent Device type. + /// public new const string DescriptionText = "Agent is a Device representing the MTConnect Agent and all its connected data sources."; private const string AdaptersId = "__adapters__"; @@ -26,11 +33,20 @@ public class Agent : Device private readonly MTConnectAgent _agent; + /// + /// The human-readable description of the Agent Device type. + /// public override string TypeDescription => DescriptionText; + /// + /// The earliest MTConnect Standard version in which the Agent Device type is defined. + /// public override Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new, empty Agent Device with empty child collections. + /// public Agent() { Type = TypeId; @@ -39,6 +55,10 @@ public Agent() Compositions = new List(); } + /// + /// Initializes a new Agent Device that represents the given running agent, deriving its Id, name, uuid, and version from it. + /// + /// The running MTConnect agent this Device represents. public Agent(MTConnectAgent agent) { Type = TypeId; @@ -56,6 +76,10 @@ public Agent(MTConnectAgent agent) } } + /// + /// Populates this Agent Device with the standard set of agent DataItems + /// (availability, application and operating-system metadata, device add/remove/change, and asset events). + /// public void InitializeDataItems() { var dataItems = new List(); @@ -92,6 +116,9 @@ public void InitializeDataItems() DataItems = dataItems; } + /// + /// Publishes the initial observations for this Agent Device's standard DataItems to the associated agent. + /// public void InitializeObservations() { if (_agent != null) diff --git a/libraries/MTConnect.NET-Common/Devices/CellDefinition.g.cs b/libraries/MTConnect.NET-Common/Devices/CellDefinition.g.cs index 08671edfb..80b1fbc8b 100644 --- a/libraries/MTConnect.NET-Common/Devices/CellDefinition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/CellDefinition.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices /// public class CellDefinition : ICellDefinition { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Semantic definition of a Cell."; @@ -17,27 +20,27 @@ public class CellDefinition : ICellDefinition /// Textual description for CellDefinition. /// public string Description { get; set; } - + /// /// Unique identification of the Cell in the Definition. key. /// public string Key { get; set; } - + /// /// Key. /// public string KeyType { get; set; } - + /// /// SubType. See DataItem. /// public string SubType { get; set; } - + /// /// Type. See DataItem Types. /// public string Type { get; set; } - + /// /// Units. See Value Properties of DataItem. /// diff --git a/libraries/MTConnect.NET-Common/Devices/CellDefinitionDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/CellDefinitionDescriptions.g.cs index 1b2c0fc28..3f98d9f6e 100644 --- a/libraries/MTConnect.NET-Common/Devices/CellDefinitionDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/CellDefinitionDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each property of CellDefinition as defined by the MTConnect Standard. + /// public static class CellDefinitionDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Component.cs b/libraries/MTConnect.NET-Common/Devices/Component.cs index 322234d02..d9d80a579 100644 --- a/libraries/MTConnect.NET-Common/Devices/Component.cs +++ b/libraries/MTConnect.NET-Common/Devices/Component.cs @@ -38,9 +38,15 @@ private struct IdFormatConfiguration } + /// + /// The MTConnect entity classification for this object, which is always . + /// public MTConnectEntityType EntityType => MTConnectEntityType.Component; + /// + /// The DataItems defined directly on this Component. + /// public IEnumerable DataItems { get; set; } /// @@ -60,23 +66,23 @@ private struct IdFormatConfiguration private string _hash; - /// - /// Condensed message digest from a secure one-way hash function. FIPS PUB 180-4 - /// - public string Hash - { - get - { - if (_hash == null) _hash = GenerateHash(); - return _hash; - } - } + /// + /// Condensed message digest from a secure one-way hash function. FIPS PUB 180-4 + /// + public string Hash + { + get + { + if (_hash == null) _hash = GenerateHash(); + return _hash; + } + } - /// - /// The text description that describes what the Component Type represents - /// - public virtual string TypeDescription => DescriptionText; + /// + /// The text description that describes what the Component Type represents + /// + public virtual string TypeDescription => DescriptionText; /// /// Gets whether the Component is an Organizer Type @@ -117,30 +123,51 @@ public string Hash public virtual Version MinimumVersion => DefaultMinimumVersion; + /// + /// The pattern used to generate Ids for child Components added to this Component. + /// public string ComponentIdFormat { get; set; } + /// + /// The pattern used to generate Ids for child Compositions added to this Component. + /// public string CompositionIdFormat { get; set; } + /// + /// The pattern used to generate Ids for DataItems added to this Component. + /// public string DataItemIdFormat { get; set; } + /// + /// Initializes a new Component with empty child collections and the default Id-format patterns. + /// public Component() { Components = new List(); Compositions = new List(); DataItems = new List(); - ComponentIdFormat = _defaultComponentIdFormat; - CompositionIdFormat = _defaultCompositionIdFormat; + ComponentIdFormat = _defaultComponentIdFormat; + CompositionIdFormat = _defaultCompositionIdFormat; DataItemIdFormat = _defaultDataItemIdFormat; } + /// + /// Computes a content hash for this Component that changes whenever its hashed members change. + /// + /// A SHA-1 hash string identifying the current state of this Component. public string GenerateHash() { return GenerateHash(this); } + /// + /// Computes a content hash for the specified Component from its hashed members and child entities. + /// + /// The Component to hash. + /// A SHA-1 hash string, or null when is null. public static string GenerateHash(IComponent component) { if (component != null) @@ -184,6 +211,11 @@ public static string GenerateHash(IComponent component) + /// + /// Builds the ordered list of Id segments from the containing hierarchy down to the Component itself. + /// + /// The Component whose Id path is built. + /// The Id segments from the outermost container to the Component, or null when is null. public static string[] GenerateIdPaths(IComponent component) { if (component != null) @@ -203,6 +235,11 @@ public static string[] GenerateIdPaths(IComponent component) return null; } + /// + /// Builds the slash-delimited Id path string from the containing hierarchy down to the Component itself. + /// + /// The Component whose Id path is built. + /// The Id segments joined with '/', or null when no path is available. public static string GenerateIdPath(IComponent component) { if (component != null && !component.IdPaths.IsNullOrEmpty()) @@ -213,6 +250,11 @@ public static string GenerateIdPath(IComponent component) return null; } + /// + /// Builds the ordered list of Type segments from the containing hierarchy down to the Component itself. + /// + /// The Component whose Type path is built. + /// The Type segments from the outermost container to the Component, or null when is null. public static string[] GenerateTypePaths(IComponent component) { if (component != null) @@ -232,6 +274,11 @@ public static string[] GenerateTypePaths(IComponent component) return null; } + /// + /// Builds the slash-delimited Type path string from the containing hierarchy down to the Component itself. + /// + /// The Component whose Type path is built. + /// The Type segments joined with '/', or null when no path is available. public static string GenerateTypePath(IComponent component) { if (component != null && !component.TypePaths.IsNullOrEmpty()) @@ -263,7 +310,7 @@ public IEnumerable GetComponents() return !l.IsNullOrEmpty() ? l : null; } - private IEnumerable GetComponents(IComponent component) + private IEnumerable GetComponents(IComponent component) { var l = new List(); @@ -281,35 +328,35 @@ private IEnumerable GetComponents(IComponent component) return !l.IsNullOrEmpty() ? l : null; } - /// - /// Return the first Component matching the Type - /// - public IComponent GetComponent(string type, string name = null, SearchType searchType = SearchType.AnyLevel) - { - if (!string.IsNullOrEmpty(type)) - { - IEnumerable components = null; - switch (searchType) - { - case SearchType.Child: components = Components; break; - case SearchType.AnyLevel: components = GetComponents(); break; - } - - if (!components.IsNullOrEmpty()) - { - if (!string.IsNullOrEmpty(name)) - { - return components.FirstOrDefault(o => o.Type == type && o.Name == name); - } - else - { - return components.FirstOrDefault(o => o.Type == type); - } - } - } - - return null; - } + /// + /// Return the first Component matching the Type + /// + public IComponent GetComponent(string type, string name = null, SearchType searchType = SearchType.AnyLevel) + { + if (!string.IsNullOrEmpty(type)) + { + IEnumerable components = null; + switch (searchType) + { + case SearchType.Child: components = Components; break; + case SearchType.AnyLevel: components = GetComponents(); break; + } + + if (!components.IsNullOrEmpty()) + { + if (!string.IsNullOrEmpty(name)) + { + return components.FirstOrDefault(o => o.Type == type && o.Name == name); + } + else + { + return components.FirstOrDefault(o => o.Type == type); + } + } + } + + return null; + } /// /// Return the first Component matching the Type @@ -333,31 +380,31 @@ public IComponent GetComponent(string name = null, SearchType search /// Return All Components matching the Type /// public IEnumerable GetComponents(string type, string name = null, SearchType searchType = SearchType.AnyLevel) - { - if (!string.IsNullOrEmpty(type)) - { - IEnumerable components = null; - switch (searchType) - { - case SearchType.Child: components = Components; break; - case SearchType.AnyLevel: components = GetComponents(); break; - } - - if (!components.IsNullOrEmpty()) - { + { + if (!string.IsNullOrEmpty(type)) + { + IEnumerable components = null; + switch (searchType) + { + case SearchType.Child: components = Components; break; + case SearchType.AnyLevel: components = GetComponents(); break; + } + + if (!components.IsNullOrEmpty()) + { if (!string.IsNullOrEmpty(name)) { - return components.Where(o => o.Type == type && o.Name == name); - } + return components.Where(o => o.Type == type && o.Name == name); + } else { - return components.Where(o => o.Type == type); - } - } - } + return components.Where(o => o.Type == type); + } + } + } - return null; - } + return null; + } /// /// Return All Components matching the Type @@ -392,7 +439,7 @@ public void AddComponent(IComponent component) if (!string.IsNullOrEmpty(Id) && string.IsNullOrEmpty(component.Id)) { ResetIds(component); - } + } var components = new List(); @@ -414,11 +461,11 @@ public void AddComponents(IEnumerable components) { if (!components.IsNullOrEmpty()) { - foreach (var component in components) - { - AddComponent(component); - } - } + foreach (var component in components) + { + AddComponent(component); + } + } } @@ -780,51 +827,51 @@ public IDataItem GetDataItemByKey(string dataItemKey) return null; } - /// - /// Return the first DataItem matching the Type - /// - public IDataItem GetDataItemByType(string type, SearchType searchType = SearchType.Child) - { - if (!string.IsNullOrEmpty(type)) - { - IEnumerable dataItems = null; - switch (searchType) - { - case SearchType.Child: dataItems = DataItems; break; - case SearchType.AnyLevel: dataItems = GetDataItems(); break; - } + /// + /// Return the first DataItem matching the Type + /// + public IDataItem GetDataItemByType(string type, SearchType searchType = SearchType.Child) + { + if (!string.IsNullOrEmpty(type)) + { + IEnumerable dataItems = null; + switch (searchType) + { + case SearchType.Child: dataItems = DataItems; break; + case SearchType.AnyLevel: dataItems = GetDataItems(); break; + } - if (!dataItems.IsNullOrEmpty()) - { - return dataItems.FirstOrDefault(o => o.Type == type.ToUnderscoreUpper()); - } - } + if (!dataItems.IsNullOrEmpty()) + { + return dataItems.FirstOrDefault(o => o.Type == type.ToUnderscoreUpper()); + } + } - return null; - } + return null; + } /// /// Return the first DataItem matching the Type and SubType /// public IDataItem GetDataItemByType(string type, string subType, SearchType searchType = SearchType.Child) - { - if (!string.IsNullOrEmpty(type)) - { - IEnumerable dataItems = null; - switch (searchType) - { - case SearchType.Child: dataItems = DataItems; break; - case SearchType.AnyLevel: dataItems = GetDataItems(); break; - } - - if (!dataItems.IsNullOrEmpty()) - { - return dataItems.FirstOrDefault(o => o.Type == type.ToUnderscoreUpper() && o.SubType == subType.ToUnderscoreUpper()); - } - } - - return null; - } + { + if (!string.IsNullOrEmpty(type)) + { + IEnumerable dataItems = null; + switch (searchType) + { + case SearchType.Child: dataItems = DataItems; break; + case SearchType.AnyLevel: dataItems = GetDataItems(); break; + } + + if (!dataItems.IsNullOrEmpty()) + { + return dataItems.FirstOrDefault(o => o.Type == type.ToUnderscoreUpper() && o.SubType == subType.ToUnderscoreUpper()); + } + } + + return null; + } /// /// Return the first DataItem matching the Type @@ -848,47 +895,47 @@ public IDataItem GetDataItem(string subType = null, SearchType search /// Return All DataItems matching the Type /// public IEnumerable GetDataItemsByType(string type, SearchType searchType = SearchType.Child) - { - if (!string.IsNullOrEmpty(type)) - { - IEnumerable dataItems = null; - switch (searchType) - { - case SearchType.Child: dataItems = DataItems; break; - case SearchType.AnyLevel: dataItems = GetDataItems(); break; - } - - if (!dataItems.IsNullOrEmpty()) - { - return dataItems.Where(o => o.Type == type.ToUnderscoreUpper()); - } - } - - return null; - } - - /// - /// Return All DataItems matching the Type and SubType - /// - public IEnumerable GetDataItemsByType(string type, string subType, SearchType searchType = SearchType.Child) - { - if (!string.IsNullOrEmpty(type)) - { - IEnumerable dataItems = null; - switch (searchType) - { - case SearchType.Child: dataItems = DataItems; break; - case SearchType.AnyLevel: dataItems = GetDataItems(); break; - } - - if (!dataItems.IsNullOrEmpty()) - { - return dataItems.Where(o => o.Type == type.ToUnderscoreUpper() && o.SubType == subType.ToUnderscoreUpper()); - } - } - - return null; - } + { + if (!string.IsNullOrEmpty(type)) + { + IEnumerable dataItems = null; + switch (searchType) + { + case SearchType.Child: dataItems = DataItems; break; + case SearchType.AnyLevel: dataItems = GetDataItems(); break; + } + + if (!dataItems.IsNullOrEmpty()) + { + return dataItems.Where(o => o.Type == type.ToUnderscoreUpper()); + } + } + + return null; + } + + /// + /// Return All DataItems matching the Type and SubType + /// + public IEnumerable GetDataItemsByType(string type, string subType, SearchType searchType = SearchType.Child) + { + if (!string.IsNullOrEmpty(type)) + { + IEnumerable dataItems = null; + switch (searchType) + { + case SearchType.Child: dataItems = DataItems; break; + case SearchType.AnyLevel: dataItems = GetDataItems(); break; + } + + if (!dataItems.IsNullOrEmpty()) + { + return dataItems.Where(o => o.Type == type.ToUnderscoreUpper() && o.SubType == subType.ToUnderscoreUpper()); + } + } + + return null; + } /// /// Return All DataItems matching the Type and SubType @@ -987,6 +1034,13 @@ public void AddDataItem(object subType) where TDataItem : IDataItem } } + /// + /// Creates a DataItem from the given category, type, and optional subtype and adds it to this Component. + /// + /// The category (Sample, Event, or Condition) of the DataItem. + /// The Type that defines what the DataItem represents. + /// An optional SubType that further refines the Type. + /// An optional explicit Id; when omitted an Id is generated from the format pattern. public void AddDataItem(DataItemCategory category, string type, string subType = null, string dataItemId = null) { if (!string.IsNullOrEmpty(type)) @@ -1041,24 +1095,24 @@ public void RemoveDataItem(string dataItemId) } } - #endregion + #endregion - #region "ID" + #region "ID" - internal static void ResetIds(IComponent component) - { + internal static void ResetIds(IComponent component) + { if (component != null) { - ((Component)component).Id = CreateContainerId(component, component.ComponentIdFormat); + ((Component)component).Id = CreateContainerId(component, component.ComponentIdFormat); - // Set Child Component IDs - if (!component.Components.IsNullOrEmpty()) - { - foreach (var subcomponent in component.Components) - { + // Set Child Component IDs + if (!component.Components.IsNullOrEmpty()) + { + foreach (var subcomponent in component.Components) + { ResetIds(subcomponent); - } - } + } + } // Set Child Composition IDs if (!component.Compositions.IsNullOrEmpty()) @@ -1071,14 +1125,14 @@ internal static void ResetIds(IComponent component) // Set Child DataItem IDs if (!component.DataItems.IsNullOrEmpty()) - { - foreach (var dataItem in component.DataItems) - { + { + foreach (var dataItem in component.DataItems) + { ResetId(component, dataItem); - } - } - } - } + } + } + } + } internal static void ResetIds(IComposition composition) { @@ -1099,19 +1153,32 @@ internal static void ResetIds(IComposition composition) } internal static void ResetId(IContainer container, IDataItem dataItem) - { - if (container != null && dataItem != null) - { - ((DataItem)dataItem).Id = CreateDataItemId(container, dataItem, container.DataItemIdFormat); - } - } + { + if (container != null && dataItem != null) + { + ((DataItem)dataItem).Id = CreateDataItemId(container, dataItem, container.DataItemIdFormat); + } + } - public static string CreateId(string parentId, string name) + /// + /// Builds a Component Id by combining a parent Id with a name segment. + /// + /// The Id of the containing Component or Device. + /// The name segment to append. + /// The composed Id in the form "parentId_name". + public static string CreateId(string parentId, string name) { return $"{parentId}_{name}"; } + /// + /// Builds a Component Id from a parent Id, a name segment, and an optional suffix. + /// + /// The Id of the containing Component or Device. + /// The name segment to append. + /// An optional suffix appended after the name when present. + /// The composed Id. public static string CreateId(string parentId, string name, string suffix) { if (!string.IsNullOrEmpty(suffix)) @@ -1125,10 +1192,16 @@ public static string CreateId(string parentId, string name, string suffix) } - public static string CreateContainerId(IContainer container, string pattern) - { - if (container != null) - { + /// + /// Builds an Id for a container by substituting its property values into the supplied format pattern. + /// + /// The container (Component or Device) supplying the substitution values. + /// The Id format pattern containing replaceable placeholders. + /// The resolved Id, or null when is null. + public static string CreateContainerId(IContainer container, string pattern) + { + if (container != null) + { var result = pattern; var configurations = GetIdFormatConfigurations(pattern); @@ -1143,24 +1216,31 @@ public static string CreateContainerId(IContainer container, string pattern) } return result; - } + } - return null; - } + return null; + } - public static string CreateDataItemId(IContainer container, IDataItem dataItem, string pattern) + /// + /// Builds an Id for a DataItem by substituting container and DataItem property values into the supplied format pattern. + /// + /// The container (Component or Device) supplying contextual substitution values. + /// The DataItem supplying its own substitution values. + /// The Id format pattern containing replaceable placeholders. + /// The resolved Id, or null when or is null. + public static string CreateDataItemId(IContainer container, IDataItem dataItem, string pattern) { if (container != null && dataItem != null) { - var result = pattern; + var result = pattern; - var configurations = GetIdFormatConfigurations(pattern); - if (configurations != null) - { - foreach (var configuration in configurations) - { - var obj = GetIdFormatObject(container, dataItem, configuration); - var value = GetPropertyValue(obj, configuration.Property); + var configurations = GetIdFormatConfigurations(pattern); + if (configurations != null) + { + foreach (var configuration in configurations) + { + var obj = GetIdFormatObject(container, dataItem, configuration); + var value = GetPropertyValue(obj, configuration.Property); if (value != null) { result = result.Replace(configuration.Pattern, $"{configuration.Prefix}{value}{configuration.Suffix}"); @@ -1169,17 +1249,17 @@ public static string CreateDataItemId(IContainer container, IDataItem dataItem, { result = result.Replace(configuration.Pattern, ""); } - } - } + } + } - return result; - } + return result; + } return null; } private static object GetIdFormatObject(IContainer container, IdFormatConfiguration configuration) - { + { if (container != null) { switch (configuration.Object.ToLower()) @@ -1194,27 +1274,27 @@ private static object GetIdFormatObject(IContainer container, IdFormatConfigurat return null; } - private static object GetIdFormatObject(IContainer container, IDataItem dataItem, IdFormatConfiguration configuration) - { - if (container != null && dataItem != null) - { - switch (configuration.Object.ToLower()) - { - case "parent": return container.Parent; - case "device": return container; - case "component": return container; - case "composition": return container; - case "dataitem": return dataItem; - } - } - - return null; - } - - private static IEnumerable GetIdFormatConfigurations(string pattern) - { - if (!string.IsNullOrEmpty(pattern)) - { + private static object GetIdFormatObject(IContainer container, IDataItem dataItem, IdFormatConfiguration configuration) + { + if (container != null && dataItem != null) + { + switch (configuration.Object.ToLower()) + { + case "parent": return container.Parent; + case "device": return container; + case "component": return container; + case "composition": return container; + case "dataitem": return dataItem; + } + } + + return null; + } + + private static IEnumerable GetIdFormatConfigurations(string pattern) + { + if (!string.IsNullOrEmpty(pattern)) + { try { var configurations = new List(); @@ -1241,7 +1321,7 @@ private static IEnumerable GetIdFormatConfigurations(stri configuration.Property = match.Groups[5].Value; configuration.Suffix = match.Groups[6].Value; configuration.IsOptional = true; - } + } configurations.Add(configuration); } @@ -1251,12 +1331,12 @@ private static IEnumerable GetIdFormatConfigurations(stri return configurations; } catch { } - } + } - return null; - } + return null; + } - private static string GetPropertyValue(object obj, string propertyName) + private static string GetPropertyValue(object obj, string propertyName) { if (obj != null && !string.IsNullOrEmpty(propertyName)) { @@ -1283,6 +1363,11 @@ private static string GetPropertyValue(object obj, string propertyName) #endregion + /// + /// Creates the most-derived Component subclass matching the given Component's Type and copies its properties. + /// + /// The source Component to recreate as its concrete type. + /// A typed Component instance, or a base Component when the Type is not recognized. public static Component Create(IComponent component) { var type = GetComponentType(component.Type); @@ -1323,12 +1408,22 @@ public static Component Create(IComponent component) return (Component)component; } + /// + /// Creates an instance of the Component subclass registered for the specified Type identifier. + /// + /// The MTConnect Component Type identifier. + /// A new typed Component instance, or null when the Type is not recognized. public static Component Create(string type) { var t = GetComponentType(type); return Create(t); } + /// + /// Creates an instance of the specified Component CLR type using its parameterless constructor. + /// + /// The concrete Component CLR type to instantiate. + /// A new Component instance, or null when instantiation fails. public static Component Create(Type type) { if (type != null) @@ -1347,6 +1442,10 @@ public static Component Create(Type type) return new Component(); } + /// + /// Returns every Component Type identifier known to the library. + /// + /// The registered Component Type identifiers. public static IEnumerable GetTypes() { if (_types == null) _types = GetAllTypes(); @@ -1354,6 +1453,10 @@ public static IEnumerable GetTypes() return _types.Keys; } + /// + /// Returns the human-readable description for every known Component Type, keyed by Type identifier. + /// + /// Pairs of Type identifier and its description text. public static IEnumerable> GetTypeDescriptions() { if (_typeDescriptions == null) @@ -1456,6 +1559,12 @@ private static Dictionary GetAllTypes() } + /// + /// Determines whether the specified Component is valid for use under the given MTConnect Standard version. + /// + /// The Component to check. + /// The target MTConnect Standard version. + /// True when the Component's version range includes ; otherwise false. public static bool IsCompatible(IComponent component, Version mtconnectVersion) { if (component != null) @@ -1466,6 +1575,13 @@ public static bool IsCompatible(IComponent component, Version mtconnectVersion) return false; } + /// + /// Produces a typed copy of the specified Component adjusted for the target MTConnect version, + /// recursively processing its child entities and dropping members not valid in that version. + /// + /// The source Component to process. + /// The target MTConnect Standard version; when null, the latest version is assumed. + /// The version-adjusted Component, or null when it is not valid in that version. public static Component Process(IComponent component, Version mtconnectVersion = null) { if (component != null) diff --git a/libraries/MTConnect.NET-Common/Devices/Component.g.cs b/libraries/MTConnect.NET-Common/Devices/Component.g.cs index 41c699015..6e3d12a12 100644 --- a/libraries/MTConnect.NET-Common/Devices/Component.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Component.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices /// public partial class Component : IComponent { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Logical or physical entity that provides a capability."; @@ -17,57 +20,57 @@ public partial class Component : IComponent /// Logical or physical entity that provides a capability. /// public System.Collections.Generic.IEnumerable Components { get; set; } - + /// /// Functional part of a piece of equipment contained within a Component. /// public System.Collections.Generic.IEnumerable Compositions { get; set; } - + /// /// Technical information about an entity describing its physical layout, functional characteristics, and relationships with other entities. /// public MTConnect.Devices.Configurations.IConfiguration Configuration { get; set; } - + /// /// Specifies the CoordinateSystem for this Component and its children. /// public string CoordinateSystemIdRef { get; set; } - + /// /// Descriptive content. /// public MTConnect.Devices.IDescription Description { get; set; } - + /// /// Unique identifier for the Component. /// public string Id { get; set; } - + /// /// Name of the Component.name **MUST** be unique for all child Component entities of a parent Component. /// public string Name { get; set; } - + /// /// Common name associated with Component. /// public string NativeName { get; set; } - + /// /// Pointer to information that is associated with another entity defined elsewhere in the MTConnectDevices entity for a piece of equipment. /// public System.Collections.Generic.IEnumerable References { get; set; } - + /// /// Interval in milliseconds between the completion of the reading of the data associated with the Component until the beginning of the next sampling of that data.This information may be used by client software applications to understand how often information from a Component is expected to be refreshed.The refresh rate for data from all child Component entities will be thesampleInterval provided for the child Component. /// public double SampleInterval { get; set; } - + /// /// SampleInterval. /// public double SampleRate { get; set; } - + /// /// Universally unique identifier for the Component. /// diff --git a/libraries/MTConnect.NET-Common/Devices/ComponentDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/ComponentDescriptions.g.cs index 02c8f6426..353b426ce 100644 --- a/libraries/MTConnect.NET-Common/Devices/ComponentDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/ComponentDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each property of Component as defined by the MTConnect Standard. + /// public static class ComponentDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ActuatorComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ActuatorComponent.g.cs index 041759e27..20a719137 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ActuatorComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ActuatorComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ActuatorComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Actuator"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "actuator"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Component composed of a physical apparatus that moves or controls a mechanism or system."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its Type set to . + /// public ActuatorComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/AdapterComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/AdapterComponent.g.cs index 81d58cd54..f08dfc4a3 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/AdapterComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/AdapterComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class AdapterComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Adapter"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "adapter"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Component that provides information about the data source for an MTConnect Agent."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public AdapterComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/AdaptersComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/AdaptersComponent.g.cs index 44aa70cf0..5f4029f9c 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/AdaptersComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/AdaptersComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class AdaptersComponent : Component, IOrganizerComponent { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Adapters"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "adapters"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Component that organize Adapter types."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public AdaptersComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/AirHandlerComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/AirHandlerComponent.g.cs index f8a812a9d..444be243d 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/AirHandlerComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/AirHandlerComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class AirHandlerComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "AirHandler"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "airHandler"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "System that circulates air or regulates airflow without altering temperature or humidity."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version23; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version23; + /// + /// Initializes a new instance with its Type set to . + /// public AirHandlerComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/AmplifierComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/AmplifierComponent.g.cs index e0d13b522..4c4c91be6 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/AmplifierComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/AmplifierComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class AmplifierComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Amplifier"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "amplifier"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component composed of an electronic component or circuit that amplifies power, electric current, or voltage."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public AmplifierComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/AutomaticToolChangerComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/AutomaticToolChangerComponent.g.cs index 3d6d28954..e15c97fc3 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/AutomaticToolChangerComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/AutomaticToolChangerComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class AutomaticToolChangerComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "AutomaticToolChanger"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "automaticToolChanger"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "ToolingDelivery composed of a tool delivery mechanism that moves tools between a ToolMagazine and a spindle a Turret."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public AutomaticToolChangerComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/AuxiliariesComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/AuxiliariesComponent.g.cs index 49d1e95d6..2fadd5d43 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/AuxiliariesComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/AuxiliariesComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class AuxiliariesComponent : Component, IOrganizerComponent { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Auxiliaries"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "auxiliaries"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Component that organize Auxiliary types."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public AuxiliariesComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/AuxiliaryComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/AuxiliaryComponent.g.cs index 3518a8506..b41b17711 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/AuxiliaryComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/AuxiliaryComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public abstract class AuxiliaryComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Auxiliary"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "auxiliary"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Abstract Component composed of removable part(s) of a piece of equipment that provides supplementary or extended functionality."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public AuxiliaryComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/AxesComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/AxesComponent.g.cs index 0da278221..f7a32dffe 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/AxesComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/AxesComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class AxesComponent : Component, IOrganizerComponent { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Axes"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "axes"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Axis types."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its Type set to . + /// public AxesComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/AxisComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/AxisComponent.g.cs index e968d52c4..900f1e3c4 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/AxisComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/AxisComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public abstract class AxisComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Axis"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "axis"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Abstract Component composed of a motion system that provides linear or rotational motion for a piece of equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its Type set to . + /// public AxisComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/BallscrewComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/BallscrewComponent.g.cs index 53db25dbc..f3b32c011 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/BallscrewComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/BallscrewComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class BallscrewComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Ballscrew"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "ballscrew"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component composed of a mechanical structure that transforms rotary motion into linear motion."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public BallscrewComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/BarFeederComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/BarFeederComponent.g.cs index 94f0a9968..a43c9df5a 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/BarFeederComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/BarFeederComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class BarFeederComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "BarFeeder"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "barFeeder"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Loader that delivers bar stock to a piece of equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public BarFeederComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/BeltComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/BeltComponent.g.cs index f209816ac..0267a398a 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/BeltComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/BeltComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class BeltComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Belt"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "belt"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component composed of an endless flexible band that transmits motion for a piece of equipment or conveys materials and objects."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public BeltComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/BrakeComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/BrakeComponent.g.cs index a8ba924c8..1c643fad2 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/BrakeComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/BrakeComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class BrakeComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Brake"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "brake"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that slows or stops a moving object by the absorption or transfer of the energy of momentum, usually by means of friction, electrical force, or magnetic force."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public BrakeComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ChainComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ChainComponent.g.cs index 0ae8774ab..6fc9f2ba2 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ChainComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ChainComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ChainComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Chain"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "chain"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component composed of interconnected series of objects that band together and are used to transmit motion for a piece of equipment or to convey materials and objects."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public ChainComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ChopperComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ChopperComponent.g.cs index ef8741ce9..e648300d1 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ChopperComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ChopperComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ChopperComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Chopper"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "chopper"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that breaks material into smaller pieces."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public ChopperComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ChuckComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ChuckComponent.g.cs index d76375407..78d5792e5 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ChuckComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ChuckComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ChuckComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Chuck"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "chuck"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component composed of a mechanism that holds a part or stock material in place."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version13; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// Initializes a new instance with its Type set to . + /// public ChuckComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ChuteComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ChuteComponent.g.cs index c32bf18ae..678a37f60 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ChuteComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ChuteComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ChuteComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Chute"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "chute"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component composed of an inclined channel that conveys material."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public ChuteComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/CircuitBreakerComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/CircuitBreakerComponent.g.cs index bb67a5eca..324dac304 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/CircuitBreakerComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/CircuitBreakerComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class CircuitBreakerComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "CircuitBreaker"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "circuitBreaker"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that interrupts an electric circuit."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public CircuitBreakerComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ClampComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ClampComponent.g.cs index 4638336bf..466729606 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ClampComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ClampComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ClampComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Clamp"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "clamp"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that strengthens, support, or fastens objects in place."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public ClampComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/CompressorComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/CompressorComponent.g.cs index f444c18b1..bfad4f16e 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/CompressorComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/CompressorComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class CompressorComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Compressor"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "compressor"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component composed of a pump or other mechanism that reduces volume and increases pressure of gases in order to condense the gases to drive pneumatically powered pieces of equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public CompressorComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ControllerComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ControllerComponent.g.cs index 22ee5eb6d..ef249cdac 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ControllerComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ControllerComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ControllerComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Controller"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "cont"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "System that provides regulation or management of a system or component. ISO 16484-5:2017"; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its Type set to . + /// public ControllerComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ControllersComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ControllersComponent.g.cs index e6b10a068..44c1fff4c 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ControllersComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ControllersComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ControllersComponent : Component, IOrganizerComponent { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Controllers"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "controllers"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Component that organize Controller entities."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version20; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version20; + /// + /// Initializes a new instance with its Type set to . + /// public ControllersComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/CoolantComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/CoolantComponent.g.cs index 00581c6cf..40d804562 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/CoolantComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/CoolantComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class CoolantComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Coolant"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "coolant"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "System that provides distribution and management of fluids that remove heat from a piece of equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its Type set to . + /// public CoolantComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/CoolingComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/CoolingComponent.g.cs index 1e9d0d911..fc7ec0596 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/CoolingComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/CoolingComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class CoolingComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Cooling"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "cooling"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "System that extracts controlled amounts of heat to achieve a target temperature at a specified cooling rate."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public CoolingComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/CoolingTowerComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/CoolingTowerComponent.g.cs index c1c147ccc..100f5e2ac 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/CoolingTowerComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/CoolingTowerComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class CoolingTowerComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "CoolingTower"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "coolingTower"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component composed of a heat exchange system that uses a fluid to transfer heat to the atmosphere."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public CoolingTowerComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/CuttingTorchComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/CuttingTorchComponent.g.cs index 8059c0618..f356cc55e 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/CuttingTorchComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/CuttingTorchComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class CuttingTorchComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "CuttingTorch"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "cuttingTorch"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Auxiliary that employs a concentrated flame to both sever materials through cutting and fuse them together in joining processes."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version26; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version26; + /// + /// Initializes a new instance with its Type set to . + /// public CuttingTorchComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/DepositionComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/DepositionComponent.g.cs index 7d2dab734..561da4906 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/DepositionComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/DepositionComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class DepositionComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Deposition"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "deposition"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Auxiliary that manages the addition of material or state change of material being performed in an additive manufacturing process."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// Initializes a new instance with its Type set to . + /// public DepositionComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/DielectricComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/DielectricComponent.g.cs index 8e3bfd885..0db774602 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/DielectricComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/DielectricComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class DielectricComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Dielectric"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "dielectric"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "System that manages a chemical mixture used in a manufacturing process being performed at that piece of equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public DielectricComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/DoorComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/DoorComponent.g.cs index b7a9e36d6..a36bb705b 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/DoorComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/DoorComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class DoorComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Door"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "door"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Component composed of a mechanical mechanism or closure that can cover a physical access portal into a piece of equipment allowing or restricting access to other parts of the equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its Type set to . + /// public DoorComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/DrainComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/DrainComponent.g.cs index a3a8b3ac9..64d126263 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/DrainComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/DrainComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class DrainComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Drain"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "drain"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that allows material to flow for the purpose of drainage from, for example, a vessel or tank."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public DrainComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ElectricComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ElectricComponent.g.cs index d375a2d83..012ff9ce1 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ElectricComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ElectricComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ElectricComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Electric"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "electric"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "System composed of the main power supply for the piece of equipment that provides distribution of that power throughout the equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its Type set to . + /// public ElectricComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ElectrodeComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ElectrodeComponent.g.cs index 99535ce5c..b8d98f78c 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ElectrodeComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ElectrodeComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ElectrodeComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Electrode"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "electrode"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Auxiliary that is used for many electrical discharge manufacturing processes like welding."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version26; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version26; + /// + /// Initializes a new instance with its Type set to . + /// public ElectrodeComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/EnclosureComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/EnclosureComponent.g.cs index 05330a428..683c80396 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/EnclosureComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/EnclosureComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class EnclosureComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Enclosure"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "enclosure"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "System composed of a structure that is used to contain or isolate a piece of equipment or area."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public EnclosureComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/EncoderComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/EncoderComponent.g.cs index ef87e7d07..7e9641e82 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/EncoderComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/EncoderComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class EncoderComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Encoder"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "encoder"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that measures position."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public EncoderComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/EndEffectorComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/EndEffectorComponent.g.cs index a2abb933c..5b830252b 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/EndEffectorComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/EndEffectorComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class EndEffectorComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "EndEffector"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "endEffector"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "System composed of functions that form the last link segment of a piece of equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// Initializes a new instance with its Type set to . + /// public EndEffectorComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/EnvironmentalComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/EnvironmentalComponent.g.cs index f21aec468..a70ca20f2 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/EnvironmentalComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/EnvironmentalComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class EnvironmentalComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Environmental"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "environmental"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Component that observes the surroundings of another Component.> Note: Environmental **SHOULD** be organized by Auxillaries, Systems or Parts depending on the relationship to the Component."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public EnvironmentalComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ExpiredPotComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ExpiredPotComponent.g.cs index 304cab5b9..01ca493e6 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ExpiredPotComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ExpiredPotComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ExpiredPotComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "ExpiredPot"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "expiredPot"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that is a Pot for a tool that is no longer usable for removal from a ToolMagazine or Turret."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public ExpiredPotComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ExposureUnitComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ExposureUnitComponent.g.cs index 4735e4518..6fecceebe 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ExposureUnitComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ExposureUnitComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ExposureUnitComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "ExposureUnit"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "exposureUnit"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that emits a type of radiation."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// Initializes a new instance with its Type set to . + /// public ExposureUnitComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ExtrusionUnitComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ExtrusionUnitComponent.g.cs index a73a60a64..d22960aba 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ExtrusionUnitComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ExtrusionUnitComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ExtrusionUnitComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "ExtrusionUnit"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "extrusionUnit"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that dispenses liquid or powered materials."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// Initializes a new instance with its Type set to . + /// public ExtrusionUnitComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/FanComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/FanComponent.g.cs index c735a2496..a906f8642 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/FanComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/FanComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class FanComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Fan"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "fan"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that produces a current of air."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public FanComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/FeatureOccurrenceComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/FeatureOccurrenceComponent.g.cs index 3e9273589..1165bd992 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/FeatureOccurrenceComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/FeatureOccurrenceComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class FeatureOccurrenceComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "FeatureOccurrence"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "featureOccurrence"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Component that provides information related to an individual feature."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version22; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version22; + /// + /// Initializes a new instance with its Type set to . + /// public FeatureOccurrenceComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/FeederComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/FeederComponent.g.cs index 0a8fd3689..dc5b32115 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/FeederComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/FeederComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class FeederComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Feeder"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "feeder"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "System that manages the delivery of materials within a piece of equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public FeederComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/FilterComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/FilterComponent.g.cs index 8f86ddffd..e36cc4cf8 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/FilterComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/FilterComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class FilterComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Filter"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "filter"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component through which liquids or gases are passed to remove suspended impurities or to recover solids."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public FilterComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/GalvanomotorComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/GalvanomotorComponent.g.cs index ee0b4afbc..daf543e6c 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/GalvanomotorComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/GalvanomotorComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class GalvanomotorComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Galvanomotor"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "galvanomotor"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component composed of an electromechanical actuator that produces deflection of a beam of light or energy in response to electric current through its coil in a magnetic field."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// Initializes a new instance with its Type set to . + /// public GalvanomotorComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/GangToolBarComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/GangToolBarComponent.g.cs index 98fbe3d59..a2c1b8ec4 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/GangToolBarComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/GangToolBarComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class GangToolBarComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "GangToolBar"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "gangToolBar"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "ToolingDelivery composed of a tool mounting mechanism that holds any number of tools."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public GangToolBarComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/GripperComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/GripperComponent.g.cs index 95fd88fb4..42e8986f9 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/GripperComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/GripperComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class GripperComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Gripper"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "gripper"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that holds a part, stock material, or any other item in place."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public GripperComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/HeatingComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/HeatingComponent.g.cs index 1a0b68c23..f88f6c4e4 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/HeatingComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/HeatingComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class HeatingComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Heating"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "heating"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "System that delivers controlled amounts of heat to achieve a target temperature at a specified heating rate."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public HeatingComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/HopperComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/HopperComponent.g.cs index aa4e5edd2..4b72bb4d5 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/HopperComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/HopperComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class HopperComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Hopper"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "hopper"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component composed of a chamber or bin in which materials are stored temporarily, typically being filled through the top and dispensed through the bottom."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public HopperComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/HydraulicComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/HydraulicComponent.g.cs index e21e7f8c7..074bd00f0 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/HydraulicComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/HydraulicComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class HydraulicComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Hydraulic"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "hydraulic"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "System that provides movement and distribution of pressurized liquid throughout the piece of equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its Type set to . + /// public HydraulicComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/InterfacesComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/InterfacesComponent.g.cs index 522ab3b25..a4a25b7ab 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/InterfacesComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/InterfacesComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class InterfacesComponent : Component, IOrganizerComponent { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Interfaces"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "interfaces"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Component that organize Interface types."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version13; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// Initializes a new instance with its Type set to . + /// public InterfacesComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/LinearComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/LinearComponent.g.cs index 7b9d99530..cf9ceef42 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/LinearComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/LinearComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class LinearComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Linear"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "linear"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Axis that provides prismatic motion along a fixed axis."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its Type set to . + /// public LinearComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/LinearPositionFeedbackComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/LinearPositionFeedbackComponent.g.cs index 6a890f42a..6c00c869d 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/LinearPositionFeedbackComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/LinearPositionFeedbackComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class LinearPositionFeedbackComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "LinearPositionFeedback"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "linearPositionFeedback"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that measures linear motion or position.**DEPRECATION WARNING** : May be deprecated in the future. Recommend using Encoder."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public LinearPositionFeedbackComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/LinkComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/LinkComponent.g.cs index 1da738757..4aaec6da1 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/LinkComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/LinkComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class LinkComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Link"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "link"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Structure that provides a connection between Component entities."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public LinkComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/LoaderComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/LoaderComponent.g.cs index 622367150..a098b9b9e 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/LoaderComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/LoaderComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class LoaderComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Loader"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "loader"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Auxiliary that provides movement and distribution of materials, parts, tooling, and other items to or from a piece of equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public LoaderComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/LockComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/LockComponent.g.cs index a559a00c2..1e1375716 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/LockComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/LockComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class LockComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Lock"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "lock"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Component that physically prohibits a Device or Component from opening or operating."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version18; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version18; + /// + /// Initializes a new instance with its Type set to . + /// public LockComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/LubricationComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/LubricationComponent.g.cs index a0fc28166..21da270a0 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/LubricationComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/LubricationComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class LubricationComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Lubrication"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "lubrication"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "System that provides distribution and management of fluids used to lubricate portions of the piece of equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its Type set to . + /// public LubricationComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/MaterialComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/MaterialComponent.g.cs index cdefc793a..16c35e005 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/MaterialComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/MaterialComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class MaterialComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Material"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "material"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Resource composed of material that is consumed or used by the piece of equipment for production of parts, materials, or other types of goods."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version18; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version18; + /// + /// Initializes a new instance with its Type set to . + /// public MaterialComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/MaterialsComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/MaterialsComponent.g.cs index e99e6c117..a891f1029 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/MaterialsComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/MaterialsComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class MaterialsComponent : Component, IOrganizerComponent { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Materials"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "materials"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Resources that organize Material types."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public MaterialsComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/MotorComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/MotorComponent.g.cs index 477de3017..e2c0c78f7 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/MotorComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/MotorComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class MotorComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Motor"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "motor"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that converts electrical, pneumatic, or hydraulic energy into mechanical energy."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public MotorComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/OilComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/OilComponent.g.cs index 02d527768..89dcd0cbc 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/OilComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/OilComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class OilComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Oil"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "oil"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component composed of a viscous liquid."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public OilComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/PartComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/PartComponent.g.cs index c8339c626..4f6419adc 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/PartComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/PartComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public abstract class PartComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Part"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "part"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Abstract Component composed of a part being processed by a piece of equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public PartComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/PartOccurrenceComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/PartOccurrenceComponent.g.cs index f2ec09769..6844f005f 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/PartOccurrenceComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/PartOccurrenceComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class PartOccurrenceComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "PartOccurrence"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "partOccurrence"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Part that exists at a specific place and time, such as a specific instance of a bracket at a specific timestamp."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public PartOccurrenceComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/PartsComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/PartsComponent.g.cs index 79a8e1321..1a3d4179e 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/PartsComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/PartsComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class PartsComponent : Component, IOrganizerComponent { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Parts"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "parts"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Component that organize Part types."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version18; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version18; + /// + /// Initializes a new instance with its Type set to . + /// public PartsComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/PathComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/PathComponent.g.cs index 097a9f7e9..b06c913c6 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/PathComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/PathComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class PathComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Path"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "path"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Component that organizes an independent operation or function within a Controller."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its Type set to . + /// public PathComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/PersonnelComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/PersonnelComponent.g.cs index 6134997f4..9c5c604e9 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/PersonnelComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/PersonnelComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class PersonnelComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Personnel"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "personnel"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Resource composed of an individual or individuals who either control, support, or otherwise interface with a piece of equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public PersonnelComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/PinToolComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/PinToolComponent.g.cs index b8b9bb91b..0375e36de 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/PinToolComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/PinToolComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class PinToolComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "PinTool"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "pinTool"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "System composed of a tool that performs the work for a Friction Stir Welding process"; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version27; + /// + /// Initializes a new instance with its Type set to . + /// public PinToolComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/PneumaticComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/PneumaticComponent.g.cs index 14e348540..9d2244160 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/PneumaticComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/PneumaticComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class PneumaticComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Pneumatic"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "pneumatic"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "System that uses compressed gasses to actuate components or do work within the piece of equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its Type set to . + /// public PneumaticComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/PotComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/PotComponent.g.cs index fc1e1f317..8be8959bb 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/PotComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/PotComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class PotComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Pot"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "pot"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component composed of a tool storage location associated with a ToolMagazine or AutomaticToolChanger."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public PotComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/PowerComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/PowerComponent.g.cs index 58754baac..0ca075c57 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/PowerComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/PowerComponent.g.cs @@ -10,15 +10,40 @@ namespace MTConnect.Devices.Components /// public class PowerComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Power"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "power"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Power was **DEPRECATED** in *MTConnect Version 1.1* and was replaced by Availability data item type."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; + + /// + /// The maximum MTConnect Version that this Component is valid for; set when the type has been deprecated. + /// public override System.Version MaximumVersion => MTConnectVersions.Version11; - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its Type set to . + /// public PowerComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/PowerSupplyComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/PowerSupplyComponent.g.cs index ce09a986c..b3cac370d 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/PowerSupplyComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/PowerSupplyComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class PowerSupplyComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "PowerSupply"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "powerSupply"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that provides power to electric mechanisms."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public PowerSupplyComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/PressureComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/PressureComponent.g.cs index ac89fde8a..55dafcdb0 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/PressureComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/PressureComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class PressureComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Pressure"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "pressure"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "System that delivers compressed gas or fluid and controls the pressure and rate of pressure change to a desired target set-point."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its Type set to . + /// public PressureComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ProcessComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ProcessComponent.g.cs index baece2281..4b519c583 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ProcessComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ProcessComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public abstract class ProcessComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Process"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "process"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Abstract Component composed of a manufacturing process being executed on a piece of equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public ProcessComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ProcessOccurrenceComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ProcessOccurrenceComponent.g.cs index a94147516..6acc06562 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ProcessOccurrenceComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ProcessOccurrenceComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ProcessOccurrenceComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "ProcessOccurrence"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "processOccurrence"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Process that takes place at a specific place and time, such as a specific instance of part-milling occurring at a specific timestamp."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public ProcessOccurrenceComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ProcessPowerComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ProcessPowerComponent.g.cs index 77ca688e7..421eff34a 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ProcessPowerComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ProcessPowerComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ProcessPowerComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "ProcessPower"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "processPower"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "System composed of a power source associated with a piece of equipment that supplies energy to the manufacturing process separate from the Electric system."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public ProcessPowerComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ProcessesComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ProcessesComponent.g.cs index aa36075ae..2d07865d7 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ProcessesComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ProcessesComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ProcessesComponent : Component, IOrganizerComponent { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Processes"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "processes"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Component that organize Process types."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public ProcessesComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ProtectiveComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ProtectiveComponent.g.cs index 49f7c92a9..624380a45 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ProtectiveComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ProtectiveComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ProtectiveComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Protective"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "protective"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "System that provides functions used to detect or prevent harm or damage to equipment or personnel."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public ProtectiveComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/PulleyComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/PulleyComponent.g.cs index 908c98506..b66c2237a 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/PulleyComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/PulleyComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class PulleyComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Pulley"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "pulley"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component composed of a mechanism or wheel that turns in a frame or block and serves to change the direction of or to transmit force."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public PulleyComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/PumpComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/PumpComponent.g.cs index 1bb34c2b2..1cf13dac1 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/PumpComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/PumpComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class PumpComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Pump"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "pump"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that raises, drives, exhausts, or compresses fluids or gases by means of a piston, plunger, or set of rotating vanes."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public PumpComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ReelComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ReelComponent.g.cs index ae58ab95a..8e0d0006f 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ReelComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ReelComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ReelComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Reel"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "reel"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component composed of a rotary storage unit for material."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// Initializes a new instance with its Type set to . + /// public ReelComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/RemovalPotComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/RemovalPotComponent.g.cs index 770576369..bfd6a3400 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/RemovalPotComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/RemovalPotComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class RemovalPotComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "RemovalPot"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "removalPot"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that is a Pot for a tool that has to be removed from a ToolMagazine or Turret to a location outside of the piece of equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public RemovalPotComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ResourceComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ResourceComponent.g.cs index 4813fec7f..cd282a6d5 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ResourceComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ResourceComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public abstract class ResourceComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Resource"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "resource"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Abstract Component composed of material or personnel involved in a manufacturing process."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public ResourceComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ResourcesComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ResourcesComponent.g.cs index 796846513..e204cb397 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ResourcesComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ResourcesComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ResourcesComponent : Component, IOrganizerComponent { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Resources"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "resources"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Component that organize Resource types."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public ResourcesComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ReturnPotComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ReturnPotComponent.g.cs index 85b912fc0..1ff417e30 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ReturnPotComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ReturnPotComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ReturnPotComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "ReturnPot"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "returnPot"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that is a Pot for a tool that has been removed from spindle or Turret and awaiting for return to a ToolMagazine."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public ReturnPotComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/RotaryComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/RotaryComponent.g.cs index d2ae36459..f01dd91c6 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/RotaryComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/RotaryComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class RotaryComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Rotary"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "rotary"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Axis that provides rotation about a fixed axis."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its Type set to . + /// public RotaryComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/SensingElementComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/SensingElementComponent.g.cs index 88c4dacdf..50586f768 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/SensingElementComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/SensingElementComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class SensingElementComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "SensingElement"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "sensingElement"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that provides a signal or measured value."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public SensingElementComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/SensorComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/SensorComponent.g.cs index 310597766..568b85a32 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/SensorComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/SensorComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class SensorComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Sensor"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "sensor"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Component that responds to a physical stimulus and transmits a resulting impulse or value from a sensing unit."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its Type set to . + /// public SensorComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/SpindleComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/SpindleComponent.g.cs index 9a9005992..c33417c31 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/SpindleComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/SpindleComponent.g.cs @@ -10,15 +10,40 @@ namespace MTConnect.Devices.Components /// public class SpindleComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Spindle"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "spindle"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Component that provides an axis of rotation for the purpose of rapidly rotating a part or a tool to provide sufficient surface speed for cutting operations.Spindle was **DEPRECATED** in *MTConnect Version 1.1* and was replaced by RotaryMode."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; + + /// + /// The maximum MTConnect Version that this Component is valid for; set when the type has been deprecated. + /// public override System.Version MaximumVersion => MTConnectVersions.Version11; - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its Type set to . + /// public SpindleComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/SpreaderComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/SpreaderComponent.g.cs index 5559917c6..9356e73c0 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/SpreaderComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/SpreaderComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class SpreaderComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Spreader"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "spreader"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that flattens or spreading materials."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// Initializes a new instance with its Type set to . + /// public SpreaderComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/StagingPotComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/StagingPotComponent.g.cs index 6cfbfa2a2..a1d50d530 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/StagingPotComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/StagingPotComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class StagingPotComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "StagingPot"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "stagingPot"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that is a Pot for a tool that is awaiting transfer to a ToolMagazine or Turret from outside of the piece of equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public StagingPotComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/StationComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/StationComponent.g.cs index ef624ddc1..c249eca16 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/StationComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/StationComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class StationComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Station"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "station"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component composed of a storage or mounting location for a tool associated with a Turret, GangToolBar, or ToolRack."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public StationComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/StockComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/StockComponent.g.cs index b6f062d62..e63784323 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/StockComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/StockComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class StockComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Stock"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "stock"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Material that is used in a manufacturing process and to which work is applied in a machine or piece of equipment to produce parts."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version13; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// Initializes a new instance with its Type set to . + /// public StockComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/StorageBatteryComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/StorageBatteryComponent.g.cs index 20b1e1e6a..b5237425e 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/StorageBatteryComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/StorageBatteryComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class StorageBatteryComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "StorageBattery"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "storageBattery"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component composed of one or more cells in which chemical energy is converted into electricity and used as a source of power."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public StorageBatteryComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/StructureComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/StructureComponent.g.cs index 87be68dea..6c15e4945 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/StructureComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/StructureComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class StructureComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Structure"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "structure"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Component composed of part(s) comprising the rigid bodies of the piece of equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public StructureComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/StructuresComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/StructuresComponent.g.cs index 5896df294..c5340bdf7 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/StructuresComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/StructuresComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class StructuresComponent : Component, IOrganizerComponent { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Structures"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "structures"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Component that organize Structure types."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public StructuresComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/SwitchComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/SwitchComponent.g.cs index 07a1aeab3..4b30b9435 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/SwitchComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/SwitchComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class SwitchComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Switch"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "switch"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that turns on or off an electric current or makes or breaks a circuit."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public SwitchComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/SystemComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/SystemComponent.g.cs index 9448ba95b..2c7cc5e87 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/SystemComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/SystemComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public abstract class SystemComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "System"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "system"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Abstract Component that is permanently integrated into the piece of equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its Type set to . + /// public SystemComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/SystemsComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/SystemsComponent.g.cs index 243a6b6d8..06b9f8137 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/SystemsComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/SystemsComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class SystemsComponent : Component, IOrganizerComponent { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Systems"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "systems"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Component that organize System types."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its Type set to . + /// public SystemsComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/TableComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/TableComponent.g.cs index d8f0a0157..dfa7f03c2 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/TableComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/TableComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class TableComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Table"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "table"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component composed of a surface for holding an object or material."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// Initializes a new instance with its Type set to . + /// public TableComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/TankComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/TankComponent.g.cs index b7f454328..f01e46e83 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/TankComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/TankComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class TankComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Tank"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "tank"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component generally composed of an enclosed container."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public TankComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/TensionerComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/TensionerComponent.g.cs index 8d88404d3..9c51c5a9e 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/TensionerComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/TensionerComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class TensionerComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Tensioner"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "tensioner"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that provides or applies a stretch or strain to another mechanism."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public TensionerComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ThermostatComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ThermostatComponent.g.cs index 04f323391..9e2719dd5 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ThermostatComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ThermostatComponent.g.cs @@ -10,15 +10,40 @@ namespace MTConnect.Devices.Components /// public class ThermostatComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Thermostat"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "thermostat"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Component composed of a sensor or an instrument that measures temperature.Thermostat was **DEPRECATED** in *MTConnect Version 1.2* and was replaced by Temperature."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; + + /// + /// The maximum MTConnect Version that this Component is valid for; set when the type has been deprecated. + /// public override System.Version MaximumVersion => MTConnectVersions.Version12; - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its Type set to . + /// public ThermostatComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ToolHolderComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ToolHolderComponent.g.cs index c2521407e..e498b3ec9 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ToolHolderComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ToolHolderComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ToolHolderComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "ToolHolder"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "toolHolder"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "System that securely interfaces a Component with a Device"; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version27; + /// + /// Initializes a new instance with its Type set to . + /// public ToolHolderComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ToolMagazineComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ToolMagazineComponent.g.cs index 3ea0a2e55..fc1cc8cfb 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ToolMagazineComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ToolMagazineComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ToolMagazineComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "ToolMagazine"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "toolMagazine"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "ToolingDelivery composed of a tool storage mechanism that holds any number of tools."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public ToolMagazineComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ToolRackComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ToolRackComponent.g.cs index eee8007ba..bae9204c8 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ToolRackComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ToolRackComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ToolRackComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "ToolRack"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "toolRack"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "ToolingDelivery composed of a linear or matrixed tool storage mechanism that holds any number of tools."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public ToolRackComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ToolingDeliveryComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ToolingDeliveryComponent.g.cs index 7f717de0e..c869b9f55 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ToolingDeliveryComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ToolingDeliveryComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ToolingDeliveryComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "ToolingDelivery"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "toolingDelivery"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Auxiliary that manages, positions, stores, and delivers tooling within a piece of equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public ToolingDeliveryComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/TransferArmComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/TransferArmComponent.g.cs index 18ae0e724..c1784ec29 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/TransferArmComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/TransferArmComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class TransferArmComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "TransferArm"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "transferArm"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that physically moves a tool from one location to another."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public TransferArmComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/TransferPotComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/TransferPotComponent.g.cs index 7139e5bb6..875697770 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/TransferPotComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/TransferPotComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class TransferPotComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "TransferPot"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "transferPot"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that is a Pot for a tool that is awaiting transfer from a ToolMagazine to spindle or Turret."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public TransferPotComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/TransformerComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/TransformerComponent.g.cs index 58f9d2e98..9eeb39f73 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/TransformerComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/TransformerComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class TransformerComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Transformer"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "transformer"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that transforms electric energy from a source to a secondary circuit."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// Initializes a new instance with its Type set to . + /// public TransformerComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/TurretComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/TurretComponent.g.cs index 044f811d4..62af6c6e6 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/TurretComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/TurretComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class TurretComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Turret"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "turret"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "ToolingDelivery composed of a tool mounting mechanism that holds any number of tools."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public TurretComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/VacuumComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/VacuumComponent.g.cs index 20c46c6c8..a9e9d50de 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/VacuumComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/VacuumComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class VacuumComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Vacuum"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "vacuum"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "System that evacuates gases and liquids from an enclosed and sealed space to a controlled negative pressure or a molecular density below the prevailing atmospheric level."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its Type set to . + /// public VacuumComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/ValveComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/ValveComponent.g.cs index 9d5b30ad5..43cb9c667 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/ValveComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/ValveComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class ValveComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Valve"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "valve"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component that halts or controls the flow of a liquid, gas, or other material through a passage, pipe, inlet, or outlet."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public ValveComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/VatComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/VatComponent.g.cs index 5249927f5..d1a529acf 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/VatComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/VatComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class VatComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Vat"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "vat"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component generally composed of an open container."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// Initializes a new instance with its Type set to . + /// public VatComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/VibrationComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/VibrationComponent.g.cs index 09abad724..cf48d2852 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/VibrationComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/VibrationComponent.g.cs @@ -10,15 +10,40 @@ namespace MTConnect.Devices.Components /// public class VibrationComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Vibration"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "vibration"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Component composed of a sensor or an instrument that measures the amount and/or frequency of vibration within a system.Vibration was **DEPRECATED** in *MTConnect Version 1.2* and was replaced by Displacement, Frequency etc."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; + + /// + /// The maximum MTConnect Version that this Component is valid for; set when the type has been deprecated. + /// public override System.Version MaximumVersion => MTConnectVersions.Version12; - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its Type set to . + /// public VibrationComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/WasteDisposalComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/WasteDisposalComponent.g.cs index 47ad7ac32..dfdea67b2 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/WasteDisposalComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/WasteDisposalComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class WasteDisposalComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "WasteDisposal"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "wasteDisposal"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Auxiliary that removes manufacturing byproducts from a piece of equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public WasteDisposalComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/WaterComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/WaterComponent.g.cs index 4e791eef5..cb34e9d67 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/WaterComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/WaterComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class WaterComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Water"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "water"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component composed of $$H_2 O$$."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public WaterComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/WireComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/WireComponent.g.cs index 05b286ac2..cbf63ea74 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/WireComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/WireComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class WireComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Wire"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "wire"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component composed of a string like piece or filament of relatively rigid or flexible material provided in a variety of diameters."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its Type set to . + /// public WireComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/WorkEnvelopeComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/WorkEnvelopeComponent.g.cs index 4759d14f1..18b39e5c4 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/WorkEnvelopeComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/WorkEnvelopeComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class WorkEnvelopeComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "WorkEnvelope"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "workEnvelope"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "System composed of the physical process execution space within a piece of equipment."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; + /// + /// Initializes a new instance with its Type set to . + /// public WorkEnvelopeComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Components/WorkpieceComponent.g.cs b/libraries/MTConnect.NET-Common/Devices/Components/WorkpieceComponent.g.cs index a9e78460e..d23654593 100644 --- a/libraries/MTConnect.NET-Common/Devices/Components/WorkpieceComponent.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Components/WorkpieceComponent.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Components /// public class WorkpieceComponent : Component { + /// + /// The MTConnect type value that identifies this Component. + /// public const string TypeId = "Workpiece"; + + /// + /// The default name assigned to an instance of this Component. + /// public const string NameId = "workpiece"; + + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Leaf Component composed of an object or material on which a form of work is performed."; + /// + /// The description of this Component as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this Component. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; + /// + /// Initializes a new instance with its Type set to . + /// public WorkpieceComponent() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Devices/Composition.cs b/libraries/MTConnect.NET-Common/Devices/Composition.cs index 962845f7b..6aa207f6a 100644 --- a/libraries/MTConnect.NET-Common/Devices/Composition.cs +++ b/libraries/MTConnect.NET-Common/Devices/Composition.cs @@ -19,9 +19,15 @@ public partial class Composition : IComposition private static Dictionary _types; + /// + /// The MTConnect entity classification for this object, which is always . + /// public MTConnectEntityType EntityType => MTConnectEntityType.Composition; + /// + /// The DataItems defined directly on this Composition. + /// public virtual IEnumerable DataItems { get; set; } /// @@ -30,18 +36,18 @@ public partial class Composition : IComposition public IContainer Parent { get; set; } - private string _hash; - /// - /// Condensed message digest from a secure one-way hash function. FIPS PUB 180-4 - /// - public string Hash - { - get - { - if (_hash == null) _hash = GenerateHash(); - return _hash; - } - } + private string _hash; + /// + /// Condensed message digest from a secure one-way hash function. FIPS PUB 180-4 + /// + public string Hash + { + get + { + if (_hash == null) _hash = GenerateHash(); + return _hash; + } + } /// /// The Agent InstanceId that produced this Device @@ -88,29 +94,50 @@ public string Hash public virtual Version MinimumVersion => DefaultMinimumVersion; - public string DataItemIdFormat { get; set; } + /// + /// The pattern used to generate Ids for DataItems added to this Composition. + /// + public string DataItemIdFormat { get; set; } - public string CompositionIdFormat { get; set; } + /// + /// The pattern used to generate Ids for child Compositions added to this Composition. + /// + public string CompositionIdFormat { get; set; } - public string ComponentIdFormat { get; set; } + /// + /// The pattern used to generate Ids for child Components added to this Composition. + /// + public string ComponentIdFormat { get; set; } - public Composition() + /// + /// Initializes a new Composition with the default Id-format patterns. + /// + public Composition() { //Id = StringFunctions.RandomString(10); DataItems = new List(); - DataItemIdFormat = Component._defaultDataItemIdFormat; - CompositionIdFormat = Component._defaultCompositionIdFormat; - ComponentIdFormat = Component._defaultComponentIdFormat; - } + DataItemIdFormat = Component._defaultDataItemIdFormat; + CompositionIdFormat = Component._defaultCompositionIdFormat; + ComponentIdFormat = Component._defaultComponentIdFormat; + } + /// + /// Computes a content hash for this Composition that changes whenever its hashed members change. + /// + /// A SHA-1 hash string identifying the current state of this Composition. public string GenerateHash() { return GenerateHash(this); } + /// + /// Computes a content hash for the specified Composition from its hashed members and child entities. + /// + /// The Composition to hash. + /// A SHA-1 hash string, or null when is null. public static string GenerateHash(IComposition composition) { if (composition != null) @@ -135,11 +162,24 @@ public static string GenerateHash(IComposition composition) } + /// + /// Builds a Composition Id by combining a parent Id with a name segment. + /// + /// The Id of the containing Component or Device. + /// The name segment to append. + /// The composed Id in the form "parentId_name". public static string CreateId(string parentId, string name) { return $"{parentId}_{name}"; } + /// + /// Builds a Composition Id from a parent Id, a name segment, and an optional suffix. + /// + /// The Id of the containing Component or Device. + /// The name segment to append. + /// An optional suffix appended after the name when present. + /// The composed Id. public static string CreateId(string parentId, string name, string suffix) { if (!string.IsNullOrEmpty(suffix)) @@ -153,6 +193,11 @@ public static string CreateId(string parentId, string name, string suffix) } + /// + /// Builds the ordered list of Id segments from the containing hierarchy down to the Composition itself. + /// + /// The Composition whose Id path is built. + /// The Id segments from the outermost container to the Composition, or null when is null. public static string[] GenerateIdPaths(IComposition composition) { if (composition != null) @@ -172,6 +217,11 @@ public static string[] GenerateIdPaths(IComposition composition) return null; } + /// + /// Builds the slash-delimited Id path string from the containing hierarchy down to the Composition itself. + /// + /// The Composition whose Id path is built. + /// The Id segments joined with '/', or null when no path is available. public static string GenerateIdPath(IComposition composition) { if (composition != null && !composition.IdPaths.IsNullOrEmpty()) @@ -182,6 +232,11 @@ public static string GenerateIdPath(IComposition composition) return null; } + /// + /// Builds the ordered list of Type segments from the containing hierarchy down to the Composition itself. + /// + /// The Composition whose Type path is built. + /// The Type segments from the outermost container to the Composition, or null when is null. public static string[] GenerateTypePaths(IComposition composition) { if (composition != null) @@ -201,6 +256,11 @@ public static string[] GenerateTypePaths(IComposition composition) return null; } + /// + /// Builds the slash-delimited Type path string from the containing hierarchy down to the Composition itself. + /// + /// The Composition whose Type path is built. + /// The Type segments joined with '/', or null when no path is available. public static string GenerateTypePath(IComposition composition) { if (composition != null && !composition.TypePaths.IsNullOrEmpty()) @@ -212,6 +272,11 @@ public static string GenerateTypePath(IComposition composition) } + /// + /// Creates the most-derived Composition subclass matching the given Composition's Type and copies its properties. + /// + /// The source Composition to recreate as its concrete type. + /// A typed Composition instance, or a base Composition when the Type is not recognized. public static Composition Create(IComposition component) { var type = GetCompositionType(component.Type); @@ -250,12 +315,22 @@ public static Composition Create(IComposition component) return (Composition)component; } + /// + /// Creates an instance of the Composition subclass registered for the specified Type identifier. + /// + /// The MTConnect Composition Type identifier. + /// A new typed Composition instance, or null when the Type is not recognized. public static Composition Create(string type) { var t = GetCompositionType(type); return Create(t); } + /// + /// Creates an instance of the specified Composition CLR type using its parameterless constructor. + /// + /// The concrete Composition CLR type to instantiate. + /// A new Composition instance, or null when instantiation fails. public static Composition Create(Type type) { if (type != null) @@ -274,6 +349,10 @@ public static Composition Create(Type type) return new Composition(); } + /// + /// Returns every Composition Type identifier known to the library. + /// + /// The registered Composition Type identifiers. public static IEnumerable GetTypes() { if (_types == null) _types = GetAllTypes(); @@ -343,6 +422,13 @@ private static Dictionary GetAllTypes() } + /// + /// Produces a typed copy of the specified Composition adjusted for the target MTConnect version, + /// dropping members not valid in that version. + /// + /// The source Composition to process. + /// The target MTConnect Standard version; when null, the latest version is assumed. + /// The version-adjusted Composition, or null when it is not valid in that version. public static Composition Process(IComposition composition, Version mtconnectVersion = null) { if (composition != null) @@ -702,6 +788,13 @@ public void AddDataItem(object subType) where TDataItem : IDataItem } } + /// + /// Creates a DataItem from the given category, type, and optional subtype and adds it to this Composition. + /// + /// The category (Sample, Event, or Condition) of the DataItem. + /// The Type that defines what the DataItem represents. + /// An optional SubType that further refines the Type. + /// An optional explicit Id; when omitted an Id is generated from the format pattern. public void AddDataItem(DataItemCategory category, string type, string subType = null, string dataItemId = null) { if (!string.IsNullOrEmpty(type)) diff --git a/libraries/MTConnect.NET-Common/Devices/Composition.g.cs b/libraries/MTConnect.NET-Common/Devices/Composition.g.cs index f0a05b0fe..7a6af5ca4 100644 --- a/libraries/MTConnect.NET-Common/Devices/Composition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Composition.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices /// public partial class Composition : IComposition { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Functional part of a piece of equipment contained within a Component."; @@ -17,62 +20,62 @@ public partial class Composition : IComposition /// Technical information about an entity describing its physical layout, functional characteristics, and relationships with other entities. /// public MTConnect.Devices.Configurations.IConfiguration Configuration { get; set; } - + /// /// Descriptive content. /// public MTConnect.Devices.IDescription Description { get; set; } - + /// /// Unique identifier for the Composition element. /// public string Id { get; set; } - + /// /// Name of the Composition element. /// public string Name { get; set; } - + /// /// Type of Composition. /// public string Type { get; set; } - + /// /// Universally unique identifier for the Composition. /// public string Uuid { get; set; } - + /// /// Logical or physical entity that provides a capability. /// public System.Collections.Generic.IEnumerable Components { get; set; } - + /// /// Functional part of a piece of equipment contained within a Component. /// public System.Collections.Generic.IEnumerable Compositions { get; set; } - + /// /// Specifies the CoordinateSystem for this Component and its children. /// public string CoordinateSystemIdRef { get; set; } - + /// /// Common name associated with Component. /// public string NativeName { get; set; } - + /// /// Pointer to information that is associated with another entity defined elsewhere in the MTConnectDevices entity for a piece of equipment. /// public System.Collections.Generic.IEnumerable References { get; set; } - + /// /// Interval in milliseconds between the completion of the reading of the data associated with the Component until the beginning of the next sampling of that data.This information may be used by client software applications to understand how often information from a Component is expected to be refreshed.The refresh rate for data from all child Component entities will be thesampleInterval provided for the child Component. /// public double SampleInterval { get; set; } - + /// /// SampleInterval. /// diff --git a/libraries/MTConnect.NET-Common/Devices/CompositionDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/CompositionDescriptions.g.cs index ea49b20e6..18dabb2b8 100644 --- a/libraries/MTConnect.NET-Common/Devices/CompositionDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/CompositionDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each property of Composition as defined by the MTConnect Standard. + /// public static class CompositionDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/ActuatorComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/ActuatorComposition.g.cs index 22af06d1d..3e7db808a 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/ActuatorComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/ActuatorComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class ActuatorComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "ACTUATOR"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "actuatorComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanism that moves or controls a mechanical part of a piece of equipment.It takes energy usually provided by air, electric current, or liquid and converts the energy into some kind of motion."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public ActuatorComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public ActuatorComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/AmplifierComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/AmplifierComposition.g.cs index 35ad97226..403d0fc4b 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/AmplifierComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/AmplifierComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class AmplifierComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "AMPLIFIER"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "amplifierComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of an electronic component or circuit that amplifies power, electric current, or voltage."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public AmplifierComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public AmplifierComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/BallscrewComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/BallscrewComposition.g.cs index 7f2cbacf2..5b02be601 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/BallscrewComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/BallscrewComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class BallscrewComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "BALLSCREW"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "ballscrewComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanical structure that transforms rotary motion into linear motion."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public BallscrewComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public BallscrewComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/BeltComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/BeltComposition.g.cs index d7160fe22..c075fe390 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/BeltComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/BeltComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class BeltComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "BELT"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "beltComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of an endless flexible band that transmits motion for a piece of equipment or conveys materials and objects."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public BeltComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public BeltComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/BrakeComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/BrakeComposition.g.cs index 834b9c2cd..83d3acc50 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/BrakeComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/BrakeComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class BrakeComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "BRAKE"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "brakeComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanism that slows down or stops a moving object by the absorption or transfer of the energy of momentum, usually by means of friction, electrical force, or magnetic force."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public BrakeComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public BrakeComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/ChainComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/ChainComposition.g.cs index 9afa4de7d..0c041740e 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/ChainComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/ChainComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class ChainComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "CHAIN"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "chainComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of an interconnected series of objects that band together and transmit motion for a piece of equipment or to convey materials and objects."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public ChainComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public ChainComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/ChopperComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/ChopperComposition.g.cs index 0ce9b36fe..71e1c83e0 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/ChopperComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/ChopperComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class ChopperComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "CHOPPER"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "chopperComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanism that breaks material into smaller pieces."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public ChopperComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public ChopperComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/ChuckComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/ChuckComposition.g.cs index fc4cd8e64..8020ba404 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/ChuckComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/ChuckComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class ChuckComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "CHUCK"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "chuckComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanism that holds a part, stock material, or any other item in place."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public ChuckComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public ChuckComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/ChuteComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/ChuteComposition.g.cs index c211f3df4..50b3c326e 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/ChuteComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/ChuteComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class ChuteComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "CHUTE"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "chuteComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of an inclined channel that conveys material."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public ChuteComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public ChuteComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/CircuitBreakerComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/CircuitBreakerComposition.g.cs index b48c04f24..c90a662e3 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/CircuitBreakerComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/CircuitBreakerComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class CircuitBreakerComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "CIRCUIT_BREAKER"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "circuitBreakerComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanism that interrupts an electric circuit."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public CircuitBreakerComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public CircuitBreakerComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/ClampComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/ClampComposition.g.cs index 57e12bbac..a3fc585f3 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/ClampComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/ClampComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class ClampComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "CLAMP"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "clampComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanism that strengthens, supports, or fastens objects in place."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public ClampComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public ClampComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/CompressorComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/CompressorComposition.g.cs index 82046d243..617f65188 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/CompressorComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/CompressorComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class CompressorComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "COMPRESSOR"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "compressorComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a pump or other mechanism that reduces volume and increases pressure of gases in order to condense the gases to drive pneumatically powered pieces of equipment."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public CompressorComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public CompressorComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/CoolingTowerComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/CoolingTowerComposition.g.cs index e1a2af890..2f80863dd 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/CoolingTowerComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/CoolingTowerComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class CoolingTowerComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "COOLING_TOWER"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "coolingTowerComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a heat exchange system that uses a fluid to transfer heat to the atmosphere."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; - public CoolingTowerComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public CoolingTowerComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/DoorComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/DoorComposition.g.cs index b70910794..792ecdc26 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/DoorComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/DoorComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class DoorComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "DOOR"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "doorComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanical mechanism or closure that covers a physical access portal into a piece of equipment allowing or restricting access to other parts of the equipment."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public DoorComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public DoorComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/DrainComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/DrainComposition.g.cs index 2ad620fd8..e0a53c4db 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/DrainComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/DrainComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class DrainComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "DRAIN"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "drainComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanism that allows material to flow for the purpose of drainage from, for example, a vessel or tank."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public DrainComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public DrainComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/EncoderComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/EncoderComposition.g.cs index fb0c554cd..a72b24b95 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/EncoderComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/EncoderComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class EncoderComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "ENCODER"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "encoderComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanism that measures rotary position."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public EncoderComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public EncoderComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/ExpiredPotComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/ExpiredPotComposition.g.cs index 164eb779f..26d26a085 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/ExpiredPotComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/ExpiredPotComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class ExpiredPotComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "EXPIRED_POT"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "expiredPotComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Pot for a tool that is no longer usable for removal from a ToolMagazine or Turret."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; - public ExpiredPotComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public ExpiredPotComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/ExposureUnitComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/ExposureUnitComposition.g.cs index edf02a55c..ac844f46a 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/ExposureUnitComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/ExposureUnitComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class ExposureUnitComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "EXPOSURE_UNIT"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "exposureUnitComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanism that emits a type of radiation."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; - public ExposureUnitComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public ExposureUnitComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/ExtrusionUnitComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/ExtrusionUnitComposition.g.cs index 800d70881..4d23cdc3d 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/ExtrusionUnitComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/ExtrusionUnitComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class ExtrusionUnitComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "EXTRUSION_UNIT"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "extrusionUnitComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanism that dispenses liquid or powered materials."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; - public ExtrusionUnitComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public ExtrusionUnitComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/FanComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/FanComposition.g.cs index 128e560d1..923324701 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/FanComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/FanComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class FanComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "FAN"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "fanComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanism that produces a current of air."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public FanComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public FanComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/FilterComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/FilterComposition.g.cs index 00c33d961..6dbe32589 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/FilterComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/FilterComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class FilterComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "FILTER"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "filterComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a substance or structure that allows liquids or gases to pass through to remove suspended impurities or to recover solids."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public FilterComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public FilterComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/GalvanomotorComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/GalvanomotorComposition.g.cs index b7f98c738..848d4d144 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/GalvanomotorComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/GalvanomotorComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class GalvanomotorComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "GALVANOMOTOR"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "galvanomotorComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of an electromechanical actuator that produces deflection of a beam of light or energy in response to electric current through its coil in a magnetic field."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; - public GalvanomotorComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public GalvanomotorComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/GripperComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/GripperComposition.g.cs index 132009634..c6fc076c8 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/GripperComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/GripperComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class GripperComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "GRIPPER"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "gripperComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanism that holds a part, stock material, or any other item in place."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public GripperComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public GripperComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/HopperComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/HopperComposition.g.cs index e455d34aa..b292cc45d 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/HopperComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/HopperComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class HopperComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "HOPPER"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "hopperComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a chamber or bin that stores materials temporarily, typically being filled through the top and dispensed through the bottom."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public HopperComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public HopperComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/LinearPositionFeedbackComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/LinearPositionFeedbackComposition.g.cs index 89b73aceb..50cd72e36 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/LinearPositionFeedbackComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/LinearPositionFeedbackComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class LinearPositionFeedbackComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "LINEAR_POSITION_FEEDBACK"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "linearPositionFeedbackComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanism that measures linear motion or position."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public LinearPositionFeedbackComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public LinearPositionFeedbackComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/MotorComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/MotorComposition.g.cs index 7d2e07457..ef31d7d9e 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/MotorComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/MotorComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class MotorComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "MOTOR"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "motorComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanism that converts electrical, pneumatic, or hydraulic energy into mechanical energy."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public MotorComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public MotorComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/OilComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/OilComposition.g.cs index b604a464a..2befde584 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/OilComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/OilComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class OilComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "OIL"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "oilComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a viscous liquid."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public OilComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public OilComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/PotComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/PotComposition.g.cs index a31b53a96..d21d03ff8 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/PotComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/PotComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class PotComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "POT"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "potComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a tool storage location associated with a ToolMagazine or AutomaticToolChanger."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; - public PotComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public PotComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/PowerSupplyComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/PowerSupplyComposition.g.cs index 40bd2eca3..52c092b48 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/PowerSupplyComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/PowerSupplyComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class PowerSupplyComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "POWER_SUPPLY"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "powerSupplyComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a unit that provides power to electric mechanisms."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public PowerSupplyComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public PowerSupplyComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/PulleyComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/PulleyComposition.g.cs index 6856bc292..9ce4da78f 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/PulleyComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/PulleyComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class PulleyComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "PULLEY"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "pulleyComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanism or wheel that turns in a frame or block and serves to change the direction of or to transmit force."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public PulleyComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public PulleyComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/PumpComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/PumpComposition.g.cs index 172f7e130..e50c2fd27 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/PumpComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/PumpComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class PumpComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "PUMP"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "pumpComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of an apparatus that raises, drives, exhausts, or compresses fluids or gases by means of a piston, plunger, or set of rotating vanes."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public PumpComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public PumpComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/ReelComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/ReelComposition.g.cs index 70fa26f3d..75ff4fdc6 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/ReelComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/ReelComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class ReelComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "REEL"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "reelComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a rotary storage unit for material."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; - public ReelComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public ReelComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/RemovalPotComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/RemovalPotComposition.g.cs index fb088e9df..5e9417ddf 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/RemovalPotComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/RemovalPotComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class RemovalPotComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "REMOVAL_POT"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "removalPotComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Pot for a tool to be removed from a ToolMagazine or Turret to a location outside of the piece of equipment."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; - public RemovalPotComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public RemovalPotComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/ReturnPotComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/ReturnPotComposition.g.cs index 0bcd8891a..cca48ca17 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/ReturnPotComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/ReturnPotComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class ReturnPotComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "RETURN_POT"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "returnPotComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Pot for a tool removed from spindle or Turret and awaiting for return to a ToolMagazine."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; - public ReturnPotComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public ReturnPotComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/SensingElementComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/SensingElementComposition.g.cs index 3b35c1ed5..c1f11fb3d 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/SensingElementComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/SensingElementComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class SensingElementComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "SENSING_ELEMENT"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "sensingElementComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanism that provides a signal or measured value."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public SensingElementComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public SensingElementComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/SpreaderComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/SpreaderComposition.g.cs index 7478b90a0..cf64db12c 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/SpreaderComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/SpreaderComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class SpreaderComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "SPREADER"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "spreaderComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanism that flattens or spreads materials."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; - public SpreaderComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public SpreaderComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/StagingPotComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/StagingPotComposition.g.cs index 6f6c5bfa3..d87c3b097 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/StagingPotComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/StagingPotComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class StagingPotComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "STAGING_POT"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "stagingPotComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Pot for a tool awaiting transfer to a ToolMagazine or Turret from outside of the piece of equipment."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; - public StagingPotComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public StagingPotComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/StationComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/StationComposition.g.cs index 0f78faca2..8730ef04b 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/StationComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/StationComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class StationComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "STATION"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "stationComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a storage or mounting location for a tool associated with a Turret, GangToolBar, or ToolRack."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; - public StationComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public StationComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/StorageBatteryComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/StorageBatteryComposition.g.cs index 86609aa47..30de3d376 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/StorageBatteryComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/StorageBatteryComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class StorageBatteryComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "STORAGE_BATTERY"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "storageBatteryComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of one or more cells that converts chemical energy to electricity and serves as a source of power."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public StorageBatteryComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public StorageBatteryComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/SwitchComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/SwitchComposition.g.cs index 84ee7fdad..e1423012d 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/SwitchComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/SwitchComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class SwitchComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "SWITCH"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "switchComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanism that turns on or off an electric current or makes or breaks a circuit."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public SwitchComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public SwitchComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/TableComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/TableComposition.g.cs index 6497b0a08..152e5e87e 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/TableComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/TableComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class TableComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "TABLE"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "tableComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a surface that holds an object or material."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; - public TableComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public TableComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/TankComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/TankComposition.g.cs index adcdc146a..a7b03cde8 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/TankComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/TankComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class TankComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "TANK"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "tankComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a receptacle or container that holds material."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public TankComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public TankComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/TensionerComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/TensionerComposition.g.cs index ae9330d0e..1aed45f8c 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/TensionerComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/TensionerComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class TensionerComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "TENSIONER"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "tensionerComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanism that provides or applies a stretch or strain to another mechanism."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public TensionerComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public TensionerComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/TransferArmComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/TransferArmComposition.g.cs index 9c65ffd01..869a74a71 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/TransferArmComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/TransferArmComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class TransferArmComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "TRANSFER_ARM"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "transferArmComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanism that physically moves a tool from one location to another."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; - public TransferArmComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public TransferArmComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/TransferPotComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/TransferPotComposition.g.cs index f39252f01..3c200ecdb 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/TransferPotComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/TransferPotComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class TransferPotComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "TRANSFER_POT"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "transferPotComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Pot for a tool awaiting transfer from a ToolMagazine to spindle or Turret."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; - public TransferPotComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public TransferPotComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/TransformerComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/TransformerComposition.g.cs index abae8529a..dcaefa0a7 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/TransformerComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/TransformerComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class TransformerComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "TRANSFORMER"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "transformerComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanism that transforms electric energy from a source to a secondary circuit."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; - public TransformerComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public TransformerComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/ValveComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/ValveComposition.g.cs index a0e43bb3a..a9ca97bc7 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/ValveComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/ValveComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class ValveComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "VALVE"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "valveComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a mechanism that halts or controls the flow of a liquid, gas, or other material through a passage, pipe, inlet, or outlet."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public ValveComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public ValveComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/VatComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/VatComposition.g.cs index 43badac4e..3fc0ed8d9 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/VatComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/VatComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class VatComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "VAT"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "vatComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a container for liquid or powdered materials."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; - public VatComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public VatComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/WaterComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/WaterComposition.g.cs index 3908899bc..165da88ce 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/WaterComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/WaterComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class WaterComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "WATER"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "waterComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a fluid."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public WaterComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public WaterComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/WireComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/WireComposition.g.cs index 92e463e83..29e4b8222 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/WireComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/WireComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class WireComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "WIRE"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "wireComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of a string like piece or filament of relatively rigid or flexible material provided in a variety of diameters."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; - public WireComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public WireComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Compositions/WorkpieceComposition.g.cs b/libraries/MTConnect.NET-Common/Devices/Compositions/WorkpieceComposition.g.cs index d0cc73adf..4e92c9266 100644 --- a/libraries/MTConnect.NET-Common/Devices/Compositions/WorkpieceComposition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Compositions/WorkpieceComposition.g.cs @@ -10,15 +10,35 @@ namespace MTConnect.Devices.Compositions /// public class WorkpieceComposition : Composition { + /// + /// The MTConnect type value that identifies this Composition. + /// public const string TypeId = "WORKPIECE"; + + /// + /// The default name assigned to an instance of this Composition. + /// public const string NameId = "workpieceComposition"; + + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Composition composed of an object or material on which a form of work is performed."; + /// + /// The description of this Composition as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this Composition. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; - public WorkpieceComposition() { Type = TypeId; } + /// + /// Initializes a new instance with its Type set to . + /// + public WorkpieceComposition() { Type = TypeId; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/AbstractAxis.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/AbstractAxis.g.cs index d6a588720..407ad6eda 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/AbstractAxis.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/AbstractAxis.g.cs @@ -10,8 +10,10 @@ namespace MTConnect.Devices.Configurations /// public abstract class AbstractAxis : IAbstractAxis { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Axis along or around which the Component moves relative to a coordinate system."; - } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/AbstractOrigin.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/AbstractOrigin.g.cs index dfe7cfaf5..233e6ee37 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/AbstractOrigin.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/AbstractOrigin.g.cs @@ -10,8 +10,10 @@ namespace MTConnect.Devices.Configurations /// public abstract class AbstractOrigin : IAbstractOrigin { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Coordinates of the origin position of a coordinate system."; - } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/AbstractRotation.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/AbstractRotation.g.cs index 204b04e8e..723bcbee6 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/AbstractRotation.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/AbstractRotation.g.cs @@ -10,8 +10,10 @@ namespace MTConnect.Devices.Configurations /// public abstract class AbstractRotation : IAbstractRotation { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Rotations about X, Y, and Z axes are expressed in A, B, and C respectively within a 3-dimensional vector."; - } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/AbstractScale.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/AbstractScale.g.cs index f8f526f44..9c9601e3f 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/AbstractScale.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/AbstractScale.g.cs @@ -10,8 +10,10 @@ namespace MTConnect.Devices.Configurations /// public abstract class AbstractScale : IAbstractScale { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Either a single multiplier applied to all three dimensions or a three space multiplier given in the X, Y, and Z dimensions in the coordinate system used for the SolidModel."; - } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/AbstractTranslation.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/AbstractTranslation.g.cs index 2f1024867..0e4229f25 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/AbstractTranslation.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/AbstractTranslation.g.cs @@ -10,8 +10,10 @@ namespace MTConnect.Devices.Configurations /// public abstract class AbstractTranslation : IAbstractTranslation { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Translations along X, Y, and Z axes are expressed as x,y, and z respectively within a 3-dimensional vector."; - } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/AlarmLimits.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/AlarmLimits.g.cs index d58dd5425..a993c11ac 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/AlarmLimits.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/AlarmLimits.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class AlarmLimits : IAlarmLimits { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Set of limits that is used to trigger warning or alarm indicators."; @@ -17,17 +20,17 @@ public class AlarmLimits : IAlarmLimits /// Lower conformance boundary for a variable.> Note: immediate concern or action may be required. /// public double? LowerLimit { get; set; } - + /// /// Lower boundary indicating increased concern and supervision may be required. /// public double? LowerWarning { get; set; } - + /// /// Upper conformance boundary for a variable.> Note: immediate concern or action may be required. /// public double? UpperLimit { get; set; } - + /// /// Upper boundary indicating increased concern and supervision may be required. /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/AlarmLimitsDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/AlarmLimitsDescriptions.g.cs index c116bf7f7..4ec660941 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/AlarmLimitsDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/AlarmLimitsDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of AlarmLimits as defined by the MTConnect Standard. + /// public static class AlarmLimitsDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/AssetRelationship.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/AssetRelationship.g.cs index 87d52c619..d72a7b347 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/AssetRelationship.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/AssetRelationship.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class AssetRelationship : ConfigurationRelationship, IAssetRelationship { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "ConfigurationRelationship that describes the association between a Component or an Asset and another Asset."; @@ -17,12 +20,12 @@ public class AssetRelationship : ConfigurationRelationship, IAssetRelationship /// Uuid of the related Asset. /// public string AssetIdRef { get; set; } - + /// /// Type of Asset being referenced. /// public string AssetType { get; set; } - + /// /// URI reference to the associated Asset. /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/AssetRelationshipDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/AssetRelationshipDescriptions.g.cs index 7448e78fb..7194c2f56 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/AssetRelationshipDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/AssetRelationshipDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of AssetRelationship as defined by the MTConnect Standard. + /// public static class AssetRelationshipDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/Axis.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/Axis.g.cs index f7cf6e9b3..4c3a8f29c 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/Axis.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/Axis.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class Axis : AbstractAxis, IAxis { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Axis along or around which the Component moves relative to a coordinate system."; diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/AxisDataSet.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/AxisDataSet.g.cs index 80e1a28fd..6b51e9676 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/AxisDataSet.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/AxisDataSet.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class AxisDataSet : AbstractAxis, IAxisDataSet, IDataSet { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Axis along or around which the Component moves relative to a coordinate system represented as a dataset."; @@ -17,12 +20,12 @@ public class AxisDataSet : AbstractAxis, IAxisDataSet, IDataSet /// X-component of Axis. /// public double X { get; set; } - + /// /// Y-component of Axis. /// public double Y { get; set; } - + /// /// Z-component of Axis. /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/AxisDataSetDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/AxisDataSetDescriptions.g.cs index c3a8b0769..039b5a01a 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/AxisDataSetDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/AxisDataSetDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of AxisDataSet as defined by the MTConnect Standard. + /// public static class AxisDataSetDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/AxisDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/AxisDescriptions.g.cs index d1c14f375..2d7234238 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/AxisDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/AxisDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of Axis as defined by the MTConnect Standard. + /// public static class AxisDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/Channel.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/Channel.g.cs index 556e72bb6..b21aa10c9 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/Channel.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/Channel.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class Channel : IChannel { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Sensing element of a Sensor."; @@ -17,27 +20,27 @@ public class Channel : IChannel /// Date upon which the sensor unit was last calibrated to the sensor element. /// public System.DateTime? CalibrationDate { get; set; } - + /// /// The initials of the person verifying the validity of the calibration data. /// public string CalibrationInitials { get; set; } - + /// /// Textual description for Channel. /// public string Description { get; set; } - + /// /// Name of the specific sensing element. /// public string Name { get; set; } - + /// /// Date upon which the sensor element is next scheduled to be calibrated with the sensor unit. /// public System.DateTime? NextCalibrationDate { get; set; } - + /// /// Unique identifier that will only refer to a specific sensing element. /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/ChannelDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/ChannelDescriptions.g.cs index 7f4d81648..d7db9a386 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/ChannelDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/ChannelDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of Channel as defined by the MTConnect Standard. + /// public static class ChannelDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/ComponentRelationship.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/ComponentRelationship.g.cs index fd509d589..96e36cd5f 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/ComponentRelationship.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/ComponentRelationship.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class ComponentRelationship : ConfigurationRelationship, IComponentRelationship { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "ConfigurationRelationship that describes the association between a Component or an Asset and another Component."; diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/ComponentRelationshipDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/ComponentRelationshipDescriptions.g.cs index 0ed6b1f3e..6f043809c 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/ComponentRelationshipDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/ComponentRelationshipDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of ComponentRelationship as defined by the MTConnect Standard. + /// public static class ComponentRelationshipDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/Configuration.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/Configuration.g.cs index 0722ee918..1d8be3109 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/Configuration.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/Configuration.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class Configuration : IConfiguration { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Technical information about an entity describing its physical layout, functional characteristics, and relationships with other entities."; @@ -17,37 +20,37 @@ public class Configuration : IConfiguration /// Reference system that associates a unique set of n parameters with each point in an n-dimensional space. ISO 10303-218:2004 /// public System.Collections.Generic.IEnumerable CoordinateSystems { get; set; } - + /// /// Reference to a file containing an image of the Component. /// public System.Collections.Generic.IEnumerable ImageFiles { get; set; } - + /// /// Movement of the component relative to a coordinate system. /// public MTConnect.Devices.Configurations.IMotion Motion { get; set; } - + /// /// Potential energy sources for the Component. /// public MTConnect.Devices.Configurations.IPowerSource PowerSource { get; set; } - + /// /// Association between two pieces of equipment or assets that may function independently but together perform a manufacturing operation. /// public System.Collections.Generic.IEnumerable Relationships { get; set; } - + /// /// Configuration for a Sensor. /// public MTConnect.Devices.Configurations.ISensorConfiguration SensorConfiguration { get; set; } - + /// /// References to a file with the three-dimensional geometry of the Component or Composition. /// public MTConnect.Devices.Configurations.ISolidModel SolidModel { get; set; } - + /// /// Design characteristics for a piece of equipment. /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/ConfigurationDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/ConfigurationDescriptions.g.cs index 09de298bb..6b9c9a3f7 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/ConfigurationDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/ConfigurationDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of Configuration as defined by the MTConnect Standard. + /// public static class ConfigurationDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/ConfigurationRelationship.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/ConfigurationRelationship.g.cs index 723162a63..dda5933bf 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/ConfigurationRelationship.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/ConfigurationRelationship.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public abstract class ConfigurationRelationship : IConfigurationRelationship { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Association between two pieces of equipment or assets that may function independently but together perform a manufacturing operation."; @@ -17,17 +20,17 @@ public abstract class ConfigurationRelationship : IConfigurationRelationship /// Defines whether the services or functions provided by the associated piece of equipment is required for the operation of this piece of equipment. /// public MTConnect.Devices.Configurations.CriticalityType? Criticality { get; set; } - + /// /// Unique identifier for this ConfigurationRelationship. /// public string Id { get; set; } - + /// /// Name associated with this ConfigurationRelationship. /// public string Name { get; set; } - + /// /// Defines the authority that this piece of equipment has relative to the associated piece of equipment. /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/ConfigurationRelationshipDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/ConfigurationRelationshipDescriptions.g.cs index 4c79f1191..7a315bb67 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/ConfigurationRelationshipDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/ConfigurationRelationshipDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of ConfigurationRelationship as defined by the MTConnect Standard. + /// public static class ConfigurationRelationshipDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/ControlLimits.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/ControlLimits.g.cs index 16121362c..3f20c7e94 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/ControlLimits.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/ControlLimits.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class ControlLimits : IControlLimits { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Set of limits that is used to indicate whether a process variable is stable and in control."; @@ -17,22 +20,22 @@ public class ControlLimits : IControlLimits /// Lower conformance boundary for a variable.> Note: immediate concern or action may be required. /// public double? LowerLimit { get; set; } - + /// /// Lower boundary indicating increased concern and supervision may be required. /// public double? LowerWarning { get; set; } - + /// /// Numeric target or expected value. /// public double? Nominal { get; set; } - + /// /// Upper conformance boundary for a variable.> Note: immediate concern or action may be required. /// public double? UpperLimit { get; set; } - + /// /// Upper boundary indicating increased concern and supervision may be required. /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/ControlLimitsDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/ControlLimitsDescriptions.g.cs index 5483bcd71..5fcbfb579 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/ControlLimitsDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/ControlLimitsDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of ControlLimits as defined by the MTConnect Standard. + /// public static class ControlLimitsDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/CoordinateSystem.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/CoordinateSystem.g.cs index c11e5826b..692cf1f60 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/CoordinateSystem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/CoordinateSystem.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class CoordinateSystem : ICoordinateSystem { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Reference system that associates a unique set of n parameters with each point in an n-dimensional space. ISO 10303-218:2004"; @@ -17,42 +20,42 @@ public class CoordinateSystem : ICoordinateSystem /// Natural language description of the CoordinateSystem. /// public string Description { get; set; } - + /// /// Unique identifier for the coordinate system. /// public string Id { get; set; } - + /// /// Name of the coordinate system. /// public string Name { get; set; } - + /// /// Manufacturer's name or users name for the coordinate system. /// public string NativeName { get; set; } - + /// /// Coordinates of the origin position of a coordinate system. /// public MTConnect.Devices.Configurations.IAbstractOrigin Origin { get; set; } - + /// /// Id. /// public string ParentIdRef { get; set; } - + /// /// Process of transforming to the origin position of the coordinate system from a parent coordinate system using Translation and Rotation. /// public MTConnect.Devices.Configurations.ITransformation Transformation { get; set; } - + /// /// Type of coordinate system. /// public MTConnect.Devices.Configurations.CoordinateSystemType Type { get; set; } - + /// /// UUID for the coordinate system. /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/CoordinateSystemDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/CoordinateSystemDescriptions.g.cs index cc4ce4e5e..8c4789615 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/CoordinateSystemDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/CoordinateSystemDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of CoordinateSystem as defined by the MTConnect Standard. + /// public static class CoordinateSystemDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/CoordinateSystemType.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/CoordinateSystemType.g.cs index 46783528d..09f196a79 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/CoordinateSystemType.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/CoordinateSystemType.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// CoordinateSystemType controlled vocabulary as defined by the MTConnect Standard. + /// public enum CoordinateSystemType { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/CoordinateSystemTypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/CoordinateSystemTypeDescriptions.g.cs index 64aa48869..32e9c6bed 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/CoordinateSystemTypeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/CoordinateSystemTypeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class CoordinateSystemTypeDescriptions { /// @@ -51,6 +54,9 @@ public static class CoordinateSystemTypeDescriptions public const string WORLD = "Stationary coordinate system referenced to earth, which is independent of the robot motion. ISO 9787:2013For non-robotic devices, stationary coordinate system referenced to earth, which is independent of the motion of a piece of equipment."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(CoordinateSystemType value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/CriticalityType.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/CriticalityType.g.cs index 3632d0dda..3339cf01f 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/CriticalityType.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/CriticalityType.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// CriticalityType controlled vocabulary as defined by the MTConnect Standard. + /// public enum CriticalityType { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/CriticalityTypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/CriticalityTypeDescriptions.g.cs index 0624769da..df7d4fab0 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/CriticalityTypeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/CriticalityTypeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class CriticalityTypeDescriptions { /// @@ -16,6 +19,9 @@ public static class CriticalityTypeDescriptions public const string NONCRITICAL = "Services or functions provided by the associated element is not required for the operation of this element."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(CriticalityType value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/DataSet.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/DataSet.g.cs index 136c34d32..273de9950 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/DataSet.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/DataSet.g.cs @@ -10,8 +10,10 @@ namespace MTConnect.Devices.Configurations /// public class DataSet : IDataSet { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Representation for an Observation composed of value(s) represented as a set of key-value pair."; - } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/DeviceRelationship.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/DeviceRelationship.g.cs index 2fd2054ee..20eecd55c 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/DeviceRelationship.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/DeviceRelationship.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class DeviceRelationship : ConfigurationRelationship, IDeviceRelationship { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "ConfigurationRelationship that describes the association between a Component or an Asset and a Device."; @@ -17,17 +20,17 @@ public class DeviceRelationship : ConfigurationRelationship, IDeviceRelationship /// Uuid of the associated piece of equipment. /// public string DeviceUuidRef { get; set; } - + /// /// URI identifying the agent that is publishing information for the associated piece of equipment. /// public string Href { get; set; } - + /// /// Defines the services or capabilities that the referenced piece of equipment provides relative to this piece of equipment. /// public MTConnect.Devices.Configurations.RoleType? Role { get; set; } - + /// /// `xlink:type`**MUST** have a fixed value of `locator` as defined in W3C XLink 1.1 https://www.w3.org/TR/xlink11/. /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/DeviceRelationshipDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/DeviceRelationshipDescriptions.g.cs index c85755b3a..04be9ac5f 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/DeviceRelationshipDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/DeviceRelationshipDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of DeviceRelationship as defined by the MTConnect Standard. + /// public static class DeviceRelationshipDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/ImageFile.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/ImageFile.g.cs index 90d57eff7..276c2ae40 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/ImageFile.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/ImageFile.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class ImageFile : IImageFile { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Reference to a file containing an image of the Component."; @@ -17,17 +20,17 @@ public class ImageFile : IImageFile /// URL giving the location of the image file. /// public string Href { get; set; } - + /// /// Unique identifier of the image file. /// public string Id { get; set; } - + /// /// Mime type of the image file. /// public string MediaType { get; set; } - + /// /// Description of the image file. /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/ImageFileDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/ImageFileDescriptions.g.cs index efb0ef992..1b464b6fb 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/ImageFileDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/ImageFileDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of ImageFile as defined by the MTConnect Standard. + /// public static class ImageFileDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/MediaType.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/MediaType.g.cs index b2eb2dcf6..639f4a7d9 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/MediaType.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/MediaType.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// MediaType controlled vocabulary as defined by the MTConnect Standard. + /// public enum MediaType { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/MediaTypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/MediaTypeDescriptions.g.cs index dee3c4f59..0424c6874 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/MediaTypeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/MediaTypeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class MediaTypeDescriptions { /// @@ -56,6 +59,9 @@ public static class MediaTypeDescriptions public const string X_T = "Parasolid XT Siemens data interchange format."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(MediaType value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/Motion.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/Motion.g.cs index ce60c73f4..8689cd1bd 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/Motion.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/Motion.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class Motion : IMotion { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Movement of the component relative to a coordinate system."; @@ -17,42 +20,42 @@ public class Motion : IMotion /// Describes if this component is actuated directly or indirectly as a result of other motion. /// public MTConnect.Devices.Configurations.MotionActuationType Actuation { get; set; } - + /// /// Axis along or around which the Component moves relative to a coordinate system. /// public MTConnect.Devices.Configurations.IAbstractAxis Axis { get; set; } - + /// /// Coordinate system within which the kinematic motion occurs. /// public string CoordinateSystemIdRef { get; set; } - + /// /// Textual description for Motion. /// public string Description { get; set; } - + /// /// Unique identifier for this element. /// public string Id { get; set; } - + /// /// Coordinates of the origin position of a coordinate system. /// public MTConnect.Devices.Configurations.IAbstractOrigin Origin { get; set; } - + /// /// Id.The kinematic chain connects all components using the parent relations. All motion is connected to the motion of the parent. The first node in the chain will not have a parent. /// public string ParentIdRef { get; set; } - + /// /// Process of transforming to the origin position of the coordinate system from a parent coordinate system using Translation and Rotation. /// public MTConnect.Devices.Configurations.ITransformation Transformation { get; set; } - + /// /// Type of motion. /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/MotionActuationType.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/MotionActuationType.g.cs index 600151ab2..de77ac3a1 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/MotionActuationType.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/MotionActuationType.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// MotionActuationType controlled vocabulary as defined by the MTConnect Standard. + /// public enum MotionActuationType { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/MotionActuationTypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/MotionActuationTypeDescriptions.g.cs index 6bd7c1e2d..17c649b43 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/MotionActuationTypeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/MotionActuationTypeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class MotionActuationTypeDescriptions { /// @@ -21,6 +24,9 @@ public static class MotionActuationTypeDescriptions public const string VIRTUAL = "Motion is computed and is used for expressing an imaginary movement."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(MotionActuationType value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/MotionDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/MotionDescriptions.g.cs index 7c887d9da..7f5ea026c 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/MotionDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/MotionDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of Motion as defined by the MTConnect Standard. + /// public static class MotionDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/MotionType.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/MotionType.g.cs index 9828c8a89..de9721571 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/MotionType.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/MotionType.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// MotionType controlled vocabulary as defined by the MTConnect Standard. + /// public enum MotionType { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/MotionTypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/MotionTypeDescriptions.g.cs index 1aa83dd88..c83fc40e2 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/MotionTypeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/MotionTypeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class MotionTypeDescriptions { /// @@ -26,6 +29,9 @@ public static class MotionTypeDescriptions public const string REVOLUTE = "Rotates around an axis with a fixed range of motion."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(MotionType value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/Origin.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/Origin.g.cs index 3d656f29f..e42fb1f86 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/Origin.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/Origin.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class Origin : AbstractOrigin, IOrigin { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Coordinates of the origin position of a coordinate system."; diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/OriginDataSet.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/OriginDataSet.g.cs index f8ed3b817..8648a4ccb 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/OriginDataSet.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/OriginDataSet.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class OriginDataSet : AbstractOrigin, IOriginDataSet, IDataSet { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Coordinates of the origin position of a coordinate system represented as a dataset."; @@ -17,12 +20,12 @@ public class OriginDataSet : AbstractOrigin, IOriginDataSet, IDataSet /// X-coordinate. /// public string X { get; set; } - + /// /// Y-coordinate. /// public string Y { get; set; } - + /// /// X-coordinate. /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/OriginDataSetDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/OriginDataSetDescriptions.g.cs index e1f10e4c3..83ea3a55e 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/OriginDataSetDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/OriginDataSetDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of OriginDataSet as defined by the MTConnect Standard. + /// public static class OriginDataSetDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/OriginDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/OriginDescriptions.g.cs index 26119baa6..48919df86 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/OriginDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/OriginDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of Origin as defined by the MTConnect Standard. + /// public static class OriginDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/Originator.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/Originator.g.cs index 453abdf41..e0777c93d 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/Originator.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/Originator.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Originator controlled vocabulary as defined by the MTConnect Standard. + /// public enum Originator { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/OriginatorDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/OriginatorDescriptions.g.cs index cf2791b42..0d263812e 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/OriginatorDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/OriginatorDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class OriginatorDescriptions { /// @@ -16,6 +19,9 @@ public static class OriginatorDescriptions public const string USER = "Owner or implementer of a piece of equipment or Component."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(Originator value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/PowerSource.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/PowerSource.g.cs index 307c7123b..977f3cba6 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/PowerSource.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/PowerSource.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class PowerSource : IPowerSource { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Potential energy sources for the Component."; @@ -17,22 +20,22 @@ public class PowerSource : IPowerSource /// Reference to the Component providing observations about the power source. /// public string ComponentIdRef { get; set; } - + /// /// Unique identifier for the power source. /// public string Id { get; set; } - + /// /// Optional precedence for a given power source. /// public int Order { get; set; } - + /// /// Type of the power source. /// public MTConnect.Devices.Configurations.PowerSourceType Type { get; set; } - + /// /// Name of the power source. /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/PowerSourceDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/PowerSourceDescriptions.g.cs index 128e98b1f..9d86779a1 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/PowerSourceDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/PowerSourceDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of PowerSource as defined by the MTConnect Standard. + /// public static class PowerSourceDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/PowerSourceType.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/PowerSourceType.g.cs index 70da3084b..c214728d3 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/PowerSourceType.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/PowerSourceType.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// PowerSourceType controlled vocabulary as defined by the MTConnect Standard. + /// public enum PowerSourceType { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/PowerSourceTypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/PowerSourceTypeDescriptions.g.cs index 25eb16c6a..87ed6e702 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/PowerSourceTypeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/PowerSourceTypeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class PowerSourceTypeDescriptions { /// @@ -21,6 +24,9 @@ public static class PowerSourceTypeDescriptions public const string STANDBY = "Held near at hand and ready for use and is uninterruptible."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(PowerSourceType value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/ProcessSpecification.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/ProcessSpecification.g.cs index 086680c0a..adb16849a 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/ProcessSpecification.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/ProcessSpecification.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class ProcessSpecification : Specification, IProcessSpecification { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Specification that provides information used to assess the conformance of a variable to process requirements."; @@ -17,12 +20,12 @@ public class ProcessSpecification : Specification, IProcessSpecification /// Set of limits that is used to trigger warning or alarm indicators. /// public MTConnect.Devices.Configurations.IAlarmLimits AlarmLimits { get; set; } - + /// /// Set of limits that is used to indicate whether a process variable is stable and in control. /// public MTConnect.Devices.Configurations.IControlLimits ControlLimits { get; set; } - + /// /// Set of limits that define a range of values designating acceptable performance for a variable. /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/ProcessSpecificationDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/ProcessSpecificationDescriptions.g.cs index 02a99f771..fa429441c 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/ProcessSpecificationDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/ProcessSpecificationDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of ProcessSpecification as defined by the MTConnect Standard. + /// public static class ProcessSpecificationDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/RelationshipType.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/RelationshipType.g.cs index dc32041ef..1565a0b5a 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/RelationshipType.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/RelationshipType.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// RelationshipType controlled vocabulary as defined by the MTConnect Standard. + /// public enum RelationshipType { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/RelationshipTypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/RelationshipTypeDescriptions.g.cs index 5538af00a..7f62506ad 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/RelationshipTypeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/RelationshipTypeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class RelationshipTypeDescriptions { /// @@ -21,6 +24,9 @@ public static class RelationshipTypeDescriptions public const string PEER = "Functions as a peer which provides equal functionality and capabilities in the relationship with the associated element."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(RelationshipType value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/RoleType.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/RoleType.g.cs index 0b945e359..db17d7c29 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/RoleType.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/RoleType.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// RoleType controlled vocabulary as defined by the MTConnect Standard. + /// public enum RoleType { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/RoleTypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/RoleTypeDescriptions.g.cs index e14d91118..a79c20047 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/RoleTypeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/RoleTypeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class RoleTypeDescriptions { /// @@ -16,6 +19,9 @@ public static class RoleTypeDescriptions public const string SYSTEM = "Associated element performs the functions of a System for this element."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(RoleType value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/Rotation.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/Rotation.g.cs index 7d1eb10c2..0d0d9e392 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/Rotation.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/Rotation.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class Rotation : AbstractRotation, IRotation { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Rotations about X, Y, and Z axes are expressed in A, B, and C respectively within a 3-dimensional vector."; diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/RotationDataSet.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/RotationDataSet.g.cs index 9e2c12bc7..3a5ecb0fd 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/RotationDataSet.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/RotationDataSet.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class RotationDataSet : AbstractRotation, IRotationDataSet, IDataSet { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Rotations about X, Y, and Z axes are expressed in A, B, and C respectively within a 3-dimensional vector represented as a dataset."; @@ -17,12 +20,12 @@ public class RotationDataSet : AbstractRotation, IRotationDataSet, IDataSet /// Rotation about X axis. /// public string A { get; set; } - + /// /// Rotation about Y axis. /// public string B { get; set; } - + /// /// Rotation about Z axis. /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/RotationDataSetDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/RotationDataSetDescriptions.g.cs index 5902c28e0..aae2d5dde 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/RotationDataSetDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/RotationDataSetDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of RotationDataSet as defined by the MTConnect Standard. + /// public static class RotationDataSetDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/RotationDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/RotationDescriptions.g.cs index d10d001be..154667662 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/RotationDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/RotationDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of Rotation as defined by the MTConnect Standard. + /// public static class RotationDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/Scale.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/Scale.g.cs index eda1879d3..9c3a611a6 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/Scale.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/Scale.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class Scale : AbstractScale, IScale { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Either a single multiplier applied to all three dimensions or a three space multiplier given in the X, Y, and Z dimensions in the coordinate system used for the SolidModel."; diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/ScaleDataSet.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/ScaleDataSet.g.cs index 71d3afe65..561b1db71 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/ScaleDataSet.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/ScaleDataSet.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class ScaleDataSet : AbstractScale, IScaleDataSet, IDataSet { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Either a single multiplier applied to all three dimensions or a three space multiplier given in the X, Y, and Z dimensions in the coordinate system used for the SolidModel represented as a dataset."; @@ -17,12 +20,12 @@ public class ScaleDataSet : AbstractScale, IScaleDataSet, IDataSet /// Multiplier for X axis. /// public double X { get; set; } - + /// /// Multiplier for Y axis. /// public double Y { get; set; } - + /// /// Multiplier for Z axis. /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/ScaleDataSetDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/ScaleDataSetDescriptions.g.cs index ab94dc19d..c29d9db42 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/ScaleDataSetDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/ScaleDataSetDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of ScaleDataSet as defined by the MTConnect Standard. + /// public static class ScaleDataSetDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/ScaleDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/ScaleDescriptions.g.cs index b510835f1..c915cca62 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/ScaleDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/ScaleDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of Scale as defined by the MTConnect Standard. + /// public static class ScaleDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/SensorConfiguration.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/SensorConfiguration.g.cs index e35d59465..e5df6628d 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/SensorConfiguration.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/SensorConfiguration.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class SensorConfiguration : ISensorConfiguration { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Configuration for a Sensor."; @@ -17,22 +20,22 @@ public class SensorConfiguration : ISensorConfiguration /// Date upon which the sensor unit was last calibrated. /// public System.DateTime? CalibrationDate { get; set; } - + /// /// The initials of the person verifying the validity of the calibration data. /// public string CalibrationInitials { get; set; } - + /// /// Sensing element of a Sensor. /// public System.Collections.Generic.IEnumerable Channels { get; set; } - + /// /// Version number for the sensor unit as specified by the manufacturer. /// public string FirmwareVersion { get; set; } - + /// /// Date upon which the sensor unit is next scheduled to be calibrated. /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/SensorConfigurationDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/SensorConfigurationDescriptions.g.cs index 1900f212d..cbb7e820d 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/SensorConfigurationDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/SensorConfigurationDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of SensorConfiguration as defined by the MTConnect Standard. + /// public static class SensorConfigurationDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/SolidModel.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/SolidModel.g.cs index fd20df670..b55330026 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/SolidModel.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/SolidModel.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class SolidModel : ISolidModel { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "References to a file with the three-dimensional geometry of the Component or Composition."; @@ -17,47 +20,47 @@ public class SolidModel : ISolidModel /// Reference to the coordinate system for this SolidModel. /// public string CoordinateSystemIdRef { get; set; } - + /// /// URL giving the location of the SolidModel. solidModelIdRef is used.href is of type `xlink:href` from the W3C XLink specification. /// public string Href { get; set; } - + /// /// Unique identifier for this element. /// public string Id { get; set; } - + /// /// SolidModelIdRef **MUST** be given. > Note: `Item` defined in ASME Y14.100 - A nonspecific term used to denote any unit or product, including materials, parts, assemblies, equipment, accessories, and computer software. /// public string ItemRef { get; set; } - + /// /// Format of the referenced document. /// public MTConnect.Devices.Configurations.MediaType MediaType { get; set; } - + /// /// NativeUnits. See DataItem. /// public string NativeUnits { get; set; } - + /// /// Either a single multiplier applied to all three dimensions or a three space multiplier given in the X, Y, and Z dimensions in the coordinate system used for the SolidModel. /// public MTConnect.Devices.Configurations.IAbstractScale Scale { get; set; } - + /// /// Associated model file if an item reference is used. /// public string SolidModelIdRef { get; set; } - + /// /// Process of transforming to the origin position of the coordinate system from a parent coordinate system using Translation and Rotation. /// public MTConnect.Devices.Configurations.ITransformation Transformation { get; set; } - + /// /// Units. See DataItem. /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/SolidModelDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/SolidModelDescriptions.g.cs index dde0bc813..ff6f56e1e 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/SolidModelDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/SolidModelDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of SolidModel as defined by the MTConnect Standard. + /// public static class SolidModelDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/Specification.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/Specification.g.cs index d5108023e..611148668 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/Specification.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/Specification.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class Specification : ISpecification { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Design characteristics for a piece of equipment."; @@ -17,77 +20,77 @@ public class Specification : ISpecification /// Id associated with this entity. /// public string CompositionIdRef { get; set; } - + /// /// References the CoordinateSystem for geometric Specification elements. /// public string CoordinateSystemIdRef { get; set; } - + /// /// Id associated with this entity. /// public string DataItemIdRef { get; set; } - + /// /// Unique identifier for this Specification. /// public string Id { get; set; } - + /// /// Lower conformance boundary for a variable.> Note: immediate concern or action may be required. /// public double? LowerLimit { get; set; } - + /// /// Lower boundary indicating increased concern and supervision may be required. /// public double? LowerWarning { get; set; } - + /// /// Numeric upper constraint. /// public double? Maximum { get; set; } - + /// /// Numeric lower constraint. /// public double? Minimum { get; set; } - + /// /// Name provides additional meaning and differentiates between Specification entities. /// public string Name { get; set; } - + /// /// Numeric target or expected value. /// public double? Nominal { get; set; } - + /// /// Reference to the creator of the Specification. /// public MTConnect.Devices.Configurations.Originator Originator { get; set; } - + /// /// SubType. See DataItem. /// public string SubType { get; set; } - + /// /// Type. See DataItem Types. /// public string Type { get; set; } - + /// /// Units. See DataItem. /// public string Units { get; set; } - + /// /// Upper conformance boundary for a variable.> Note: immediate concern or action may be required. /// public double? UpperLimit { get; set; } - + /// /// Upper boundary indicating increased concern and supervision may be required. /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/SpecificationDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/SpecificationDescriptions.g.cs index f4f86b913..afba06508 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/SpecificationDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/SpecificationDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of Specification as defined by the MTConnect Standard. + /// public static class SpecificationDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/SpecificationLimits.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/SpecificationLimits.g.cs index 89c77119f..d348eabef 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/SpecificationLimits.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/SpecificationLimits.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class SpecificationLimits : ISpecificationLimits { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Set of limits that define a range of values designating acceptable performance for a variable."; @@ -17,12 +20,12 @@ public class SpecificationLimits : ISpecificationLimits /// Lower conformance boundary for a variable.> Note: immediate concern or action may be required. /// public double? LowerLimit { get; set; } - + /// /// Numeric target or expected value. /// public double? Nominal { get; set; } - + /// /// Upper conformance boundary for a variable.> Note: immediate concern or action may be required. /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/SpecificationLimitsDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/SpecificationLimitsDescriptions.g.cs index d2a17a8d4..2950c6195 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/SpecificationLimitsDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/SpecificationLimitsDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of SpecificationLimits as defined by the MTConnect Standard. + /// public static class SpecificationLimitsDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/Transformation.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/Transformation.g.cs index 7fc0d8923..ce53a868a 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/Transformation.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/Transformation.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class Transformation : ITransformation { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Process of transforming to the origin position of the coordinate system from a parent coordinate system using Translation and Rotation."; @@ -17,7 +20,7 @@ public class Transformation : ITransformation /// Rotations about X, Y, and Z axes are expressed in A, B, and C respectively within a 3-dimensional vector. /// public MTConnect.Devices.Configurations.IAbstractRotation Rotation { get; set; } - + /// /// Translations along X, Y, and Z axes are expressed as x,y, and z respectively within a 3-dimensional vector. /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/TransformationDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/TransformationDescriptions.g.cs index caf7b8c10..de51af1d9 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/TransformationDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/TransformationDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of Transformation as defined by the MTConnect Standard. + /// public static class TransformationDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/Translation.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/Translation.g.cs index 841aeaa42..4ba735a4b 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/Translation.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/Translation.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class Translation : AbstractTranslation, ITranslation { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Translations along X, Y, and Z axes are expressed as x,y, and z respectively within a 3-dimensional vector."; diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/TranslationDataSet.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/TranslationDataSet.g.cs index 0d7c27d9c..1291d23be 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/TranslationDataSet.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/TranslationDataSet.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.Configurations /// public class TranslationDataSet : AbstractTranslation, ITranslationDataSet, IDataSet { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Translations along X, Y, and Z axes are expressed as x,y, and z respectively within a 3-dimensional vector represented as a dataset."; @@ -17,12 +20,12 @@ public class TranslationDataSet : AbstractTranslation, ITranslationDataSet, IDat /// Translation along X axis. /// public string X { get; set; } - + /// /// Translation along Y axis. /// public string Y { get; set; } - + /// /// Translation along Z axis. /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/TranslationDataSetDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/TranslationDataSetDescriptions.g.cs index 71f2b5af7..871d58658 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/TranslationDataSetDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/TranslationDataSetDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of TranslationDataSet as defined by the MTConnect Standard. + /// public static class TranslationDataSetDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Configurations/TranslationDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/Configurations/TranslationDescriptions.g.cs index 09908e812..f66d8f530 100644 --- a/libraries/MTConnect.NET-Common/Devices/Configurations/TranslationDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Configurations/TranslationDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.Configurations { + /// + /// Description text for each property of Translation as defined by the MTConnect Standard. + /// public static class TranslationDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Constraints.g.cs b/libraries/MTConnect.NET-Common/Devices/Constraints.g.cs index 730573f12..1653e7817 100644 --- a/libraries/MTConnect.NET-Common/Devices/Constraints.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Constraints.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices /// public class Constraints : IConstraints { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Organize a set of expected values that can be reported for a DataItem."; @@ -17,22 +20,22 @@ public class Constraints : IConstraints /// Provides a means to control when an agent records updated information for a DataItem. /// public MTConnect.Devices.IFilter Filter { get; set; } - + /// /// Numeric upper constraint.If the data reported for a data item is a range of numeric values, the expected value reported **MAY** be described with an upper limit defined by this constraint. /// public double? Maximum { get; set; } - + /// /// Numeric lower constraint.If the data reported for a data item is a range of numeric values, the expected value reported **MAY** be described with a lower limit defined by this constraint. /// public double? Minimum { get; set; } - + /// /// Numeric target or expected value. /// public double? Nominal { get; set; } - + /// /// Single data value that is expected to be reported for a DataItem.Value **MUST NOT** be used in conjunction with any other Constraint elements. /// diff --git a/libraries/MTConnect.NET-Common/Devices/ConstraintsDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/ConstraintsDescriptions.g.cs index 1ae6daae3..555c4065f 100644 --- a/libraries/MTConnect.NET-Common/Devices/ConstraintsDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/ConstraintsDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each property of Constraints as defined by the MTConnect Standard. + /// public static class ConstraintsDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItem.cs b/libraries/MTConnect.NET-Common/Devices/DataItem.cs index 7ed929847..ad7f1935d 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItem.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItem.cs @@ -46,6 +46,9 @@ public string Uuid set => _uuid = value; } + /// + /// The MTConnect entity classification for this object, which is always . + /// public MTConnectEntityType EntityType => MTConnectEntityType.DataItem; /// @@ -65,22 +68,22 @@ public string Uuid private string _hash; - /// - /// Condensed message digest from a secure one-way hash function. FIPS PUB 180-4 - /// - public string Hash - { - get - { - if (_hash == null) _hash = GenerateHash(); - return _hash; - } - } - - /// - /// The text description that describes what the DataItem Type represents - /// - public virtual string TypeDescription => DescriptionText; + /// + /// Condensed message digest from a secure one-way hash function. FIPS PUB 180-4 + /// + public string Hash + { + get + { + if (_hash == null) _hash = GenerateHash(); + return _hash; + } + } + + /// + /// The text description that describes what the DataItem Type represents + /// + public virtual string TypeDescription => DescriptionText; /// /// The text description that describes what the DataItem SubType represents @@ -122,16 +125,27 @@ public string Hash internal bool _isExtended; /// - /// + /// Indicates that this DataItem uses a Type or SubType that is not defined by the MTConnect Standard, + /// meaning it was created from an unrecognized (vendor- or application-specific) extension value. /// public bool IsExtended => _isExtended; + /// + /// Initializes a new, empty DataItem with its default Type registrations loaded. + /// public DataItem() { Init(); } + /// + /// Initializes a new DataItem with the specified category, type, and optional subtype and identifier. + /// + /// The category (Sample, Event, or Condition) of the DataItem. + /// The Type that defines what the DataItem represents. + /// An optional SubType that further refines the meaning of the Type. + /// An optional unique identifier for the DataItem. public DataItem(DataItemCategory category, string type, string subType = null, string dataItemId = null) { Init(); @@ -142,6 +156,10 @@ public DataItem(DataItemCategory category, string type, string subType = null, s SubType = subType; } + /// + /// Initializes a new DataItem by copying every property from an existing DataItem instance. + /// + /// The DataItem to copy. When null, an empty DataItem is produced. public DataItem(IDataItem dataItem) { Init(); @@ -183,11 +201,20 @@ private void Init() } + /// + /// Computes a content hash for this DataItem that changes whenever any hashed property or relationship changes. + /// + /// A SHA-1 hash string identifying the current state of this DataItem. public string GenerateHash() { return GenerateHash(this); } + /// + /// Computes a content hash for the specified DataItem, incorporating its hashed properties and the hashes of its relationships. + /// + /// The DataItem to hash. + /// A SHA-1 hash string, or null when is null. public static string GenerateHash(IDataItem dataItem) { if (dataItem != null) @@ -211,6 +238,11 @@ public static string GenerateHash(IDataItem dataItem) } + /// + /// Builds the ordered list of Id segments from the containing hierarchy down to the DataItem itself. + /// + /// The DataItem whose Id path is built. + /// The Id segments from the outermost container to the DataItem, or null when is null. public static string[] GenerateIdPaths(IDataItem dataItem) { if (dataItem != null) @@ -230,6 +262,11 @@ public static string[] GenerateIdPaths(IDataItem dataItem) return null; } + /// + /// Builds the slash-delimited Id path string from the containing hierarchy down to the DataItem itself. + /// + /// The DataItem whose Id path is built. + /// The Id segments joined with '/', or null when no path is available. public static string GenerateIdPath(IDataItem dataItem) { if (dataItem != null && !dataItem.IdPaths.IsNullOrEmpty()) @@ -240,6 +277,11 @@ public static string GenerateIdPath(IDataItem dataItem) return null; } + /// + /// Builds the ordered list of Type segments from the containing hierarchy down to the DataItem itself. + /// + /// The DataItem whose Type path is built. + /// The Type segments from the outermost container to the DataItem, or null when is null. public static string[] GenerateTypePaths(IDataItem dataItem) { if (dataItem != null) @@ -259,6 +301,11 @@ public static string[] GenerateTypePaths(IDataItem dataItem) return null; } + /// + /// Builds the slash-delimited Type path string from the containing hierarchy down to the DataItem itself. + /// + /// The DataItem whose Type path is built. + /// The Type segments joined with '/', or null when no path is available. public static string GenerateTypePath(IDataItem dataItem) { if (dataItem != null && !dataItem.TypePaths.IsNullOrEmpty()) @@ -270,11 +317,23 @@ public static string GenerateTypePath(IDataItem dataItem) } + /// + /// Produces a copy of this DataItem adjusted for the specified MTConnect version, dropping members not valid in that version. + /// + /// The target MTConnect Standard version. + /// The version-adjusted DataItem, or null when this DataItem is not valid in that version. public DataItem Process(Version mtconnectVersion) { return Process(this, mtconnectVersion); } + /// + /// Hook for derived DataItem types to apply type-specific adjustments during version processing. + /// The base implementation returns the DataItem unchanged. + /// + /// The DataItem being processed. + /// The target MTConnect Standard version. + /// The adjusted DataItem. protected virtual DataItem OnProcess(DataItem dataItem, Version mtconnectVersion) { return dataItem; @@ -310,8 +369,8 @@ public ValidationResult Validate(Version mtconnectVersion, IObservationInput obs var conditionValidation = ValidateCondition(mtconnectVersion, observation); if (!conditionValidation.IsValid) result = conditionValidation; break; - } - + } + return result; } @@ -356,7 +415,7 @@ public ValidationResult Validate(Version mtconnectVersion, IObservation observat if (!conditionValidation.IsValid) result = conditionValidation; break; } - } + } return result; } @@ -435,22 +494,49 @@ private ValidationResult ValidateCondition(Version mtconnectVersion, IObservatio return OnValidation(mtconnectVersion, observation); } + /// + /// Hook for derived DataItem types to apply type-specific validation of an input value. + /// The base implementation treats every value as valid. + /// + /// The MTConnect Standard version to validate against. + /// The observation input being validated. + /// The validation result for the type-specific check. protected virtual ValidationResult OnValidation(Version mtconnectVerion, IObservationInput observation) { return new ValidationResult(true); } + /// + /// Hook for derived DataItem types to apply type-specific validation of an existing observation. + /// The base implementation treats every observation as valid. + /// + /// The MTConnect Standard version to validate against. + /// The observation being validated. + /// The validation result for the type-specific check. protected virtual ValidationResult OnValidation(Version mtconnectVerion, IObservation observation) { return new ValidationResult(true); } + /// + /// Builds a DataItem Id by combining a parent Id with a name segment. + /// + /// The Id of the containing Component or Device. + /// The name segment to append. + /// The composed Id in the form "parentId_name". public static string CreateId(string parentId, string name) { return $"{parentId}_{name}"; } + /// + /// Builds a DataItem Id from a parent Id and the DataItem's type and optional subtype. + /// + /// The Id of the containing Component or Device. + /// The DataItem Type. + /// An optional SubType included in the Id when present. + /// The composed Id, or null when or is empty. public static string CreateDataItemId(string parentId, string type, string subType = null) { if (!string.IsNullOrEmpty(parentId) && !string.IsNullOrEmpty(type)) @@ -468,6 +554,13 @@ public static string CreateDataItemId(string parentId, string type, string subTy return null; } + /// + /// Builds a DataItem Id from a parent Id, a name segment, and an optional suffix. + /// + /// The Id of the containing Component or Device. + /// The name segment to append. + /// An optional suffix appended after the name when present. + /// The composed Id. public static string CreateId(string parentId, string name, string suffix) { if (!string.IsNullOrEmpty(name)) @@ -521,6 +614,11 @@ public static string GetPascalCaseType(string type) } + /// + /// Creates the most-derived DataItem subclass matching the given DataItem's Type and copies its properties. + /// + /// The source DataItem to recreate as its concrete type. + /// A typed DataItem instance, or a base DataItem when the Type is not recognized. public static DataItem Create(IDataItem dataItem) { var type = GetDataItemType(dataItem.Type); @@ -557,12 +655,22 @@ public static DataItem Create(IDataItem dataItem) return (DataItem)dataItem; } + /// + /// Creates an instance of the DataItem subclass registered for the specified Type identifier. + /// + /// The MTConnect DataItem Type identifier. + /// A new typed DataItem instance, or null when the Type is not recognized. public static DataItem Create(string type) { var t = GetDataItemType(type); return Create(t); } + /// + /// Creates an instance of the specified DataItem CLR type using its parameterless constructor. + /// + /// The concrete DataItem CLR type to instantiate. + /// A new DataItem instance, or null when instantiation fails. public static DataItem Create(Type type) { if (type != null) @@ -582,6 +690,10 @@ public static DataItem Create(Type type) return new DataItem(); } + /// + /// Returns every DataItem Type identifier known to the library across all categories. + /// + /// The registered DataItem Type identifiers. public static IEnumerable GetTypes() { lock (_lock) @@ -592,6 +704,10 @@ public static IEnumerable GetTypes() } } + /// + /// Returns every DataItem Type identifier that belongs to the Condition category. + /// + /// The registered Condition-category Type identifiers. public static IEnumerable GetConditionTypes() { if (_conditionTypes == null) @@ -618,6 +734,10 @@ public static IEnumerable GetConditionTypes() return _conditionTypes; } + /// + /// Returns every DataItem Type identifier that belongs to the Event category. + /// + /// The registered Event-category Type identifiers. public static IEnumerable GetEventTypes() { if (_eventTypes == null) @@ -644,6 +764,10 @@ public static IEnumerable GetEventTypes() return _eventTypes; } + /// + /// Returns every DataItem Type identifier that belongs to the Sample category. + /// + /// The registered Sample-category Type identifiers. public static IEnumerable GetSampleTypes() { if (_sampleTypes == null) @@ -670,6 +794,10 @@ public static IEnumerable GetSampleTypes() return _sampleTypes; } + /// + /// Returns the human-readable description for every known DataItem Type, keyed by Type identifier. + /// + /// Pairs of Type identifier and its description text. public static IEnumerable> GetTypeDescriptions() { if (_typeDescriptions == null) @@ -695,6 +823,10 @@ public static IEnumerable> GetTypeDescriptions() return _typeDescriptions; } + /// + /// Returns the set of valid SubType identifiers for every known DataItem Type, keyed by Type identifier. + /// + /// Pairs of Type identifier and its collection of valid SubType identifiers. public static IEnumerable>> GetSubTypes() { if (_subtypes == null) @@ -731,6 +863,10 @@ public static IEnumerable>> GetSubTypes return _subtypes; } + /// + /// Returns the human-readable description for every known DataItem SubType, keyed by "Type.SubType". + /// + /// Pairs of qualified SubType key and its description text. public static IEnumerable> GetSubTypeDescriptions() { if (_subtypeDescriptions == null) @@ -781,6 +917,10 @@ public static IEnumerable> GetSubTypeDescriptions() return _subtypeDescriptions; } + /// + /// Returns the conventional default name for every known DataItem Type, keyed by Type identifier. + /// + /// Pairs of Type identifier and its default name. public static IEnumerable> GetDefaultNames() { if (_defaultNames == null) @@ -810,6 +950,10 @@ public static IEnumerable> GetDefaultNames() return _defaultNames; } + /// + /// Returns the default measurement Units for every known DataItem Type, keyed by Type identifier. + /// + /// Pairs of Type identifier and its default Units. public static IEnumerable> GetDefaultUnits() { if (_defaultUnits == null) @@ -839,6 +983,10 @@ public static IEnumerable> GetDefaultUnits() return _defaultUnits; } + /// + /// Returns the default significant-digit precision for every known DataItem Type, keyed by Type identifier. + /// + /// Pairs of Type identifier and its default significant-digit count. public static IEnumerable> GetDefaultSignificantDigits() { if (_defaultSignificantDigits == null) @@ -868,6 +1016,11 @@ public static IEnumerable> GetDefaultSignificantDigits return _defaultSignificantDigits; } + /// + /// Resolves the concrete DataItem CLR type registered for the specified Type identifier. + /// + /// The MTConnect DataItem Type identifier. + /// The matching CLR type, or null when the Type is not recognized. public static Type GetDataItemType(string type) { if (!string.IsNullOrEmpty(type)) @@ -894,6 +1047,11 @@ public static Type GetDataItemType(string type) return typeof(DataItem); } + /// + /// Returns the human-readable description for the specified DataItem Type. + /// + /// The MTConnect DataItem Type identifier. + /// The description text, or null when the Type is not recognized. public static string GetDataItemDescription(string type) { if (!string.IsNullOrEmpty(type)) @@ -908,6 +1066,11 @@ public static string GetDataItemDescription(string type) return null; } + /// + /// Returns the valid SubType identifiers for the specified DataItem Type. + /// + /// The MTConnect DataItem Type identifier. + /// The valid SubType identifiers, or null when the Type has none or is not recognized. public static IEnumerable GetDataItemSubTypes(string type) { if (!string.IsNullOrEmpty(type)) @@ -922,6 +1085,12 @@ public static IEnumerable GetDataItemSubTypes(string type) return null; } + /// + /// Returns the human-readable description for a specific SubType of the specified DataItem Type. + /// + /// The MTConnect DataItem Type identifier. + /// The SubType identifier. + /// The description text, or null when the Type/SubType pair is not recognized. public static string GetDataItemSubTypeDescription(string type, string subtype) { if (!string.IsNullOrEmpty(type) && !string.IsNullOrEmpty(subtype)) @@ -936,6 +1105,11 @@ public static string GetDataItemSubTypeDescription(string type, string subtype) return null; } + /// + /// Returns the conventional default name for the specified DataItem Type. + /// + /// The MTConnect DataItem Type identifier. + /// The default name, or null when the Type is not recognized. public static string GetDataItemDefaultName(string type) { if (!string.IsNullOrEmpty(type)) @@ -950,6 +1124,11 @@ public static string GetDataItemDefaultName(string type) return null; } + /// + /// Returns the default measurement Units for the specified DataItem Type. + /// + /// The MTConnect DataItem Type identifier. + /// The default Units, or null when the Type has no defined Units or is not recognized. public static string GetDataItemDefaultUnits(string type) { if (!string.IsNullOrEmpty(type)) @@ -964,6 +1143,11 @@ public static string GetDataItemDefaultUnits(string type) return null; } + /// + /// Returns the default significant-digit precision for the specified DataItem Type. + /// + /// The MTConnect DataItem Type identifier. + /// The default significant-digit count, or zero when none is defined for the Type. public static int GetDataItemDefaultSignificantDigits(string type) { if (!string.IsNullOrEmpty(type)) @@ -1018,6 +1202,12 @@ private static Dictionary GetAllTypes() } + /// + /// Determines whether the specified DataItem is valid for use under the given MTConnect Standard version. + /// + /// The DataItem to check. + /// The target MTConnect Standard version. + /// True when the DataItem's version range includes ; otherwise false. public static bool IsCompatible(IDataItem dataItem, Version mtconnectVersion) { if (dataItem != null) @@ -1028,6 +1218,13 @@ public static bool IsCompatible(IDataItem dataItem, Version mtconnectVersion) return false; } + /// + /// Produces a typed copy of the specified DataItem adjusted for the target MTConnect version, + /// returning null when the DataItem is not valid in that version. + /// + /// The source DataItem to process. + /// The target MTConnect Standard version; when null, the latest version is assumed. + /// The version-adjusted DataItem, or null when it is not valid in that version. public static DataItem Process(IDataItem dataItem, Version mtconnectVersion = null) { if (dataItem != null) @@ -1135,7 +1332,7 @@ public static DataItem Process(IDataItem dataItem, Version mtconnectVersion = nu // Check CompositionId if (version >= MTConnectVersions.Version14) - { + { obj.CompositionId = dataItem.CompositionId; } else if (!string.IsNullOrEmpty(dataItem.CompositionId)) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItem.g.cs index f286481b1..f6e8a6de1 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItem.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices /// public partial class DataItem : IDataItem { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Information reported about a piece of equipment."; @@ -17,112 +20,112 @@ public partial class DataItem : IDataItem /// Specifies the kind of information provided by a data item. /// public MTConnect.Devices.DataItemCategory Category { get; set; } - + /// /// Identifier attribute of the Composition that the reported data is most closely associated. /// public string CompositionId { get; set; } - + /// /// Organize a set of expected values that can be reported for a DataItem. /// public MTConnect.Devices.IConstraints Constraints { get; set; } - + /// /// For measured values relative to a coordinate system like Position, the coordinate system used may be reported.coordinateSystemIdRef. /// public MTConnect.Devices.DataItemCoordinateSystem CoordinateSystem { get; set; } - + /// /// Associated CoordinateSystem context for the DataItem. /// public string CoordinateSystemIdRef { get; set; } - + /// /// Representation is either `DATA_SET` or `TABLE`. /// public MTConnect.Devices.IDataItemDefinition Definition { get; set; } - + /// /// Indication signifying whether each value reported for the Observation is significant and whether duplicate values are to be suppressed.discrete, the default value **MUST** be `false`. /// public bool Discrete { get; set; } - + /// /// Provides a means to control when an agent records updated information for a DataItem. /// public System.Collections.Generic.IEnumerable Filters { get; set; } - + /// /// Unique identifier for this data item. /// public string Id { get; set; } - + /// /// Starting value for a DataItem as well as the value to be set for the DataItem after a reset event. /// public string InitialValue { get; set; } - + /// /// Name of the data item. /// public string Name { get; set; } - + /// /// Used to convert the reported value to represent the original measured value. /// public int NativeScale { get; set; } - + /// /// Native units of measurement for the reported value of the data item. /// public string NativeUnits { get; set; } - + /// /// Association between a DataItem and another entity. /// public System.Collections.Generic.IEnumerable Relationships { get; set; } - + /// /// Description of a means to interpret data consisting of multiple data points or samples reported as a single value. representation is not specified, it **MUST** be determined to be `VALUE`. /// public MTConnect.Devices.DataItemRepresentation Representation { get; set; } - + /// /// Type of event that may cause a reset to occur. /// public MTConnect.Devices.DataItemResetTrigger? ResetTrigger { get; set; } - + /// /// Rate at which successive samples of a data item are recorded by a piece of equipment. /// public double SampleRate { get; set; } - + /// /// Number of significant digits in the reported value. /// public int? SignificantDigits { get; set; } - + /// /// Identifies the Component, DataItem, or Composition from which a measured value originates. /// public MTConnect.Devices.ISource Source { get; set; } - + /// /// Type of statistical calculation performed on a series of data samples to provide the reported data value. /// public MTConnect.Devices.DataItemStatistic? Statistic { get; set; } - + /// /// Type. /// public string SubType { get; set; } - + /// /// Type of data being measured. See DataItem Types. /// public string Type { get; set; } - + /// /// Unit of measurement for the reported value of the data item. /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItemCategory.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItemCategory.g.cs index 66197bc88..d59311fa5 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItemCategory.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItemCategory.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// DataItemCategory controlled vocabulary as defined by the MTConnect Standard. + /// public enum DataItemCategory { /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItemCategoryDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItemCategoryDescriptions.g.cs index 94c81851d..460aa7657 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItemCategoryDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItemCategoryDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class DataItemCategoryDescriptions { /// @@ -21,6 +24,9 @@ public static class DataItemCategoryDescriptions public const string SAMPLE = "Continuously variable or analog data value. A continuous value can be measured at any point-in-time and will always produce a result."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(DataItemCategory value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItemCoordinateSystem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItemCoordinateSystem.g.cs index 85a2f82d3..a45f47442 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItemCoordinateSystem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItemCoordinateSystem.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// DataItemCoordinateSystem controlled vocabulary as defined by the MTConnect Standard. + /// public enum DataItemCoordinateSystem { /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItemCoordinateSystemDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItemCoordinateSystemDescriptions.g.cs index a0c7a35f3..c46127e9c 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItemCoordinateSystemDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItemCoordinateSystemDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class DataItemCoordinateSystemDescriptions { /// @@ -16,6 +19,9 @@ public static class DataItemCoordinateSystemDescriptions public const string WORK = "Coordinate system that represents the working area for a particular workpiece whose origin is shifted within the `MACHINE` coordinate system.If the `WORK` coordinates are not currently defined in the piece of equipment, the `MACHINE` coordinates will be used."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(DataItemCoordinateSystem value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItemDefinition.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItemDefinition.g.cs index 54511b89c..1d2010f68 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItemDefinition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItemDefinition.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices /// public class DataItemDefinition : IDataItemDefinition { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Representation is either `DATA_SET` or `TABLE`."; @@ -17,12 +20,12 @@ public class DataItemDefinition : IDataItemDefinition /// Semantic definition of a Cell. /// public System.Collections.Generic.IEnumerable CellDefinitions { get; set; } - + /// /// Textual description for Definition. /// public string Description { get; set; } - + /// /// Semantic definition of an Entry. /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItemDefinitionDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItemDefinitionDescriptions.g.cs index 1e4d30d5a..d328b4217 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItemDefinitionDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItemDefinitionDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each property of DataItemDefinition as defined by the MTConnect Standard. + /// public static class DataItemDefinitionDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItemDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItemDescriptions.g.cs index 19364ba60..44abfe535 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItemDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItemDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each property of DataItem as defined by the MTConnect Standard. + /// public static class DataItemDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItemFilterType.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItemFilterType.g.cs index 786051e6e..2c880799e 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItemFilterType.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItemFilterType.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// DataItemFilterType controlled vocabulary as defined by the MTConnect Standard. + /// public enum DataItemFilterType { /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItemFilterTypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItemFilterTypeDescriptions.g.cs index 0e562f485..469b7f3a3 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItemFilterTypeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItemFilterTypeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class DataItemFilterTypeDescriptions { /// @@ -16,6 +19,9 @@ public static class DataItemFilterTypeDescriptions public const string PERIOD = "Data reported for a data item is provided on a periodic basis. The `PERIOD` for reporting data is defined in the value of the Filter.The value of Filter **MUST** be an absolute value reported in seconds representing the time between reported samples of the value of the data item."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(DataItemFilterType value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItemRelationship.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItemRelationship.g.cs index 4ca954285..681ac9136 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItemRelationship.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItemRelationship.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices /// public class DataItemRelationship : AbstractDataItemRelationship, IDataItemRelationship { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Type."; diff --git a/libraries/MTConnect.NET-Common/Devices/DataItemRelationshipDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItemRelationshipDescriptions.g.cs index 76fd462c7..6cb186932 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItemRelationshipDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItemRelationshipDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each property of DataItemRelationship as defined by the MTConnect Standard. + /// public static class DataItemRelationshipDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItemRelationshipType.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItemRelationshipType.g.cs index 1e9b415f2..2d3849b97 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItemRelationshipType.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItemRelationshipType.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// DataItemRelationshipType controlled vocabulary as defined by the MTConnect Standard. + /// public enum DataItemRelationshipType { /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItemRelationshipTypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItemRelationshipTypeDescriptions.g.cs index f768ae23f..30b389e08 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItemRelationshipTypeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItemRelationshipTypeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class DataItemRelationshipTypeDescriptions { /// @@ -26,6 +29,9 @@ public static class DataItemRelationshipTypeDescriptions public const string OBSERVATION = "Referenced DataItem provides the observed values."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(DataItemRelationshipType value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItemRepresentation.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItemRepresentation.g.cs index adcea9a77..b09126e2d 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItemRepresentation.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItemRepresentation.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// DataItemRepresentation controlled vocabulary as defined by the MTConnect Standard. + /// public enum DataItemRepresentation { /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItemRepresentationDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItemRepresentationDescriptions.g.cs index 59c987576..277eef7c0 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItemRepresentationDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItemRepresentationDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class DataItemRepresentationDescriptions { /// @@ -31,6 +34,9 @@ public static class DataItemRepresentationDescriptions public const string VALUE = "Measured value of the sample data.representation **MUST** be determined to be `VALUE`."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(DataItemRepresentation value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItemResetTrigger.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItemResetTrigger.g.cs index b9a36163a..5c915d9f8 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItemResetTrigger.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItemResetTrigger.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// DataItemResetTrigger controlled vocabulary as defined by the MTConnect Standard. + /// public enum DataItemResetTrigger { /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItemResetTriggerDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItemResetTriggerDescriptions.g.cs index 0cbf0fd59..75c45865b 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItemResetTriggerDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItemResetTriggerDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class DataItemResetTriggerDescriptions { /// @@ -51,6 +54,9 @@ public static class DataItemResetTriggerDescriptions public const string WEEK = "Observation of the DataItem is to be reset at the end of a 7-day period."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(DataItemResetTrigger value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItemStatistic.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItemStatistic.g.cs index 5e08671fd..d47f88b6a 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItemStatistic.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItemStatistic.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// DataItemStatistic controlled vocabulary as defined by the MTConnect Standard. + /// public enum DataItemStatistic { /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItemStatisticDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItemStatisticDescriptions.g.cs index 169e052fd..d2048e3f2 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItemStatisticDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItemStatisticDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class DataItemStatisticDescriptions { /// @@ -51,6 +54,9 @@ public static class DataItemStatisticDescriptions public const string STANDARD_DEVIATION = "Statistical Standard Deviation value calculated for the data item during the calculation period."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(DataItemStatistic value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AccelerationDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AccelerationDataItem.g.cs index 2a023fa56..bc91d60eb 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AccelerationDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AccelerationDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class AccelerationDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ACCELERATION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "acceleration"; - - public const string DefaultUnits = Devices.Units.MILLIMETER_PER_SECOND_SQUARED; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER_PER_SECOND_SQUARED; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Positive rate of change of velocity."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AccelerationDataItem() { Category = CategoryId; @@ -50,6 +80,11 @@ public AccelerationDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public AccelerationDataItem( string parentId, SubTypes subType @@ -64,8 +99,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +120,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AccumulatedTimeDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AccumulatedTimeDataItem.g.cs index 929dcb774..8fe894738 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AccumulatedTimeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AccumulatedTimeDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class AccumulatedTimeDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ACCUMULATED_TIME"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "accumulatedTime"; - - public const string DefaultUnits = Devices.Units.SECOND; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.SECOND; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Accumulated time for an activity or event."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AccumulatedTimeDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public AccumulatedTimeDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public AccumulatedTimeDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ActivationCountDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ActivationCountDataItem.g.cs index 663e051bb..a9b3dd130 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ActivationCountDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ActivationCountDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class ActivationCountDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ACTIVATION_COUNT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "activationCount"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Accumulation of the number of times a function has attempted to, or is planned to attempt to, activate or be performed."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version18; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version18; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -66,6 +93,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ActivationCountDataItem() { Category = CategoryId; @@ -75,6 +105,11 @@ public ActivationCountDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public ActivationCountDataItem( string parentId, SubTypes subType @@ -89,8 +124,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -109,6 +150,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ActiveAxesDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ActiveAxesDataItem.g.cs index 477a87861..7338ccf9d 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ActiveAxesDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ActiveAxesDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class ActiveAxesDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ACTIVE_AXES"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "activeAxes"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Set of axes currently associated with a Path or Controller."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ActiveAxesDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public ActiveAxesDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ActiveAxesDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ActivePowerSourceDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ActivePowerSourceDataItem.g.cs index 44bcf207d..578a86ad6 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ActivePowerSourceDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ActivePowerSourceDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class ActivePowerSourceDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ACTIVE_POWER_SOURCE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "activePowerSource"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Active energy source for the Component."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version23; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version23; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ActivePowerSourceDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public ActivePowerSourceDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ActivePowerSourceDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ActuatorDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ActuatorDataItem.g.cs index ca7860429..bac05de38 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ActuatorDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ActuatorDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class ActuatorDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.CONDITION; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ACTUATOR"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "actuator"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Indication of a fault associated with an actuator."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ActuatorDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public ActuatorDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ActuatorDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ActuatorStateDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ActuatorStateDataItem.g.cs index 2354360e8..5062721ab 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ActuatorStateDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ActuatorStateDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class ActuatorStateDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ACTUATOR_STATE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "actuatorState"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Operational state of an apparatus for moving or controlling a mechanism or system."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ActuatorStateDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public ActuatorStateDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ActuatorStateDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AdapterSoftwareVersionDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AdapterSoftwareVersionDataItem.g.cs index f488dd43c..b3c30a396 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AdapterSoftwareVersionDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AdapterSoftwareVersionDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class AdapterSoftwareVersionDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ADAPTER_SOFTWARE_VERSION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "adapterSoftwareVersion"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Originator’s software version of the adapter."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AdapterSoftwareVersionDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public AdapterSoftwareVersionDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public AdapterSoftwareVersionDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AdapterUriDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AdapterUriDataItem.g.cs index a436d7fde..a6f52a085 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AdapterUriDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AdapterUriDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class AdapterUriDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ADAPTER_URI"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "adapterUri"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "URI of the adapter."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AdapterUriDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public AdapterUriDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public AdapterUriDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AlarmDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AlarmDataItem.g.cs index e7e9b0862..5867def35 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AlarmDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AlarmDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class AlarmDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ALARM"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "alarm"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "**DEPRECATED:** Replaced with `CONDITION` category data items in Version 1.1.0."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; + + /// + /// The maximum MTConnect Version that this DataItem is valid for; set when the type has been deprecated. + /// public override System.Version MaximumVersion => MTConnectVersions.Version11; - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AlarmDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public AlarmDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public AlarmDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AlarmLimitDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AlarmLimitDataItem.g.cs index fa7a802c8..7ba12da36 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AlarmLimitDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AlarmLimitDataItem.g.cs @@ -10,18 +10,50 @@ namespace MTConnect.Devices.DataItems /// public class AlarmLimitDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ALARM_LIMIT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "alarmLimit"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.DATA_SET; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.DATA_SET; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Set of limits used to trigger warning or alarm indicators.**DEPRECATED** in *Version 2.5*. Replaced by `ALARM_LIMITS`."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; + + /// + /// The maximum MTConnect Version that this DataItem is valid for; set when the type has been deprecated. + /// public override System.Version MaximumVersion => MTConnectVersions.Version25; - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AlarmLimitDataItem() { Category = CategoryId; @@ -31,13 +63,17 @@ public AlarmLimitDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public AlarmLimitDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AlarmLimitsDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AlarmLimitsDataItem.g.cs index 24c189edd..5cec47bda 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AlarmLimitsDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AlarmLimitsDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class AlarmLimitsDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ALARM_LIMITS"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "alarmLimits"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.DATA_SET; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.DATA_SET; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Set of limits used to trigger warning or alarm indicators."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version23; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version23; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AlarmLimitsDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public AlarmLimitsDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public AlarmLimitsDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AmperageACDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AmperageACDataItem.g.cs index 85a249767..39e6d2feb 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AmperageACDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AmperageACDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class AmperageACDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "AMPERAGE_AC"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "amperageAc"; - - public const string DefaultUnits = Devices.Units.AMPERE; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.AMPERE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Electrical current that reverses direction at regular short intervals."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AmperageACDataItem() { Category = CategoryId; @@ -50,6 +80,11 @@ public AmperageACDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public AmperageACDataItem( string parentId, SubTypes subType @@ -64,8 +99,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +120,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AmperageDCDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AmperageDCDataItem.g.cs index eb6464376..b44da34fa 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AmperageDCDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AmperageDCDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class AmperageDCDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "AMPERAGE_DC"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "amperageDc"; - - public const string DefaultUnits = Devices.Units.AMPERE; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.AMPERE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Electric current flowing in one direction only."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AmperageDCDataItem() { Category = CategoryId; @@ -50,6 +80,11 @@ public AmperageDCDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public AmperageDCDataItem( string parentId, SubTypes subType @@ -64,8 +99,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +120,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AmperageDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AmperageDataItem.g.cs index 820a2dd3e..3da1ff182 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AmperageDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AmperageDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class AmperageDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "AMPERAGE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "amperage"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Strength of electrical current.**DEPRECATED** in *Version 1.6*. Replaced by `AMPERAGE_AC` and `AMPERAGE_DC`."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; + + /// + /// The maximum MTConnect Version that this DataItem is valid for; set when the type has been deprecated. + /// public override System.Version MaximumVersion => MTConnectVersions.Version16; - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -46,6 +73,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AmperageDataItem() { Category = CategoryId; @@ -55,6 +85,11 @@ public AmperageDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public AmperageDataItem( string parentId, SubTypes subType @@ -69,8 +104,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -85,6 +126,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AngleDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AngleDataItem.g.cs index 07889be13..83a6c71af 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AngleDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AngleDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class AngleDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ANGLE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "angle"; - - public const string DefaultUnits = Devices.Units.DEGREE; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.DEGREE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Angular position."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AngleDataItem() { Category = CategoryId; @@ -45,6 +75,11 @@ public AngleDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public AngleDataItem( string parentId, SubTypes subType @@ -59,8 +94,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -73,6 +114,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AngularAccelerationDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AngularAccelerationDataItem.g.cs index 42f227ce4..47c663b38 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AngularAccelerationDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AngularAccelerationDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class AngularAccelerationDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ANGULAR_ACCELERATION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "angularAcceleration"; - - public const string DefaultUnits = Devices.Units.DEGREE_PER_SECOND_SQUARED; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.DEGREE_PER_SECOND_SQUARED; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Positive rate of change of angular velocity."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AngularAccelerationDataItem() { Category = CategoryId; @@ -50,6 +80,11 @@ public AngularAccelerationDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public AngularAccelerationDataItem( string parentId, SubTypes subType @@ -64,8 +99,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +120,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AngularDecelerationDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AngularDecelerationDataItem.g.cs index f30a429f4..25647892e 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AngularDecelerationDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AngularDecelerationDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class AngularDecelerationDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ANGULAR_DECELERATION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "angularDeceleration"; - - public const string DefaultUnits = Devices.Units.DEGREE_PER_SECOND_SQUARED; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.DEGREE_PER_SECOND_SQUARED; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Negative rate of change of angular velocity."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AngularDecelerationDataItem() { Category = CategoryId; @@ -50,6 +80,11 @@ public AngularDecelerationDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public AngularDecelerationDataItem( string parentId, SubTypes subType @@ -64,8 +99,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +120,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AngularVelocityDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AngularVelocityDataItem.g.cs index 0c538c9c0..e4dadc476 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AngularVelocityDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AngularVelocityDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class AngularVelocityDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ANGULAR_VELOCITY"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "angularVelocity"; - - public const string DefaultUnits = Devices.Units.DEGREE_PER_SECOND; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.DEGREE_PER_SECOND; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Rate of change of angular position."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AngularVelocityDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public AngularVelocityDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public AngularVelocityDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ApplicationDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ApplicationDataItem.g.cs index 2a176e2d3..5a84ad525 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ApplicationDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ApplicationDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class ApplicationDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "APPLICATION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "application"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Application on a Component."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -51,6 +73,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ApplicationDataItem() { Category = CategoryId; @@ -60,6 +85,11 @@ public ApplicationDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public ApplicationDataItem( string parentId, SubTypes subType @@ -74,8 +104,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -91,6 +127,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AssetAddedDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AssetAddedDataItem.g.cs index 945b06f5f..0215a8269 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AssetAddedDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AssetAddedDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class AssetAddedDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ASSET_ADDED"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "assetAdded"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "AssetId of the Asset that has been added."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version26; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version26; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AssetAddedDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public AssetAddedDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public AssetAddedDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AssetChangedDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AssetChangedDataItem.g.cs index 7d15a7cab..1889501cd 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AssetChangedDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AssetChangedDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class AssetChangedDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ASSET_CHANGED"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "assetChanged"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "AssetId of the Asset that has been changed."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AssetChangedDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public AssetChangedDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public AssetChangedDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AssetCountDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AssetCountDataItem.g.cs index bfa4fca6e..46ad55320 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AssetCountDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AssetCountDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class AssetCountDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ASSET_COUNT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "assetCount"; + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.DATA_SET; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Data set of the number of Asset of a given type for a Device."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version20; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version20; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AssetCountDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public AssetCountDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public AssetCountDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AssetRemovedDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AssetRemovedDataItem.g.cs index b75918d77..5e7399abd 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AssetRemovedDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AssetRemovedDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class AssetRemovedDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ASSET_REMOVED"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "assetRemoved"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "AssetId of the Asset that has been removed."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version13; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AssetRemovedDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public AssetRemovedDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public AssetRemovedDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AssetUpdateRateDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AssetUpdateRateDataItem.g.cs index 6bc4d68f6..f10d445ff 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AssetUpdateRateDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AssetUpdateRateDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class AssetUpdateRateDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ASSET_UPDATE_RATE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "assetUpdateRate"; - - public const string DefaultUnits = Devices.Units.COUNT_PER_SECOND; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.COUNT_PER_SECOND; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Average rate of change of values for assets in the MTConnect streams. The average is computed over a rolling window defined by the implementation."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AssetUpdateRateDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public AssetUpdateRateDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public AssetUpdateRateDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AssociatedAssetIdDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AssociatedAssetIdDataItem.g.cs index e9b4c7bec..c3e281c7d 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AssociatedAssetIdDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AssociatedAssetIdDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class AssociatedAssetIdDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ASSOCIATED_ASSET_ID"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "associatedAssetId"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "AssetId of the Assets associated with a Component."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version26; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version26; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AssociatedAssetIdDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public AssociatedAssetIdDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public AssociatedAssetIdDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AvailabilityDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AvailabilityDataItem.g.cs index c7cdbd694..399a3149c 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AvailabilityDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AvailabilityDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class AvailabilityDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "AVAILABILITY"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "availability"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Agent's ability to communicate with the data source."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AvailabilityDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public AvailabilityDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public AvailabilityDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AxisCouplingDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AxisCouplingDataItem.g.cs index 264e1a9cc..35826732b 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AxisCouplingDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AxisCouplingDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class AxisCouplingDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "AXIS_COUPLING"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "axisCoupling"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Describes the way the axes will be associated to each other. This is used in conjunction with `COUPLED_AXES` to indicate the way they are interacting."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AxisCouplingDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public AxisCouplingDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public AxisCouplingDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AxisFeedrateDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AxisFeedrateDataItem.g.cs index d254e0375..46871704c 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AxisFeedrateDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AxisFeedrateDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class AxisFeedrateDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "AXIS_FEEDRATE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "axisFeedrate"; - - public const string DefaultUnits = Devices.Units.MILLIMETER_PER_SECOND; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER_PER_SECOND; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Feedrate of a linear axis."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -56,6 +83,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AxisFeedrateDataItem() { Category = CategoryId; @@ -65,6 +95,11 @@ public AxisFeedrateDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public AxisFeedrateDataItem( string parentId, SubTypes subType @@ -79,8 +114,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -97,6 +138,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AxisFeedrateOverrideDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AxisFeedrateOverrideDataItem.g.cs index 3598fe0bd..53f7481f9 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AxisFeedrateOverrideDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AxisFeedrateOverrideDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class AxisFeedrateOverrideDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "AXIS_FEEDRATE_OVERRIDE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "axisFeedrateOverride"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Value of a signal or calculation issued to adjust the feedrate of an individual linear type axis."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version13; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AxisFeedrateOverrideDataItem() { Category = CategoryId; @@ -50,6 +80,11 @@ public AxisFeedrateOverrideDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public AxisFeedrateOverrideDataItem( string parentId, SubTypes subType @@ -64,8 +99,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +120,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AxisInterlockDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AxisInterlockDataItem.g.cs index 7fd46034a..dd56ca24c 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AxisInterlockDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AxisInterlockDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class AxisInterlockDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "AXIS_INTERLOCK"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "axisInterlock"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "State of the axis lockout function when power has been removed and the axis is allowed to move freely."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version13; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AxisInterlockDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public AxisInterlockDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public AxisInterlockDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/AxisStateDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/AxisStateDataItem.g.cs index 0a5c181b0..2c1eb4cbb 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/AxisStateDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/AxisStateDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class AxisStateDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "AXIS_STATE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "axisState"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "State of a Linear or Rotary component representing an axis."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version13; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public AxisStateDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public AxisStateDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public AxisStateDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/BatteryCapacityDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/BatteryCapacityDataItem.g.cs index 3d5bf2da7..4d0e25a4f 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/BatteryCapacityDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/BatteryCapacityDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class BatteryCapacityDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "BATTERY_CAPACITY"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "batteryCapacity"; - - public const string DefaultUnits = Devices.Units.COULOMB; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.COULOMB; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Maximum rated charge a battery is capable of maintaining based on the battery discharging at a specified current over a specified time period."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version21; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version21; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public BatteryCapacityDataItem() { Category = CategoryId; @@ -45,6 +75,11 @@ public BatteryCapacityDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public BatteryCapacityDataItem( string parentId, SubTypes subType @@ -59,8 +94,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -73,6 +114,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/BatteryChargeDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/BatteryChargeDataItem.g.cs index bd683b342..71c5d1f22 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/BatteryChargeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/BatteryChargeDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class BatteryChargeDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "BATTERY_CHARGE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "batteryCharge"; - - public const string DefaultUnits = Devices.Units.PERCENT; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.PERCENT; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Value of the battery's present capacity expressed as a percentage of the battery's maximum rated capacity."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version21; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version21; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public BatteryChargeDataItem() { Category = CategoryId; @@ -45,6 +75,11 @@ public BatteryChargeDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public BatteryChargeDataItem( string parentId, SubTypes subType @@ -59,8 +94,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -73,6 +114,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/BatteryStateDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/BatteryStateDataItem.g.cs index 3bae11fba..e2ae63fcd 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/BatteryStateDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/BatteryStateDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class BatteryStateDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "BATTERY_STATE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "batteryState"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Present status of the battery."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version21; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version21; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public BatteryStateDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public BatteryStateDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public BatteryStateDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/BindingStateDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/BindingStateDataItem.g.cs index 1cc7050c9..e2ad2e7e8 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/BindingStateDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/BindingStateDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class BindingStateDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "BINDING_STATE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "bindingState"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "State of the binding process when Component participates in a task as a collaborator"; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version27; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public BindingStateDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public BindingStateDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public BindingStateDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/BlockCountDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/BlockCountDataItem.g.cs index dd3e9be72..db6a45516 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/BlockCountDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/BlockCountDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class BlockCountDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "BLOCK_COUNT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "blockCount"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Total count of the number of blocks of program code that have been executed since execution started."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public BlockCountDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public BlockCountDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public BlockCountDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/BlockDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/BlockDataItem.g.cs index 33ee04f7b..b145af01a 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/BlockDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/BlockDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class BlockDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "BLOCK"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "block"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Line of code or command being executed by a Controller entity."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public BlockDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public BlockDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public BlockDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/CapacityFluidDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/CapacityFluidDataItem.g.cs index 2c7e1f69d..861d3c5c2 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/CapacityFluidDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/CapacityFluidDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class CapacityFluidDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "CAPACITY_FLUID"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "capacityFluid"; - - public const string DefaultUnits = Devices.Units.MILLILITER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLILITER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Maximum amount of fluid that can be held by a container."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public CapacityFluidDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public CapacityFluidDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public CapacityFluidDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/CapacitySpatialDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/CapacitySpatialDataItem.g.cs index b64865c78..2dd6b730e 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/CapacitySpatialDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/CapacitySpatialDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class CapacitySpatialDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "CAPACITY_SPATIAL"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "capacitySpatial"; - - public const string DefaultUnits = Devices.Units.CUBIC_MILLIMETER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.CUBIC_MILLIMETER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Maximum amount of material that can be held by a container."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public CapacitySpatialDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public CapacitySpatialDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public CapacitySpatialDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/CharacteristicPersistentIdDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/CharacteristicPersistentIdDataItem.g.cs index 3ce9cb0aa..7ae1e80d6 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/CharacteristicPersistentIdDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/CharacteristicPersistentIdDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class CharacteristicPersistentIdDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "CHARACTERISTIC_PERSISTENT_ID"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "characteristicPersistentId"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "UUID of the characteristic."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version22; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version22; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public CharacteristicPersistentIdDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public CharacteristicPersistentIdDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public CharacteristicPersistentIdDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/CharacteristicStatusDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/CharacteristicStatusDataItem.g.cs index 4b06d0c66..140f1dc95 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/CharacteristicStatusDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/CharacteristicStatusDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class CharacteristicStatusDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "CHARACTERISTIC_STATUS"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "characteristicStatus"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Pass/fail result of the measurement."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version22; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version22; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public CharacteristicStatusDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public CharacteristicStatusDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public CharacteristicStatusDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ChargeRateDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ChargeRateDataItem.g.cs index 674b80bbc..b31c7e484 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ChargeRateDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ChargeRateDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class ChargeRateDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "CHARGE_RATE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "chargeRate"; - - public const string DefaultUnits = Devices.Units.AMPERE; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.AMPERE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Value of the current being supplied to the Component for the purpose of charging."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version21; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version21; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ChargeRateDataItem() { Category = CategoryId; @@ -45,6 +75,11 @@ public ChargeRateDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public ChargeRateDataItem( string parentId, SubTypes subType @@ -59,8 +94,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -73,6 +114,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ChuckInterlockDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ChuckInterlockDataItem.g.cs index 01b0159e7..e3629db0d 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ChuckInterlockDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ChuckInterlockDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class ChuckInterlockDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "CHUCK_INTERLOCK"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "chuckInterlock"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "State of an interlock function or control logic state intended to prevent the associated Chuck component from being operated."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version13; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ChuckInterlockDataItem() { Category = CategoryId; @@ -45,6 +75,11 @@ public ChuckInterlockDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public ChuckInterlockDataItem( string parentId, SubTypes subType @@ -59,8 +94,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -72,6 +113,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ChuckStateDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ChuckStateDataItem.g.cs index 7c1c61809..0241afef2 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ChuckStateDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ChuckStateDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class ChuckStateDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "CHUCK_STATE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "chuckState"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Operating state of a mechanism that holds a part or stock material during a manufacturing process. It may also represent a mechanism that holds any other mechanism in place within a piece of equipment."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version13; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ChuckStateDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public ChuckStateDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ChuckStateDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ClockTimeDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ClockTimeDataItem.g.cs index 9f02e5e2b..fcad898fd 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ClockTimeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ClockTimeDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class ClockTimeDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "CLOCK_TIME"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "clockTime"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Time provided by a timing device at a specific point in time."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ClockTimeDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public ClockTimeDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ClockTimeDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/CodeDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/CodeDataItem.g.cs index 756c68691..e51b5587e 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/CodeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/CodeDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class CodeDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "CODE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "code"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Programmatic code being executed.**DEPRECATED** in *Version 1.1*."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; + + /// + /// The maximum MTConnect Version that this DataItem is valid for; set when the type has been deprecated. + /// public override System.Version MaximumVersion => MTConnectVersions.Version11; - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public CodeDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public CodeDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public CodeDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/CommunicationsDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/CommunicationsDataItem.g.cs index 5347cf80f..950e5486b 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/CommunicationsDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/CommunicationsDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class CommunicationsDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.CONDITION; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "COMMUNICATIONS"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "communications"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Indication that the piece of equipment has experienced a communications failure."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public CommunicationsDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public CommunicationsDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public CommunicationsDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ComponentDataDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ComponentDataDataItem.g.cs index 068399413..e597ac30e 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ComponentDataDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ComponentDataDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class ComponentDataDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "COMPONENT_DATA"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "componentData"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Event that represents a Component where the EntryDefinition identifies the Component and the CellDefinitions define the Component's observed DataItems."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version22; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version22; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ComponentDataDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public ComponentDataDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ComponentDataDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/CompositionStateDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/CompositionStateDataItem.g.cs index a84c52b0a..6ea03da8b 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/CompositionStateDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/CompositionStateDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class CompositionStateDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "COMPOSITION_STATE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "compositionState"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Operating state of a mechanism represented by a Composition entity."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -51,6 +73,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public CompositionStateDataItem() { Category = CategoryId; @@ -60,6 +85,11 @@ public CompositionStateDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public CompositionStateDataItem( string parentId, SubTypes subType @@ -74,8 +104,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -91,6 +127,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ConcentrationDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ConcentrationDataItem.g.cs index 77805d8b4..5cccc7d50 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ConcentrationDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ConcentrationDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class ConcentrationDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "CONCENTRATION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "concentration"; - - public const string DefaultUnits = Devices.Units.PERCENT; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.PERCENT; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Percentage of one component within a mixture of components."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ConcentrationDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public ConcentrationDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ConcentrationDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ConductivityDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ConductivityDataItem.g.cs index 2b4b0e912..9e65caded 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ConductivityDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ConductivityDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class ConductivityDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "CONDUCTIVITY"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "conductivity"; - - public const string DefaultUnits = Devices.Units.SIEMENS_PER_METER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.SIEMENS_PER_METER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Ability of a material to conduct electricity."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ConductivityDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public ConductivityDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ConductivityDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ConnectionStatusDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ConnectionStatusDataItem.g.cs index 271d02848..16520251c 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ConnectionStatusDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ConnectionStatusDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class ConnectionStatusDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "CONNECTION_STATUS"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "connectionStatus"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Status of the connection between an adapter and an agent."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ConnectionStatusDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public ConnectionStatusDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ConnectionStatusDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ControlLimitDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ControlLimitDataItem.g.cs index b287c0e50..6f549ad66 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ControlLimitDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ControlLimitDataItem.g.cs @@ -10,18 +10,50 @@ namespace MTConnect.Devices.DataItems /// public class ControlLimitDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "CONTROL_LIMIT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "controlLimit"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.DATA_SET; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.DATA_SET; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Set of limits used to indicate whether a process variable is stable and in control.**DEPRECATED** in *Version 2.5*. Replaced by `CONTROL_LIMITS`."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; + + /// + /// The maximum MTConnect Version that this DataItem is valid for; set when the type has been deprecated. + /// public override System.Version MaximumVersion => MTConnectVersions.Version25; - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ControlLimitDataItem() { Category = CategoryId; @@ -31,13 +63,17 @@ public ControlLimitDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ControlLimitDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ControlLimitsDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ControlLimitsDataItem.g.cs index c370c018c..5cbaeb20d 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ControlLimitsDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ControlLimitsDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class ControlLimitsDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "CONTROL_LIMITS"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "controlLimits"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.DATA_SET; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.DATA_SET; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Set of limits used to indicate whether a process variable is stable and in control."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version23; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version23; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ControlLimitsDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public ControlLimitsDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ControlLimitsDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ControllerModeDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ControllerModeDataItem.g.cs index 1e986f473..8d8f7c73f 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ControllerModeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ControllerModeDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class ControllerModeDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "CONTROLLER_MODE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "mode"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Current mode of the Controller component."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ControllerModeDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public ControllerModeDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ControllerModeDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ControllerModeOverrideDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ControllerModeOverrideDataItem.g.cs index 927297b10..e3c4d43ed 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ControllerModeOverrideDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ControllerModeOverrideDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class ControllerModeOverrideDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "CONTROLLER_MODE_OVERRIDE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "controllerModeOverride"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Setting or operator selection that changes the behavior of a piece of equipment."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -56,6 +83,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ControllerModeOverrideDataItem() { Category = CategoryId; @@ -65,6 +95,11 @@ public ControllerModeOverrideDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public ControllerModeOverrideDataItem( string parentId, SubTypes subType @@ -79,8 +114,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -96,6 +137,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/CoupledAxesDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/CoupledAxesDataItem.g.cs index ca496beba..d9199773e 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/CoupledAxesDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/CoupledAxesDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class CoupledAxesDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "COUPLED_AXES"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "coupledAxes"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Set of associated axes."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public CoupledAxesDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public CoupledAxesDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public CoupledAxesDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/CuttingSpeedDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/CuttingSpeedDataItem.g.cs index 53ceba5e2..a5aa2965f 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/CuttingSpeedDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/CuttingSpeedDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class CuttingSpeedDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "CUTTING_SPEED"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "cuttingSpeed"; - - public const string DefaultUnits = Devices.Units.MILLIMETER_PER_SECOND; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER_PER_SECOND; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Speed difference (relative velocity) between the cutting mechanism and the surface of the workpiece it is operating on."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public CuttingSpeedDataItem() { Category = CategoryId; @@ -50,6 +80,11 @@ public CuttingSpeedDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public CuttingSpeedDataItem( string parentId, SubTypes subType @@ -64,8 +99,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +120,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/CycleCountDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/CycleCountDataItem.g.cs index e4b8da74b..ff91dad75 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/CycleCountDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/CycleCountDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class CycleCountDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "CYCLE_COUNT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "cycleCount"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Accumulation of the number of times a cyclic function has attempted to, or is planned to attempt to execute."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version18; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version18; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -66,6 +93,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public CycleCountDataItem() { Category = CategoryId; @@ -75,6 +105,11 @@ public CycleCountDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public CycleCountDataItem( string parentId, SubTypes subType @@ -89,8 +124,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -109,6 +150,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DataRangeDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DataRangeDataItem.g.cs index 886845c83..884974584 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DataRangeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DataRangeDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class DataRangeDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.CONDITION; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DATA_RANGE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "dataRange"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Indication that the value of the data associated with a measured value or a calculation is outside of an expected range."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DataRangeDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public DataRangeDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public DataRangeDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DateCodeDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DateCodeDataItem.g.cs index 1312e7e04..b45a31825 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DateCodeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DateCodeDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class DateCodeDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DATE_CODE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "dateCode"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Time and date code associated with a material or other physical item."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DateCodeDataItem() { Category = CategoryId; @@ -50,6 +80,11 @@ public DateCodeDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public DateCodeDataItem( string parentId, SubTypes subType @@ -64,8 +99,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +120,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DeactivationCountDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DeactivationCountDataItem.g.cs index 268b9da13..8d65cb6a9 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DeactivationCountDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DeactivationCountDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class DeactivationCountDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DEACTIVATION_COUNT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "deactivationCount"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Accumulation of the number of times a function has attempted to, or is planned to attempt to, deactivate or cease."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version18; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version18; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -66,6 +93,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DeactivationCountDataItem() { Category = CategoryId; @@ -75,6 +105,11 @@ public DeactivationCountDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public DeactivationCountDataItem( string parentId, SubTypes subType @@ -89,8 +124,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -109,6 +150,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DecelerationDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DecelerationDataItem.g.cs index 5d32fc65e..7be7766cb 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DecelerationDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DecelerationDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class DecelerationDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DECELERATION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "deceleration"; - - public const string DefaultUnits = Devices.Units.MILLIMETER_PER_SECOND_SQUARED; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER_PER_SECOND_SQUARED; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Negative rate of change of velocity."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DecelerationDataItem() { Category = CategoryId; @@ -50,6 +80,11 @@ public DecelerationDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public DecelerationDataItem( string parentId, SubTypes subType @@ -64,8 +99,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +120,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DensityDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DensityDataItem.g.cs index a37d8a3c5..3a8e77b7e 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DensityDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DensityDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class DensityDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DENSITY"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "density"; - - public const string DefaultUnits = Devices.Units.MILLIGRAM_PER_CUBIC_MILLIMETER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIGRAM_PER_CUBIC_MILLIMETER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Volumetric mass of a material per unit volume of that material."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DensityDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public DensityDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public DensityDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DepositionAccelerationVolumetricDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DepositionAccelerationVolumetricDataItem.g.cs index eec2a1bf7..13784de77 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DepositionAccelerationVolumetricDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DepositionAccelerationVolumetricDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class DepositionAccelerationVolumetricDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DEPOSITION_ACCELERATION_VOLUMETRIC"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "depositionAccelerationVolumetric"; - - public const string DefaultUnits = Devices.Units.CUBIC_MILLIMETER_PER_SECOND_SQUARED; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.CUBIC_MILLIMETER_PER_SECOND_SQUARED; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Rate of change in spatial volume of material deposited in an additive manufacturing process."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DepositionAccelerationVolumetricDataItem() { Category = CategoryId; @@ -45,6 +75,11 @@ public DepositionAccelerationVolumetricDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public DepositionAccelerationVolumetricDataItem( string parentId, SubTypes subType @@ -59,8 +94,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -73,6 +114,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DepositionDensityDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DepositionDensityDataItem.g.cs index e5f6cb874..2d675b8e1 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DepositionDensityDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DepositionDensityDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class DepositionDensityDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DEPOSITION_DENSITY"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "depositionDensity"; - - public const string DefaultUnits = Devices.Units.MILLIGRAM_PER_CUBIC_MILLIMETER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIGRAM_PER_CUBIC_MILLIMETER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Density of the material deposited in an additive manufacturing process per unit of volume."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DepositionDensityDataItem() { Category = CategoryId; @@ -45,6 +75,11 @@ public DepositionDensityDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public DepositionDensityDataItem( string parentId, SubTypes subType @@ -59,8 +94,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -73,6 +114,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DepositionMassDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DepositionMassDataItem.g.cs index 6dd5a4991..d1dafaa6c 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DepositionMassDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DepositionMassDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class DepositionMassDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DEPOSITION_MASS"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "depositionMass"; - - public const string DefaultUnits = Devices.Units.MILLIGRAM; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIGRAM; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Mass of the material deposited in an additive manufacturing process."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DepositionMassDataItem() { Category = CategoryId; @@ -45,6 +75,11 @@ public DepositionMassDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public DepositionMassDataItem( string parentId, SubTypes subType @@ -59,8 +94,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -73,6 +114,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DepositionRateVolumetricDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DepositionRateVolumetricDataItem.g.cs index e5683ccb8..56af5e8f4 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DepositionRateVolumetricDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DepositionRateVolumetricDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class DepositionRateVolumetricDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DEPOSITION_RATE_VOLUMETRIC"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "depositionRateVolumetric"; - - public const string DefaultUnits = Devices.Units.CUBIC_MILLIMETER_PER_SECOND; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.CUBIC_MILLIMETER_PER_SECOND; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Rate at which a spatial volume of material is deposited in an additive manufacturing process."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DepositionRateVolumetricDataItem() { Category = CategoryId; @@ -45,6 +75,11 @@ public DepositionRateVolumetricDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public DepositionRateVolumetricDataItem( string parentId, SubTypes subType @@ -59,8 +94,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -73,6 +114,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DepositionVolumeDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DepositionVolumeDataItem.g.cs index 3dde69312..4166a2b78 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DepositionVolumeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DepositionVolumeDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class DepositionVolumeDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DEPOSITION_VOLUME"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "depositionVolume"; - - public const string DefaultUnits = Devices.Units.CUBIC_MILLIMETER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.CUBIC_MILLIMETER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Spatial volume of material to be deposited in an additive manufacturing process."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DepositionVolumeDataItem() { Category = CategoryId; @@ -45,6 +75,11 @@ public DepositionVolumeDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public DepositionVolumeDataItem( string parentId, SubTypes subType @@ -59,8 +94,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -73,6 +114,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DepthDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DepthDataItem.g.cs index 9fe3a3366..39221e103 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DepthDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DepthDataItem.g.cs @@ -10,18 +10,50 @@ namespace MTConnect.Devices.DataItems /// public class DepthDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DEPTH"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "depth"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Dimension or distance as measured downwards from the top"; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version27; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -46,6 +78,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DepthDataItem() { Category = CategoryId; @@ -55,6 +90,11 @@ public DepthDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public DepthDataItem( string parentId, SubTypes subType @@ -69,8 +109,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -85,6 +131,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DeviceAddedDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DeviceAddedDataItem.g.cs index 9676a2fb8..b3b30b56b 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DeviceAddedDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DeviceAddedDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class DeviceAddedDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DEVICE_ADDED"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "deviceAdded"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "UUID of new device added to an MTConnect Agent."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DeviceAddedDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public DeviceAddedDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public DeviceAddedDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DeviceChangedDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DeviceChangedDataItem.g.cs index 154623933..e4b1e0ed3 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DeviceChangedDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DeviceChangedDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class DeviceChangedDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DEVICE_CHANGED"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "deviceChanged"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "UUID of the device whose metadata has changed."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DeviceChangedDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public DeviceChangedDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public DeviceChangedDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DeviceRemovedDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DeviceRemovedDataItem.g.cs index 8739e2408..3109f3e98 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DeviceRemovedDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DeviceRemovedDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class DeviceRemovedDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DEVICE_REMOVED"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "deviceRemoved"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "UUID of a device removed from an MTConnect Agent."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DeviceRemovedDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public DeviceRemovedDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public DeviceRemovedDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DeviceUuidDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DeviceUuidDataItem.g.cs index 7dd8b6a1e..24c15e354 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DeviceUuidDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DeviceUuidDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class DeviceUuidDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DEVICE_UUID"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "deviceUuid"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Identifier of another piece of equipment that is temporarily associated with a component of this piece of equipment to perform a particular function."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DeviceUuidDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public DeviceUuidDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public DeviceUuidDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DewPointDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DewPointDataItem.g.cs index b8c8f9b66..589b37f1f 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DewPointDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DewPointDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class DewPointDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DEW_POINT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "dewPoint"; - - public const string DefaultUnits = Devices.Units.CELSIUS; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.CELSIUS; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Temperature at which moisture begins to condense, corresponding to saturation for a given absolute humidity."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version21; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version21; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DewPointDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public DewPointDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public DewPointDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DiameterDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DiameterDataItem.g.cs index 77f5befe0..53ffef48d 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DiameterDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DiameterDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class DiameterDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DIAMETER"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "diameter"; - - public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Dimension of a diameter."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DiameterDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public DiameterDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public DiameterDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DirectionDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DirectionDataItem.g.cs index fd240d652..db9b00883 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DirectionDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DirectionDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class DirectionDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DIRECTION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "direction"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Direction of motion."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DirectionDataItem() { Category = CategoryId; @@ -50,6 +80,11 @@ public DirectionDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public DirectionDataItem( string parentId, SubTypes subType @@ -64,8 +99,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -78,6 +119,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DischargeRateDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DischargeRateDataItem.g.cs index f52afde7e..9a5d1f433 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DischargeRateDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DischargeRateDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class DischargeRateDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DISCHARGE_RATE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "dischargeRate"; - - public const string DefaultUnits = Devices.Units.AMPERE; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.AMPERE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Value of current being drawn from the Component."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version21; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version21; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DischargeRateDataItem() { Category = CategoryId; @@ -45,6 +75,11 @@ public DischargeRateDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public DischargeRateDataItem( string parentId, SubTypes subType @@ -59,8 +94,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -73,6 +114,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DisplacementAngularDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DisplacementAngularDataItem.g.cs index f72ee9310..9661295f7 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DisplacementAngularDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DisplacementAngularDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class DisplacementAngularDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DISPLACEMENT_ANGULAR"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "displacementAngular"; - - public const string DefaultUnits = Devices.Units.DEGREE; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.DEGREE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Absolute value of the change in angular position around a vector"; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version21; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version21; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DisplacementAngularDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public DisplacementAngularDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public DisplacementAngularDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DisplacementDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DisplacementDataItem.g.cs index 99187722a..95fe46b9b 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DisplacementDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DisplacementDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class DisplacementDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DISPLACEMENT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "displacement"; - - public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Change in position of an object."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DisplacementDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public DisplacementDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public DisplacementDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DisplacementLinearDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DisplacementLinearDataItem.g.cs index ee6f32b67..fb4bea0d9 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DisplacementLinearDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DisplacementLinearDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class DisplacementLinearDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DISPLACEMENT_LINEAR"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "displacementLinear"; - - public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Absolute value of the change in position along a vector."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version21; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version21; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DisplacementLinearDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public DisplacementLinearDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public DisplacementLinearDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/DoorStateDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/DoorStateDataItem.g.cs index a0a102da2..33ee78370 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/DoorStateDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/DoorStateDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class DoorStateDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "DOOR_STATE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "doorState"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Operational state of a Door component or composition element."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public DoorStateDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public DoorStateDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public DoorStateDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ElectricalEnergyDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ElectricalEnergyDataItem.g.cs index e6e55fe8f..d2858bf99 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ElectricalEnergyDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ElectricalEnergyDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class ElectricalEnergyDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ELECTRICAL_ENERGY"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "electricalEnergy"; - - public const string DefaultUnits = Devices.Units.WATT_SECOND; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.WATT_SECOND; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Wattage used or generated by a component over an interval of time."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ElectricalEnergyDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public ElectricalEnergyDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ElectricalEnergyDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/EmergencyStopDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/EmergencyStopDataItem.g.cs index c018e9731..f2cb320cb 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/EmergencyStopDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/EmergencyStopDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class EmergencyStopDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "EMERGENCY_STOP"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "estop"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "State of the emergency stop signal for a piece of equipment, controller path, or any other component or subsystem of a piece of equipment."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public EmergencyStopDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public EmergencyStopDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public EmergencyStopDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/EndOfBarDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/EndOfBarDataItem.g.cs index a70c3835c..e6cfb7f1d 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/EndOfBarDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/EndOfBarDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class EndOfBarDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "END_OF_BAR"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "endOfBar"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Indication of whether the end of a piece of bar stock being feed by a bar feeder has been reached."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version13; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public EndOfBarDataItem() { Category = CategoryId; @@ -50,6 +80,11 @@ public EndOfBarDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public EndOfBarDataItem( string parentId, SubTypes subType @@ -64,8 +99,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -78,6 +119,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/EquipmentModeDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/EquipmentModeDataItem.g.cs index c06c98431..714e3bb46 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/EquipmentModeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/EquipmentModeDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class EquipmentModeDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "EQUIPMENT_MODE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "equipmentMode"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Indication that a piece of equipment, or a sub-part of a piece of equipment, is performing specific types of activities."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -56,6 +83,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public EquipmentModeDataItem() { Category = CategoryId; @@ -65,6 +95,11 @@ public EquipmentModeDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public EquipmentModeDataItem( string parentId, SubTypes subType @@ -79,8 +114,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -96,6 +137,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/EquipmentTimerDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/EquipmentTimerDataItem.g.cs index 898f02e2e..ba5deff2a 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/EquipmentTimerDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/EquipmentTimerDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class EquipmentTimerDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "EQUIPMENT_TIMER"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "equipmentTimer"; - - public const string DefaultUnits = Devices.Units.SECOND; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.SECOND; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Amount of time a piece of equipment or a sub-part of a piece of equipment has performed specific activities."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -51,6 +78,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public EquipmentTimerDataItem() { Category = CategoryId; @@ -60,6 +90,11 @@ public EquipmentTimerDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public EquipmentTimerDataItem( string parentId, SubTypes subType @@ -74,8 +109,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -91,6 +132,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ExecutionDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ExecutionDataItem.g.cs index d42f3b551..aae1f5092 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ExecutionDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ExecutionDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class ExecutionDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "EXECUTION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "exec"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Operating state of a Component."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ExecutionDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public ExecutionDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ExecutionDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/FeatureMeasurementDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/FeatureMeasurementDataItem.g.cs index c040efdef..797add352 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/FeatureMeasurementDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/FeatureMeasurementDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class FeatureMeasurementDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "FEATURE_MEASUREMENT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "featureMeasurement"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.TABLE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.TABLE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Assessing elements of a feature."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version22; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version22; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public FeatureMeasurementDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public FeatureMeasurementDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public FeatureMeasurementDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/FillHeightDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/FillHeightDataItem.g.cs index 5da2d044a..6e2ff354d 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/FillHeightDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/FillHeightDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class FillHeightDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "FILL_HEIGHT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "fillHeight"; - - public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Amount of a substance in a container."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version25; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version25; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public FillHeightDataItem() { Category = CategoryId; @@ -45,6 +75,11 @@ public FillHeightDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public FillHeightDataItem( string parentId, SubTypes subType @@ -59,8 +94,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -73,6 +114,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/FillLevelDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/FillLevelDataItem.g.cs index 515c7f34b..ca7d44c60 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/FillLevelDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/FillLevelDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class FillLevelDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "FILL_LEVEL"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "fillLevel"; - - public const string DefaultUnits = Devices.Units.PERCENT; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.PERCENT; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Amount of a substance remaining compared to the planned maximum amount of that substance."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public FillLevelDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public FillLevelDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public FillLevelDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/FirmwareDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/FirmwareDataItem.g.cs index c8eec89f6..339acd5b5 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/FirmwareDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/FirmwareDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class FirmwareDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "FIRMWARE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "firmware"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Embedded software of a Component."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -51,6 +73,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public FirmwareDataItem() { Category = CategoryId; @@ -60,6 +85,11 @@ public FirmwareDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public FirmwareDataItem( string parentId, SubTypes subType @@ -74,8 +104,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -91,6 +127,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/FixtureAssetIdDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/FixtureAssetIdDataItem.g.cs index 52cf6f581..4f07e1c4a 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/FixtureAssetIdDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/FixtureAssetIdDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class FixtureAssetIdDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "FIXTURE_ASSET_ID"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "fixtureAssetId"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "AssetId of the Fixture that is associated with a Component"; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version27; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public FixtureAssetIdDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public FixtureAssetIdDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public FixtureAssetIdDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/FixtureIdDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/FixtureIdDataItem.g.cs index e27ef2ae3..f246a8024 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/FixtureIdDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/FixtureIdDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class FixtureIdDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "FIXTURE_ID"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "fixtureId"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Identifier for the current workholding or part clamp in use by a piece of equipment."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version20; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version20; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public FixtureIdDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public FixtureIdDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public FixtureIdDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/FlowDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/FlowDataItem.g.cs index fdcbb3f1c..966291114 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/FlowDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/FlowDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class FlowDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "FLOW"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "flow"; - - public const string DefaultUnits = Devices.Units.LITER_PER_SECOND; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.LITER_PER_SECOND; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Rate of flow of a fluid."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public FlowDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public FlowDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public FlowDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/FollowingErrorAngularDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/FollowingErrorAngularDataItem.g.cs index 84e5d8392..adb7deff4 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/FollowingErrorAngularDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/FollowingErrorAngularDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class FollowingErrorAngularDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "FOLLOWING_ERROR_ANGULAR"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "followingErrorAngular"; - - public const string DefaultUnits = Devices.Units.DEGREE; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.DEGREE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Angular difference between the commanded encoder/resolver position and the actual encoder/resolver position at any specified point in time during a motion."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version21; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version21; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -31,6 +58,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public FollowingErrorAngularDataItem() { Category = CategoryId; @@ -40,6 +70,11 @@ public FollowingErrorAngularDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public FollowingErrorAngularDataItem( string parentId, SubTypes subType @@ -54,8 +89,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -67,6 +108,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/FollowingErrorDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/FollowingErrorDataItem.g.cs index c1d7a1def..22429189a 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/FollowingErrorDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/FollowingErrorDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class FollowingErrorDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "FOLLOWING_ERROR"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "followingError"; - - public const string DefaultUnits = Devices.Units.COUNT; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.COUNT; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Difference between actual and commanded position at any specific point in time during a motion."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version21; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version21; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -31,6 +58,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public FollowingErrorDataItem() { Category = CategoryId; @@ -40,6 +70,11 @@ public FollowingErrorDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public FollowingErrorDataItem( string parentId, SubTypes subType @@ -54,8 +89,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -67,6 +108,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/FollowingErrorLinearDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/FollowingErrorLinearDataItem.g.cs index 7df4e4a5e..5a0a99d0e 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/FollowingErrorLinearDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/FollowingErrorLinearDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class FollowingErrorLinearDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "FOLLOWING_ERROR_LINEAR"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "followingErrorLinear"; - - public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Difference between the commanded encoder/resolver position and the actual encoder/resolver position at any specified point in time during a motion."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version21; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version21; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -31,6 +58,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public FollowingErrorLinearDataItem() { Category = CategoryId; @@ -40,6 +70,11 @@ public FollowingErrorLinearDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public FollowingErrorLinearDataItem( string parentId, SubTypes subType @@ -54,8 +89,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -67,6 +108,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/FrequencyDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/FrequencyDataItem.g.cs index 74739407a..e4306b734 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/FrequencyDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/FrequencyDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class FrequencyDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "FREQUENCY"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "frequency"; - - public const string DefaultUnits = Devices.Units.HERTZ; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.HERTZ; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Number of occurrences of a repeating event per unit time."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public FrequencyDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public FrequencyDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public FrequencyDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/FunctionalModeDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/FunctionalModeDataItem.g.cs index bf49642d3..68e69df22 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/FunctionalModeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/FunctionalModeDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class FunctionalModeDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "FUNCTIONAL_MODE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "functionalMode"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Current intended production status of the Component."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version13; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public FunctionalModeDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public FunctionalModeDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public FunctionalModeDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/GlobalPositionDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/GlobalPositionDataItem.g.cs index 14ee08f11..4bf6851d8 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/GlobalPositionDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/GlobalPositionDataItem.g.cs @@ -10,18 +10,50 @@ namespace MTConnect.Devices.DataItems /// public class GlobalPositionDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "GLOBAL_POSITION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "globalPosition"; - - public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Position in three-dimensional space.**DEPRECATED** in Version 1.1."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; + + /// + /// The maximum MTConnect Version that this DataItem is valid for; set when the type has been deprecated. + /// public override System.Version MaximumVersion => MTConnectVersions.Version11; - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public GlobalPositionDataItem() { Category = CategoryId; @@ -45,6 +80,11 @@ public GlobalPositionDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public GlobalPositionDataItem( string parentId, SubTypes subType @@ -59,8 +99,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -73,6 +119,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/GravitationalAccelerationDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/GravitationalAccelerationDataItem.g.cs index 67da5253d..5a8de0465 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/GravitationalAccelerationDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/GravitationalAccelerationDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class GravitationalAccelerationDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "GRAVITATIONAL_ACCELERATION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "gravitationalAcceleration"; - - public const string DefaultUnits = Devices.NativeUnits.GRAVITATIONAL_ACCELERATION; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.NativeUnits.GRAVITATIONAL_ACCELERATION; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Acceleration relative to Earth's gravity of 9.80665 `METER/SECOND^2`."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version21; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version21; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public GravitationalAccelerationDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public GravitationalAccelerationDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public GravitationalAccelerationDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/GravitationalForceDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/GravitationalForceDataItem.g.cs index 038b886fe..d48571bef 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/GravitationalForceDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/GravitationalForceDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class GravitationalForceDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "GRAVITATIONAL_FORCE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "gravitationalForce"; - - public const string DefaultUnits = Devices.NativeUnits.GRAVITATIONAL_FORCE; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.NativeUnits.GRAVITATIONAL_FORCE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Force relative to earth's gravity."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version21; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version21; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public GravitationalForceDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public GravitationalForceDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public GravitationalForceDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/HardnessDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/HardnessDataItem.g.cs index 650d161d2..ea728d4ab 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/HardnessDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/HardnessDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class HardnessDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "HARDNESS"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "hardness"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Hardness of a material."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -56,6 +83,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public HardnessDataItem() { Category = CategoryId; @@ -65,6 +95,11 @@ public HardnessDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public HardnessDataItem( string parentId, SubTypes subType @@ -79,8 +114,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -97,6 +138,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/HardwareDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/HardwareDataItem.g.cs index a6900f8e0..0eef302e8 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/HardwareDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/HardwareDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class HardwareDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "HARDWARE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "hardware"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Hardware of a Component."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -56,6 +78,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public HardwareDataItem() { Category = CategoryId; @@ -65,6 +90,11 @@ public HardwareDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public HardwareDataItem( string parentId, SubTypes subType @@ -79,8 +109,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -97,6 +133,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/HostNameDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/HostNameDataItem.g.cs index 11c3f3fa4..8c8b160bf 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/HostNameDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/HostNameDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class HostNameDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "HOST_NAME"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "hostName"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Name of the host computer supplying data."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version21; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version21; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public HostNameDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public HostNameDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public HostNameDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/HumidityAbsoluteDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/HumidityAbsoluteDataItem.g.cs index bc123ed68..fafbb699f 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/HumidityAbsoluteDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/HumidityAbsoluteDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class HumidityAbsoluteDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "HUMIDITY_ABSOLUTE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "humidityAbsolute"; - - public const string DefaultUnits = Devices.Units.GRAM_PER_CUBIC_METER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.GRAM_PER_CUBIC_METER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Amount of water vapor expressed in grams per cubic meter."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public HumidityAbsoluteDataItem() { Category = CategoryId; @@ -45,6 +75,11 @@ public HumidityAbsoluteDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public HumidityAbsoluteDataItem( string parentId, SubTypes subType @@ -59,8 +94,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -73,6 +114,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/HumidityRelativeDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/HumidityRelativeDataItem.g.cs index 27860bcfc..930ee990c 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/HumidityRelativeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/HumidityRelativeDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class HumidityRelativeDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "HUMIDITY_RELATIVE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "humidityRelative"; - - public const string DefaultUnits = Devices.Units.PERCENT; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.PERCENT; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Amount of water vapor present expressed as a percent to reach saturation at the same temperature."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public HumidityRelativeDataItem() { Category = CategoryId; @@ -45,6 +75,11 @@ public HumidityRelativeDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public HumidityRelativeDataItem( string parentId, SubTypes subType @@ -59,8 +94,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -73,6 +114,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/HumiditySpecificDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/HumiditySpecificDataItem.g.cs index cc8556494..19cdefa4c 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/HumiditySpecificDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/HumiditySpecificDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class HumiditySpecificDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "HUMIDITY_SPECIFIC"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "humiditySpecific"; - - public const string DefaultUnits = Devices.Units.PERCENT; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.PERCENT; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Ratio of the water vapor present over the total weight of the water vapor and air present expressed as a percent."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public HumiditySpecificDataItem() { Category = CategoryId; @@ -45,6 +75,11 @@ public HumiditySpecificDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public HumiditySpecificDataItem( string parentId, SubTypes subType @@ -59,8 +94,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -73,6 +114,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/LeakDetectDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/LeakDetectDataItem.g.cs index 9ca9c6b15..e19239225 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/LeakDetectDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/LeakDetectDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class LeakDetectDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "LEAK_DETECT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "leakDetect"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Indication designating whether a leak has been detected."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version21; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version21; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public LeakDetectDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public LeakDetectDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public LeakDetectDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/LengthDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/LengthDataItem.g.cs index 325142ca5..030617f64 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/LengthDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/LengthDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class LengthDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "LENGTH"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "length"; - - public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Length of an object."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version13; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public LengthDataItem() { Category = CategoryId; @@ -50,6 +80,11 @@ public LengthDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public LengthDataItem( string parentId, SubTypes subType @@ -64,8 +99,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +120,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/LevelDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/LevelDataItem.g.cs index aef6b4739..fddec55b0 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/LevelDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/LevelDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class LevelDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "LEVEL"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "level"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Level of a resource.**DEPRECATED** in *Version 1.2*. See `FILL_LEVEL`."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; + + /// + /// The maximum MTConnect Version that this DataItem is valid for; set when the type has been deprecated. + /// public override System.Version MaximumVersion => MTConnectVersions.Version12; - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public LevelDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public LevelDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public LevelDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/LibraryDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/LibraryDataItem.g.cs index 1ab708e25..ae1427011 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/LibraryDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/LibraryDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class LibraryDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "LIBRARY"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "library"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Software library on a Component"; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -51,6 +73,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public LibraryDataItem() { Category = CategoryId; @@ -60,6 +85,11 @@ public LibraryDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public LibraryDataItem( string parentId, SubTypes subType @@ -74,8 +104,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -91,6 +127,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/LineDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/LineDataItem.g.cs index fe1c91258..61f6e3ca6 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/LineDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/LineDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class LineDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "LINE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "line"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Current line of code being executed.**DEPRECATED** in *Version 1.4.0*."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; + + /// + /// The maximum MTConnect Version that this DataItem is valid for; set when the type has been deprecated. + /// public override System.Version MaximumVersion => MTConnectVersions.Version14; - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public LineDataItem() { Category = CategoryId; @@ -45,6 +75,11 @@ public LineDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public LineDataItem( string parentId, SubTypes subType @@ -59,8 +94,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -73,6 +114,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/LineLabelDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/LineLabelDataItem.g.cs index 501b15c05..3b044ca12 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/LineLabelDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/LineLabelDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class LineLabelDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "LINE_LABEL"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "lineLabel"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Identifier for a Block of code in a Program."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public LineLabelDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public LineLabelDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public LineLabelDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/LineNumberDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/LineNumberDataItem.g.cs index 8ca6c819f..be4553d7e 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/LineNumberDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/LineNumberDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class LineNumberDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "LINE_NUMBER"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "lineNumber"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Position of a block of program code within a control program."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public LineNumberDataItem() { Category = CategoryId; @@ -45,6 +75,11 @@ public LineNumberDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public LineNumberDataItem( string parentId, SubTypes subType @@ -59,8 +94,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -73,6 +114,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/LinearForceDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/LinearForceDataItem.g.cs index a038243dd..999de40d5 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/LinearForceDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/LinearForceDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class LinearForceDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "LINEAR_FORCE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "linearForce"; - - public const string DefaultUnits = Devices.Units.NEWTON; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.NEWTON; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Force applied to a mass in one direction only."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public LinearForceDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public LinearForceDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public LinearForceDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/LoadCountDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/LoadCountDataItem.g.cs index 4728ed669..1549b446c 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/LoadCountDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/LoadCountDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class LoadCountDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "LOAD_COUNT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "loadCount"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Accumulation of the number of times an operation has attempted to, or is planned to attempt to, load materials, parts, or other items."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version18; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version18; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -66,6 +93,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public LoadCountDataItem() { Category = CategoryId; @@ -75,6 +105,11 @@ public LoadCountDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public LoadCountDataItem( string parentId, SubTypes subType @@ -89,8 +124,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -109,6 +150,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/LoadDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/LoadDataItem.g.cs index 9a20f1481..eef638b8a 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/LoadDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/LoadDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class LoadDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "LOAD"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "load"; - - public const string DefaultUnits = Devices.Units.PERCENT; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.PERCENT; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Actual versus the standard rating of a piece of equipment."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public LoadDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public LoadDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public LoadDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/LocationAddressDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/LocationAddressDataItem.g.cs index a5a842c04..e4abc1815 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/LocationAddressDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/LocationAddressDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class LocationAddressDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "LOCATION_ADDRESS"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "locationAddress"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.DATA_SET; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.DATA_SET; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Structured information that allows the unambiguous determination of an object for purposes of identification and location. ISO 19160-4:2017"; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version23; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version23; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public LocationAddressDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public LocationAddressDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public LocationAddressDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/LocationNarrativeDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/LocationNarrativeDataItem.g.cs index c7bfc3a6f..136575dbd 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/LocationNarrativeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/LocationNarrativeDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class LocationNarrativeDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "LOCATION_NARRATIVE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "locationNarrative"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Textual description of the location of an object or activity."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version24; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version24; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public LocationNarrativeDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public LocationNarrativeDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public LocationNarrativeDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/LocationSpatialGeographicDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/LocationSpatialGeographicDataItem.g.cs index b5c81fc6e..b42a74258 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/LocationSpatialGeographicDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/LocationSpatialGeographicDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class LocationSpatialGeographicDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "LOCATION_SPATIAL_GEOGRAPHIC"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "locationSpatialGeographic"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.DATA_SET; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.DATA_SET; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Absolute geographic location defined by two coordinates, longitude and latitude and an elevation."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version23; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version23; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public LocationSpatialGeographicDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public LocationSpatialGeographicDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public LocationSpatialGeographicDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/LockStateDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/LockStateDataItem.g.cs index a380f7398..1249a9366 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/LockStateDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/LockStateDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class LockStateDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "LOCK_STATE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "lockState"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "State or operating mode of a Lock."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version18; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version18; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public LockStateDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public LockStateDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public LockStateDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/LogicProgramDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/LogicProgramDataItem.g.cs index 9cf6b029a..62af0e777 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/LogicProgramDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/LogicProgramDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class LogicProgramDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.CONDITION; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "LOGIC_PROGRAM"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "logicProgram"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Indication that an error occurred in the logic program or programmable logic controller (PLC) associated with a piece of equipment."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public LogicProgramDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public LogicProgramDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public LogicProgramDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/MTConnectVersionDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/MTConnectVersionDataItem.g.cs index 4abc53e0a..34365cce4 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/MTConnectVersionDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/MTConnectVersionDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class MTConnectVersionDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "MTCONNECT_VERSION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "mtconnectVersion"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Reference version of the MTConnect Standard supported by the adapter."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public MTConnectVersionDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public MTConnectVersionDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public MTConnectVersionDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/MaintenanceListDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/MaintenanceListDataItem.g.cs index 5e7af94b3..2e5e1b1f7 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/MaintenanceListDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/MaintenanceListDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class MaintenanceListDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "MAINTENANCE_LIST"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "maintenanceList"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.TABLE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.TABLE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Actions or activities to be performed in support of a piece of equipment."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version20; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version20; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public MaintenanceListDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public MaintenanceListDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public MaintenanceListDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/MassDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/MassDataItem.g.cs index 90651dab9..f3803126a 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/MassDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/MassDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class MassDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "MASS"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "mass"; - - public const string DefaultUnits = Devices.Units.KILOGRAM; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.KILOGRAM; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Mass of an object(s) or an amount of material."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public MassDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public MassDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public MassDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/MaterialDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/MaterialDataItem.g.cs index 8442ca945..c41bde27c 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/MaterialDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/MaterialDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class MaterialDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "MATERIAL"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "material"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Identifier of a material used or consumed in the manufacturing process"; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public MaterialDataItem() { Category = CategoryId; @@ -50,6 +75,11 @@ public MaterialDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public MaterialDataItem( string parentId, SubTypes subType @@ -64,8 +94,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +115,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/MaterialLayerDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/MaterialLayerDataItem.g.cs index 974443b0b..4149dff4a 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/MaterialLayerDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/MaterialLayerDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class MaterialLayerDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "MATERIAL_LAYER"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "materialLayer"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Identifies the layers of material applied to a part or product as part of an additive manufacturing process."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public MaterialLayerDataItem() { Category = CategoryId; @@ -45,6 +75,11 @@ public MaterialLayerDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public MaterialLayerDataItem( string parentId, SubTypes subType @@ -59,8 +94,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -73,6 +114,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/MeasurementTypeDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/MeasurementTypeDataItem.g.cs index aeacfbd66..9d87282f0 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/MeasurementTypeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/MeasurementTypeDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class MeasurementTypeDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "MEASUREMENT_TYPE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "measurementType"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Class of measurement being performed. QIF 3:2018 Section 6.3"; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version22; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version22; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public MeasurementTypeDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public MeasurementTypeDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public MeasurementTypeDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/MeasurementUnitsDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/MeasurementUnitsDataItem.g.cs index 2d3dd63f2..22ad25d4a 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/MeasurementUnitsDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/MeasurementUnitsDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class MeasurementUnitsDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "MEASUREMENT_UNITS"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "measurementUnits"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Engineering units of the measurement."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version22; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version22; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public MeasurementUnitsDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public MeasurementUnitsDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public MeasurementUnitsDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/MeasurementValueDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/MeasurementValueDataItem.g.cs index ddbb7d407..025653582 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/MeasurementValueDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/MeasurementValueDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class MeasurementValueDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "MEASUREMENT_VALUE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "measurementValue"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Measurement based on the measurement type."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version22; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version22; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public MeasurementValueDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public MeasurementValueDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public MeasurementValueDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/MessageDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/MessageDataItem.g.cs index c4ad7d2f5..8bb5ba140 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/MessageDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/MessageDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class MessageDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "MESSAGE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "message"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Information to be transferred from a piece of equipment to a client software application."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public MessageDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public MessageDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public MessageDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/MotionProgramDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/MotionProgramDataItem.g.cs index 1a4b0f52f..d9393ca1b 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/MotionProgramDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/MotionProgramDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class MotionProgramDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.CONDITION; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "MOTION_PROGRAM"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "motionProgram"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Indication that an error occurred in the motion program associated with a piece of equipment."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public MotionProgramDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public MotionProgramDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public MotionProgramDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/NetworkDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/NetworkDataItem.g.cs index de684082d..9d14fb26b 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/NetworkDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/NetworkDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class NetworkDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "NETWORK"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "network"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Network details of a Component."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -61,6 +83,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public NetworkDataItem() { Category = CategoryId; @@ -70,6 +95,11 @@ public NetworkDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public NetworkDataItem( string parentId, SubTypes subType @@ -84,8 +114,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -103,6 +139,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/NetworkPortDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/NetworkPortDataItem.g.cs index 2318b116b..74a4d5dff 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/NetworkPortDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/NetworkPortDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class NetworkPortDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "NETWORK_PORT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "networkPort"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Number of the TCP/IP or UDP/IP port for the connection endpoint."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version21; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version21; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public NetworkPortDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public NetworkPortDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public NetworkPortDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ObservationUpdateRateDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ObservationUpdateRateDataItem.g.cs index 468255275..8b8d4aa97 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ObservationUpdateRateDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ObservationUpdateRateDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class ObservationUpdateRateDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "OBSERVATION_UPDATE_RATE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "observationUpdateRate"; - - public const string DefaultUnits = Devices.Units.COUNT_PER_SECOND; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.COUNT_PER_SECOND; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Average rate of change of values for data items in the MTConnect streams. The average is computed over a rolling window defined by the implementation."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ObservationUpdateRateDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public ObservationUpdateRateDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ObservationUpdateRateDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/OpennessDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/OpennessDataItem.g.cs index 73e51f1da..11d3ff0eb 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/OpennessDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/OpennessDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class OpennessDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "OPENNESS"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "openness"; - - public const string DefaultUnits = Devices.Units.PERCENT; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.PERCENT; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Percentage open where 100% is fully open and 0% is fully closed."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version20; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version20; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public OpennessDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public OpennessDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public OpennessDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/OperatingModeDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/OperatingModeDataItem.g.cs index 6444f824d..ea71e45ee 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/OperatingModeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/OperatingModeDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class OperatingModeDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "OPERATING_MODE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "operatingMode"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "State of Component or Composition that describes the automatic or manual operation of the entity."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version20; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version20; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public OperatingModeDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public OperatingModeDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public OperatingModeDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/OperatingSystemDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/OperatingSystemDataItem.g.cs index d4ec9cf5a..9c917fff8 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/OperatingSystemDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/OperatingSystemDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class OperatingSystemDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "OPERATING_SYSTEM"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "operatingSystem"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Operating System (OS) of a Component."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -51,6 +73,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public OperatingSystemDataItem() { Category = CategoryId; @@ -60,6 +85,11 @@ public OperatingSystemDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public OperatingSystemDataItem( string parentId, SubTypes subType @@ -74,8 +104,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -91,6 +127,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/OperatorIdDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/OperatorIdDataItem.g.cs index 00ff74cc4..a30f53373 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/OperatorIdDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/OperatorIdDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class OperatorIdDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "OPERATOR_ID"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "operatorId"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Identifier of the person currently responsible for operating the piece of equipment."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version13; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public OperatorIdDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public OperatorIdDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public OperatorIdDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/OrientationDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/OrientationDataItem.g.cs index 527f35571..675f65333 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/OrientationDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/OrientationDataItem.g.cs @@ -10,18 +10,50 @@ namespace MTConnect.Devices.DataItems /// public class OrientationDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ORIENTATION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "orientation"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - public const string DefaultUnits = Devices.Units.DEGREE_3D; + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.DEGREE_3D; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Angular position of a plane or vector relative to a cartesian coordinate system"; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public OrientationDataItem() { Category = CategoryId; @@ -45,6 +80,11 @@ public OrientationDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public OrientationDataItem( string parentId, SubTypes subType @@ -59,8 +99,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -73,6 +119,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PHDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PHDataItem.g.cs index 805fe17b9..1f10454a2 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PHDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PHDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class PHDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PH"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "ph"; - - public const string DefaultUnits = Devices.Units.PH; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.PH; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Acidity or alkalinity of a solution."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PHDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public PHDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public PHDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PalletIdDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PalletIdDataItem.g.cs index 9b4adae54..7a6fdeef7 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PalletIdDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PalletIdDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class PalletIdDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PALLET_ID"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "palletId"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Identifier for a pallet."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PalletIdDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public PalletIdDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public PalletIdDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PartCountDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PartCountDataItem.g.cs index 9f03b8a8a..815306820 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PartCountDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PartCountDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class PartCountDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PART_COUNT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "partCount"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Aggregate count of parts."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -66,6 +93,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PartCountDataItem() { Category = CategoryId; @@ -75,6 +105,11 @@ public PartCountDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public PartCountDataItem( string parentId, SubTypes subType @@ -89,8 +124,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -109,6 +150,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PartCountTypeDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PartCountTypeDataItem.g.cs index 46affab74..350e7b279 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PartCountTypeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PartCountTypeDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class PartCountTypeDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PART_COUNT_TYPE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "partCountType"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Interpretation of `PART_COUNT`."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version20; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version20; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PartCountTypeDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public PartCountTypeDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public PartCountTypeDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PartDetectDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PartDetectDataItem.g.cs index 330daa08d..9ae1a8cdd 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PartDetectDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PartDetectDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class PartDetectDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PART_DETECT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "partDetect"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Indication designating whether a part or work piece has been detected or is present."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PartDetectDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public PartDetectDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public PartDetectDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PartGroupIdDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PartGroupIdDataItem.g.cs index 1e40e176f..b7254476a 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PartGroupIdDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PartGroupIdDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class PartGroupIdDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PART_GROUP_ID"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "partGroupId"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Identifier given to a collection of individual parts."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -51,6 +73,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PartGroupIdDataItem() { Category = CategoryId; @@ -60,6 +85,11 @@ public PartGroupIdDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public PartGroupIdDataItem( string parentId, SubTypes subType @@ -74,8 +104,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -91,6 +127,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PartIdDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PartIdDataItem.g.cs index 9b29f2dc4..d51e2ef55 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PartIdDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PartIdDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class PartIdDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PART_ID"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "partId"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Identifier of a part in a manufacturing operation."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PartIdDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public PartIdDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public PartIdDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PartIndexDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PartIndexDataItem.g.cs index 32017bf3c..e04042057 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PartIndexDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PartIndexDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class PartIndexDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PART_INDEX"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "partIndex"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Sequence of a part in a group of parts."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version25; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version25; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PartIndexDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public PartIndexDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public PartIndexDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PartKindIdDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PartKindIdDataItem.g.cs index 9ced0df96..07eed342f 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PartKindIdDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PartKindIdDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class PartKindIdDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PART_KIND_ID"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "partKindId"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Identifier given to link the individual occurrence to a class of parts, typically distinguished by a particular part design."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -46,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PartKindIdDataItem() { Category = CategoryId; @@ -55,6 +80,11 @@ public PartKindIdDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public PartKindIdDataItem( string parentId, SubTypes subType @@ -69,8 +99,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -85,6 +121,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PartNumberDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PartNumberDataItem.g.cs index ea3572a3f..56f49b341 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PartNumberDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PartNumberDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class PartNumberDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PART_NUMBER"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "partNumber"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Identifier of a part or product moving through the manufacturing process.**DEPRECATED** in *Version 1.7*. `PART_NUMBER` is now a `subType` of `PART_KIND_ID`."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; + + /// + /// The maximum MTConnect Version that this DataItem is valid for; set when the type has been deprecated. + /// public override System.Version MaximumVersion => MTConnectVersions.Version17; - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PartNumberDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public PartNumberDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public PartNumberDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PartProcessingStateDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PartProcessingStateDataItem.g.cs index 7d98aa018..636c149c7 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PartProcessingStateDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PartProcessingStateDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class PartProcessingStateDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PART_PROCESSING_STATE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "partProcessingState"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Particular condition of the part occurrence at a specific time."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version18; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version18; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PartProcessingStateDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public PartProcessingStateDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public PartProcessingStateDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PartStatusDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PartStatusDataItem.g.cs index f3f0ccabf..6a1ddd68b 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PartStatusDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PartStatusDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class PartStatusDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PART_STATUS"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "partStatus"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "State or condition of a part."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PartStatusDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public PartStatusDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public PartStatusDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PartUniqueIdDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PartUniqueIdDataItem.g.cs index e08b60e37..3076f04fe 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PartUniqueIdDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PartUniqueIdDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class PartUniqueIdDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PART_UNIQUE_ID"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "partUniqueId"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Identifier given to a distinguishable, individual part."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PartUniqueIdDataItem() { Category = CategoryId; @@ -50,6 +75,11 @@ public PartUniqueIdDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public PartUniqueIdDataItem( string parentId, SubTypes subType @@ -64,8 +94,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +115,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ParticleCountDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ParticleCountDataItem.g.cs index fe5b9f64e..ed4ed445a 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ParticleCountDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ParticleCountDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class ParticleCountDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PARTICLE_COUNT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "particleCount"; - - public const string DefaultUnits = Devices.Units.COUNT; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.COUNT; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Number of particles counted by their size or other characteristics."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version25; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version25; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ParticleCountDataItem() { Category = CategoryId; @@ -50,6 +80,11 @@ public ParticleCountDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public ParticleCountDataItem( string parentId, SubTypes subType @@ -64,8 +99,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +120,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ParticleSizeDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ParticleSizeDataItem.g.cs index f671a0c9a..215c1a5b0 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ParticleSizeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ParticleSizeDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class ParticleSizeDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PARTICLE_SIZE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "particleSize"; - - public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Size of particles counted by their size or other characteristics."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version25; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version25; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ParticleSizeDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public ParticleSizeDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ParticleSizeDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PathFeedrateDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PathFeedrateDataItem.g.cs index c93c56e38..e97313032 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PathFeedrateDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PathFeedrateDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class PathFeedrateDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PATH_FEEDRATE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "pathFeedrate"; - - public const string DefaultUnits = Devices.Units.MILLIMETER_PER_SECOND; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER_PER_SECOND; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Feedrate for the axes, or a single axis, associated with a Path component."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -56,6 +83,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PathFeedrateDataItem() { Category = CategoryId; @@ -65,6 +95,11 @@ public PathFeedrateDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public PathFeedrateDataItem( string parentId, SubTypes subType @@ -79,8 +114,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -97,6 +138,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PathFeedrateOverrideDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PathFeedrateOverrideDataItem.g.cs index 9aca991fd..d7972dbbc 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PathFeedrateOverrideDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PathFeedrateOverrideDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class PathFeedrateOverrideDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PATH_FEEDRATE_OVERRIDE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "pathFeedrateOverride"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Value of a signal or calculation issued to adjust the feedrate for the axes associated with a Path component that may represent a single axis or the coordinated movement of multiple axes."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version13; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PathFeedrateOverrideDataItem() { Category = CategoryId; @@ -50,6 +80,11 @@ public PathFeedrateOverrideDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public PathFeedrateOverrideDataItem( string parentId, SubTypes subType @@ -64,8 +99,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +120,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PathFeedratePerRevolutionDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PathFeedratePerRevolutionDataItem.g.cs index 29500a76d..deb0c0175 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PathFeedratePerRevolutionDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PathFeedratePerRevolutionDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class PathFeedratePerRevolutionDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PATH_FEEDRATE_PER_REVOLUTION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "pathFeedratePerRevolution"; - - public const string DefaultUnits = Devices.Units.MILLIMETER_PER_REVOLUTION; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER_PER_REVOLUTION; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Feedrate for the axes, or a single axis."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PathFeedratePerRevolutionDataItem() { Category = CategoryId; @@ -50,6 +80,11 @@ public PathFeedratePerRevolutionDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public PathFeedratePerRevolutionDataItem( string parentId, SubTypes subType @@ -64,8 +99,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +120,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PathModeDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PathModeDataItem.g.cs index e4ff59985..121ae92f4 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PathModeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PathModeDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class PathModeDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PATH_MODE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "pathMode"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Describes the operational relationship between a Path entity and another Path entity for pieces of equipment comprised of multiple logical groupings of controlled axes or other logical operations."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PathModeDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public PathModeDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public PathModeDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PathPositionDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PathPositionDataItem.g.cs index 968cb2707..afe0d2eeb 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PathPositionDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PathPositionDataItem.g.cs @@ -10,18 +10,50 @@ namespace MTConnect.Devices.DataItems /// public class PathPositionDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PATH_POSITION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "pathPosition"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - public const string DefaultUnits = Devices.Units.MILLIMETER_3D; + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER_3D; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Position of a control point associated with a Controller or a Path."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -46,6 +78,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PathPositionDataItem() { Category = CategoryId; @@ -55,6 +90,11 @@ public PathPositionDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public PathPositionDataItem( string parentId, SubTypes subType @@ -69,8 +109,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -85,6 +131,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PositionCartesianDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PositionCartesianDataItem.g.cs index f0a3fb600..5b43d07ea 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PositionCartesianDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PositionCartesianDataItem.g.cs @@ -10,18 +10,50 @@ namespace MTConnect.Devices.DataItems /// public class PositionCartesianDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "POSITION_CARTESIAN"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "positionCartesian"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - public const string DefaultUnits = Devices.Units.MILLIMETER_3D; + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER_3D; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Point in a cartesian coordinate system."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version21; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version21; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PositionCartesianDataItem() { Category = CategoryId; @@ -31,13 +63,17 @@ public PositionCartesianDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public PositionCartesianDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PositionDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PositionDataItem.g.cs index f0417a888..fc060a91c 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PositionDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PositionDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class PositionDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "POSITION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "pos"; - - public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Point along an axis in a cartesian coordinate system."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -46,6 +73,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PositionDataItem() { Category = CategoryId; @@ -55,6 +85,11 @@ public PositionDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public PositionDataItem( string parentId, SubTypes subType @@ -69,8 +104,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -85,6 +126,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PowerFactorDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PowerFactorDataItem.g.cs index 3ca929064..82d7c6a2f 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PowerFactorDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PowerFactorDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class PowerFactorDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "POWER_FACTOR"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "powerFactor"; - - public const string DefaultUnits = Devices.Units.PERCENT; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.PERCENT; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Ratio of real power flowing to a load to the apparent power in that AC circuit."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PowerFactorDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public PowerFactorDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public PowerFactorDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PowerStateDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PowerStateDataItem.g.cs index c26b1ffe6..86d5c6482 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PowerStateDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PowerStateDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class PowerStateDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "POWER_STATE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "powerState"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Indication of the status of the source of energy for an entity to allow it to perform its intended function or the state of an enabling signal providing permission for the entity to perform its functions."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PowerStateDataItem() { Category = CategoryId; @@ -50,6 +80,11 @@ public PowerStateDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public PowerStateDataItem( string parentId, SubTypes subType @@ -64,8 +99,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -78,6 +119,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PowerStatusDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PowerStatusDataItem.g.cs index 14c153ab4..0c00fb1b8 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PowerStatusDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PowerStatusDataItem.g.cs @@ -15,18 +15,50 @@ namespace MTConnect.Devices.DataItems /// public class PowerStatusDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "POWER_STATUS"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "powerStatus"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Status of the Component.**DEPRECATED** in *Version 1.1.0*."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; + + /// + /// The maximum MTConnect Version that this DataItem is valid for; set when the type has been deprecated. + /// public override System.Version MaximumVersion => MTConnectVersions.Version11; - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PowerStatusDataItem() { Category = CategoryId; @@ -36,13 +68,17 @@ public PowerStatusDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public PowerStatusDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PressureAbsoluteDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PressureAbsoluteDataItem.g.cs index 46a7bec76..b587f8d5f 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PressureAbsoluteDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PressureAbsoluteDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class PressureAbsoluteDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PRESSURE_ABSOLUTE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "pressureAbsolute"; - - public const string DefaultUnits = Devices.Units.PASCAL; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.PASCAL; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Force per unit area measured relative to a vacuum."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PressureAbsoluteDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public PressureAbsoluteDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public PressureAbsoluteDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PressureDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PressureDataItem.g.cs index b59c2e4ff..2bd72900d 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PressureDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PressureDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class PressureDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PRESSURE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "pressure"; - - public const string DefaultUnits = Devices.Units.PASCAL; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.PASCAL; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Force per unit area measured relative to atmospheric pressure. Commonly referred to as gauge pressure."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PressureDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public PressureDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public PressureDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/PressurizationRateDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/PressurizationRateDataItem.g.cs index 0549161b2..5ca154c93 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/PressurizationRateDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/PressurizationRateDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class PressurizationRateDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PRESSURIZATION_RATE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "pressurizationRate"; - - public const string DefaultUnits = Devices.Units.PASCAL_PER_SECOND; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.PASCAL_PER_SECOND; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Change of pressure per unit time."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public PressurizationRateDataItem() { Category = CategoryId; @@ -50,6 +80,11 @@ public PressurizationRateDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public PressurizationRateDataItem( string parentId, SubTypes subType @@ -64,8 +99,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +120,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessAggregateIdDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessAggregateIdDataItem.g.cs index 96af4495d..b3a08c162 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessAggregateIdDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessAggregateIdDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class ProcessAggregateIdDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PROCESS_AGGREGATE_ID"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "processAggregateId"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Identifier given to link the individual occurrence to a group of related occurrences, such as a process step in a process plan."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ProcessAggregateIdDataItem() { Category = CategoryId; @@ -50,6 +75,11 @@ public ProcessAggregateIdDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public ProcessAggregateIdDataItem( string parentId, SubTypes subType @@ -64,8 +94,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +115,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessKindIdDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessKindIdDataItem.g.cs index 3510a8a4f..e8d9b5509 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessKindIdDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessKindIdDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class ProcessKindIdDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PROCESS_KIND_ID"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "processKindId"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Identifier given to link the individual occurrence to a class of processes or process definition."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ProcessKindIdDataItem() { Category = CategoryId; @@ -50,6 +75,11 @@ public ProcessKindIdDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public ProcessKindIdDataItem( string parentId, SubTypes subType @@ -64,8 +94,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +115,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessOccurrenceIdDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessOccurrenceIdDataItem.g.cs index 65f812e5f..0f1c47b2d 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessOccurrenceIdDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessOccurrenceIdDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class ProcessOccurrenceIdDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PROCESS_OCCURRENCE_ID"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "processOccurrenceId"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Identifier of a process being executed by the device."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -46,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ProcessOccurrenceIdDataItem() { Category = CategoryId; @@ -55,6 +80,11 @@ public ProcessOccurrenceIdDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public ProcessOccurrenceIdDataItem( string parentId, SubTypes subType @@ -69,8 +99,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -85,6 +121,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessStateDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessStateDataItem.g.cs index 5ab02cfaa..df276ff82 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessStateDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessStateDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class ProcessStateDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PROCESS_STATE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "processState"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Particular condition of the process occurrence at a specific time."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version18; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version18; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ProcessStateDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public ProcessStateDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ProcessStateDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessTimeDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessTimeDataItem.g.cs index 596297fd5..72340fad8 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessTimeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessTimeDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class ProcessTimeDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PROCESS_TIME"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "processTime"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Time and date associated with an activity or event."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ProcessTimeDataItem() { Category = CategoryId; @@ -50,6 +75,11 @@ public ProcessTimeDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public ProcessTimeDataItem( string parentId, SubTypes subType @@ -64,8 +94,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +115,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessTimerDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessTimerDataItem.g.cs index ed34063bf..7958f103d 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessTimerDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ProcessTimerDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class ProcessTimerDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PROCESS_TIMER"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "processTimer"; - - public const string DefaultUnits = Devices.Units.SECOND; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.SECOND; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Amount of time a piece of equipment has performed different types of activities associated with the process being performed at that piece of equipment."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ProcessTimerDataItem() { Category = CategoryId; @@ -45,6 +75,11 @@ public ProcessTimerDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public ProcessTimerDataItem( string parentId, SubTypes subType @@ -59,8 +94,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -73,6 +114,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramCommentDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramCommentDataItem.g.cs index e83a40974..7b206de5c 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramCommentDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramCommentDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class ProgramCommentDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PROGRAM_COMMENT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "programComment"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Comment or non-executable statement in the control program."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version13; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ProgramCommentDataItem() { Category = CategoryId; @@ -50,6 +75,11 @@ public ProgramCommentDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public ProgramCommentDataItem( string parentId, SubTypes subType @@ -64,8 +94,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +115,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramDataItem.g.cs index 83543e358..16efc7daf 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class ProgramDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PROGRAM"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "program"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Name of the logic or motion program being executed by the Controller component."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -61,6 +83,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ProgramDataItem() { Category = CategoryId; @@ -70,6 +95,11 @@ public ProgramDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public ProgramDataItem( string parentId, SubTypes subType @@ -84,8 +114,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -103,6 +139,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramEditDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramEditDataItem.g.cs index 6cfe41234..27f5832fd 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramEditDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramEditDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class ProgramEditDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PROGRAM_EDIT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "programEdit"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Indication of the status of the Controller components program editing mode.A program may be edited while another is executed."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version13; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ProgramEditDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public ProgramEditDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ProgramEditDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramEditNameDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramEditNameDataItem.g.cs index 79f4a9ee6..317479778 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramEditNameDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramEditNameDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class ProgramEditNameDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PROGRAM_EDIT_NAME"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "programEditName"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Name of the program being edited. This is used in conjunction with ProgramEdit when in `ACTIVE` state."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version13; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ProgramEditNameDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public ProgramEditNameDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ProgramEditNameDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramHeaderDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramHeaderDataItem.g.cs index 37aa66ad7..184f8b869 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramHeaderDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramHeaderDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class ProgramHeaderDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PROGRAM_HEADER"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "programHeader"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Non-executable header section of the control program."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version13; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ProgramHeaderDataItem() { Category = CategoryId; @@ -50,6 +75,11 @@ public ProgramHeaderDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public ProgramHeaderDataItem( string parentId, SubTypes subType @@ -64,8 +94,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +115,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramLocationDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramLocationDataItem.g.cs index 80f1595c7..2c8f6d8a9 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramLocationDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramLocationDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class ProgramLocationDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PROGRAM_LOCATION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "programLocation"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "URI for the source file associated with Program."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ProgramLocationDataItem() { Category = CategoryId; @@ -50,6 +75,11 @@ public ProgramLocationDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public ProgramLocationDataItem( string parentId, SubTypes subType @@ -64,8 +94,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +115,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramLocationTypeDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramLocationTypeDataItem.g.cs index 451e11d02..c86d59ec9 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramLocationTypeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramLocationTypeDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class ProgramLocationTypeDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PROGRAM_LOCATION_TYPE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "programLocationType"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Defines whether the logic or motion program defined by Program is being executed from the local memory of the controller or from an outside source."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -46,6 +73,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ProgramLocationTypeDataItem() { Category = CategoryId; @@ -55,6 +85,11 @@ public ProgramLocationTypeDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public ProgramLocationTypeDataItem( string parentId, SubTypes subType @@ -69,8 +104,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -84,6 +125,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramNestLevelDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramNestLevelDataItem.g.cs index b0676bc9c..885a77c37 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramNestLevelDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ProgramNestLevelDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class ProgramNestLevelDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "PROGRAM_NEST_LEVEL"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "programNestLevel"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Indication of the nesting level within a control program that is associated with the code or instructions that is currently being executed."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ProgramNestLevelDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public ProgramNestLevelDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ProgramNestLevelDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ResistanceDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ResistanceDataItem.g.cs index 2c132f4c0..99a26de5e 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ResistanceDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ResistanceDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class ResistanceDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "RESISTANCE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "resistance"; - - public const string DefaultUnits = Devices.Units.OHM; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.OHM; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Degree to which a substance opposes the passage of an electric current."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ResistanceDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public ResistanceDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ResistanceDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ResistivityDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ResistivityDataItem.g.cs index c221f5fa2..ed9534999 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ResistivityDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ResistivityDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class ResistivityDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "RESISTIVITY"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "resistivity"; - - public const string DefaultUnits = Devices.Units.OHM_METER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.OHM_METER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Inability of a material to conduct electricity."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version25; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version25; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ResistivityDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public ResistivityDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ResistivityDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/RotaryModeDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/RotaryModeDataItem.g.cs index 13e60c567..251163d61 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/RotaryModeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/RotaryModeDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class RotaryModeDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ROTARY_MODE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "rotaryMode"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Current operating mode for a Rotary type axis."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public RotaryModeDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public RotaryModeDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public RotaryModeDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/RotaryVelocityDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/RotaryVelocityDataItem.g.cs index 394dc67cf..5c0bf5618 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/RotaryVelocityDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/RotaryVelocityDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class RotaryVelocityDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ROTARY_VELOCITY"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "rotaryVelocity"; - - public const string DefaultUnits = Devices.Units.REVOLUTION_PER_MINUTE; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.REVOLUTION_PER_MINUTE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Rotational speed of a rotary axis."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -46,6 +73,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public RotaryVelocityDataItem() { Category = CategoryId; @@ -55,6 +85,11 @@ public RotaryVelocityDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public RotaryVelocityDataItem( string parentId, SubTypes subType @@ -69,8 +104,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -85,6 +126,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/RotaryVelocityOverrideDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/RotaryVelocityOverrideDataItem.g.cs index c687e5720..372892775 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/RotaryVelocityOverrideDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/RotaryVelocityOverrideDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class RotaryVelocityOverrideDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ROTARY_VELOCITY_OVERRIDE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "rotaryVelocityOverride"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Percentage change to the velocity of the programmed velocity for a Rotary axis."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version13; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public RotaryVelocityOverrideDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public RotaryVelocityOverrideDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public RotaryVelocityOverrideDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/RotationDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/RotationDataItem.g.cs index b1c743cc2..1ef4e51e8 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/RotationDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/RotationDataItem.g.cs @@ -10,18 +10,50 @@ namespace MTConnect.Devices.DataItems /// public class RotationDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "ROTATION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "rotation"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - public const string DefaultUnits = Devices.Units.DEGREE_3D; + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.DEGREE_3D; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Three space angular displacement of an object or coordinate system relative to a cartesian coordinate system."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public RotationDataItem() { Category = CategoryId; @@ -31,13 +63,17 @@ public RotationDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public RotationDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/SensorAttachmentDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/SensorAttachmentDataItem.g.cs index e55193931..ca6e5070a 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/SensorAttachmentDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/SensorAttachmentDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class SensorAttachmentDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "SENSOR_ATTACHMENT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "sensorAttachment"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.DATA_SET; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.DATA_SET; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Attachment between a sensor and an entity."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public SensorAttachmentDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public SensorAttachmentDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public SensorAttachmentDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/SensorStateDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/SensorStateDataItem.g.cs index 35d0a31a2..08bc1ae82 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/SensorStateDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/SensorStateDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class SensorStateDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "SENSOR_STATE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "sensorState"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Detection result of a sensor."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version22; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version22; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -46,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public SensorStateDataItem() { Category = CategoryId; @@ -55,6 +80,11 @@ public SensorStateDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public SensorStateDataItem( string parentId, SubTypes subType @@ -69,8 +99,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -85,6 +121,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/SerialNumberDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/SerialNumberDataItem.g.cs index d50dfe492..f188a6c18 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/SerialNumberDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/SerialNumberDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class SerialNumberDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "SERIAL_NUMBER"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "serialNumber"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Serial number associated with a Component, Asset, or Device."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public SerialNumberDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public SerialNumberDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public SerialNumberDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/SettlingErrorAngularDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/SettlingErrorAngularDataItem.g.cs index 6759e2b70..ecb4b84dc 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/SettlingErrorAngularDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/SettlingErrorAngularDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class SettlingErrorAngularDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "SETTLING_ERROR_ANGULAR"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "settlingErrorAngular"; - - public const string DefaultUnits = Devices.Units.DEGREE; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.DEGREE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Angular difference between the commanded encoder/resolver position, and the actual encoder/resolver position when motion is complete."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version21; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version21; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -31,6 +58,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public SettlingErrorAngularDataItem() { Category = CategoryId; @@ -40,6 +70,11 @@ public SettlingErrorAngularDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public SettlingErrorAngularDataItem( string parentId, SubTypes subType @@ -54,8 +89,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -67,6 +108,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/SettlingErrorDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/SettlingErrorDataItem.g.cs index 50d8a1e25..d5fe0d658 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/SettlingErrorDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/SettlingErrorDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class SettlingErrorDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "SETTLING_ERROR"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "settlingError"; - - public const string DefaultUnits = Devices.Units.COUNT; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.COUNT; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Difference between actual and commanded position at the end of a motion."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version21; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version21; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -31,6 +58,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public SettlingErrorDataItem() { Category = CategoryId; @@ -40,6 +70,11 @@ public SettlingErrorDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public SettlingErrorDataItem( string parentId, SubTypes subType @@ -54,8 +89,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -67,6 +108,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/SettlingErrorLinearDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/SettlingErrorLinearDataItem.g.cs index fc42bc218..9e8d14f70 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/SettlingErrorLinearDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/SettlingErrorLinearDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class SettlingErrorLinearDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "SETTLING_ERROR_LINEAR"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "settlingErrorLinear"; - - public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Difference between the commanded encoder/resolver position, and the actual encoder/resolver position when motion is complete."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version21; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version21; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -31,6 +58,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public SettlingErrorLinearDataItem() { Category = CategoryId; @@ -40,6 +70,11 @@ public SettlingErrorLinearDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public SettlingErrorLinearDataItem( string parentId, SubTypes subType @@ -54,8 +89,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -67,6 +108,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/SoundLevelDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/SoundLevelDataItem.g.cs index adc9d6bd9..e1239c386 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/SoundLevelDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/SoundLevelDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class SoundLevelDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "SOUND_LEVEL"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "soundLevel"; - - public const string DefaultUnits = Devices.Units.DECIBEL; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.DECIBEL; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Sound level or sound pressure level relative to atmospheric pressure."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -51,6 +78,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public SoundLevelDataItem() { Category = CategoryId; @@ -60,6 +90,11 @@ public SoundLevelDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public SoundLevelDataItem( string parentId, SubTypes subType @@ -74,8 +109,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -91,6 +132,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/SpecificationLimitDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/SpecificationLimitDataItem.g.cs index 6d98d3009..2e5734e50 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/SpecificationLimitDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/SpecificationLimitDataItem.g.cs @@ -10,18 +10,50 @@ namespace MTConnect.Devices.DataItems /// public class SpecificationLimitDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "SPECIFICATION_LIMIT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "specificationLimit"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.DATA_SET; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.DATA_SET; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Set of limits defining a range of values designating acceptable performance for a variable.**DEPRECATED** in *Version 2.5*. Replaced by `SPECIFICATION_LIMITS`."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; + + /// + /// The maximum MTConnect Version that this DataItem is valid for; set when the type has been deprecated. + /// public override System.Version MaximumVersion => MTConnectVersions.Version25; - public override System.Version MinimumVersion => MTConnectVersions.Version17; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version17; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public SpecificationLimitDataItem() { Category = CategoryId; @@ -31,13 +63,17 @@ public SpecificationLimitDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public SpecificationLimitDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/SpecificationLimitsDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/SpecificationLimitsDataItem.g.cs index 91d2286ac..f60deb274 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/SpecificationLimitsDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/SpecificationLimitsDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class SpecificationLimitsDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "SPECIFICATION_LIMITS"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "specificationLimits"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.DATA_SET; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.DATA_SET; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Set of limits defining a range of values designating acceptable performance for a variable."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version23; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version23; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public SpecificationLimitsDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public SpecificationLimitsDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public SpecificationLimitsDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/SpindleInterlockDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/SpindleInterlockDataItem.g.cs index 8b305e8a0..0228cb0de 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/SpindleInterlockDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/SpindleInterlockDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class SpindleInterlockDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "SPINDLE_INTERLOCK"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "spindleInterlock"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Indication of the status of the spindle for a piece of equipment when power has been removed and it is free to rotate."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version13; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public SpindleInterlockDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public SpindleInterlockDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public SpindleInterlockDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/SpindleSpeedDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/SpindleSpeedDataItem.g.cs index c3a9d5b0d..fd88d523b 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/SpindleSpeedDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/SpindleSpeedDataItem.g.cs @@ -10,18 +10,50 @@ namespace MTConnect.Devices.DataItems /// public class SpindleSpeedDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "SPINDLE_SPEED"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "spindleSpeed"; - - public const string DefaultUnits = Devices.Units.REVOLUTION_PER_MINUTE; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.REVOLUTION_PER_MINUTE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Rotational speed of the rotary axis.**DEPRECATED** in *Version 1.2*. Replaced by `ROTARY_VELOCITY`."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; + + /// + /// The maximum MTConnect Version that this DataItem is valid for; set when the type has been deprecated. + /// public override System.Version MaximumVersion => MTConnectVersions.Version12; - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +73,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public SpindleSpeedDataItem() { Category = CategoryId; @@ -50,6 +85,11 @@ public SpindleSpeedDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public SpindleSpeedDataItem( string parentId, SubTypes subType @@ -64,8 +104,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +125,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/StrainDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/StrainDataItem.g.cs index e2a867b77..d71694ecd 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/StrainDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/StrainDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class StrainDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "STRAIN"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "strain"; - - public const string DefaultUnits = Devices.Units.PERCENT; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.PERCENT; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Amount of deformation per unit length of an object when a load is applied."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public StrainDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public StrainDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public StrainDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/SwingAngleDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/SwingAngleDataItem.g.cs index ec1c3542d..74ff8ee48 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/SwingAngleDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/SwingAngleDataItem.g.cs @@ -10,18 +10,50 @@ namespace MTConnect.Devices.DataItems /// public class SwingAngleDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "SWING_ANGLE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "swingAngle"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Angular range over which the object is designed to move about a fixed axis or pivot"; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version27; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public SwingAngleDataItem() { Category = CategoryId; @@ -31,13 +63,17 @@ public SwingAngleDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public SwingAngleDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/SwingDiameterDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/SwingDiameterDataItem.g.cs index 16c01c994..a76ee1565 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/SwingDiameterDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/SwingDiameterDataItem.g.cs @@ -10,18 +10,50 @@ namespace MTConnect.Devices.DataItems /// public class SwingDiameterDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "SWING_DIAMETER"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "swingDiameter"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Maximal linear width (diameter) of the area described by the object’s movement about an axis"; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version27; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public SwingDiameterDataItem() { Category = CategoryId; @@ -31,13 +63,17 @@ public SwingDiameterDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public SwingDiameterDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/SwingRadiusDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/SwingRadiusDataItem.g.cs index 4085ae076..9596111bf 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/SwingRadiusDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/SwingRadiusDataItem.g.cs @@ -10,18 +10,50 @@ namespace MTConnect.Devices.DataItems /// public class SwingRadiusDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "SWING_RADIUS"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "swingRadius"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Maximal linear distance from the pivot or axis to the furthest point reached by the object’s swing"; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version27; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public SwingRadiusDataItem() { Category = CategoryId; @@ -31,13 +63,17 @@ public SwingRadiusDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public SwingRadiusDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/SystemDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/SystemDataItem.g.cs index 47286a4b1..2f03d7bf2 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/SystemDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/SystemDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class SystemDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.CONDITION; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "SYSTEM"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "system"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "General purpose indication associated with an electronic component of a piece of equipment or a controller that represents a fault that is not associated with the operator, program, or hardware."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public SystemDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public SystemDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public SystemDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/TaskAssetIdDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/TaskAssetIdDataItem.g.cs index 5e13b4ef4..3b871e376 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/TaskAssetIdDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/TaskAssetIdDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class TaskAssetIdDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "TASK_ASSET_ID"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "taskAssetId"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "AssetId of the Task that the Component binds to"; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version27; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public TaskAssetIdDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public TaskAssetIdDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public TaskAssetIdDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/TemperatureDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/TemperatureDataItem.g.cs index f0483e15e..d7d15e30b 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/TemperatureDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/TemperatureDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class TemperatureDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "TEMPERATURE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "temp"; - - public const string DefaultUnits = Devices.Units.CELSIUS; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.CELSIUS; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Degree of hotness or coldness measured on a definite scale."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public TemperatureDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public TemperatureDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public TemperatureDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/TensionDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/TensionDataItem.g.cs index c15d59d79..3950eef14 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/TensionDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/TensionDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class TensionDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "TENSION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "tension"; - - public const string DefaultUnits = Devices.Units.NEWTON; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.NEWTON; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Force that stretches or elongates an object."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public TensionDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public TensionDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public TensionDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ThicknessDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ThicknessDataItem.g.cs index 58d84c8b5..a970d0f49 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ThicknessDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ThicknessDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class ThicknessDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "THICKNESS"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "thickness"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Dimension between two surfaces of an object, usually the dimension of smallest measure, for example an additive layer, or a depth of cut."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version24; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version24; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -46,6 +73,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ThicknessDataItem() { Category = CategoryId; @@ -55,6 +85,11 @@ public ThicknessDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public ThicknessDataItem( string parentId, SubTypes subType @@ -69,8 +104,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -85,6 +126,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/TiltDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/TiltDataItem.g.cs index 87834fe30..a5328d76e 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/TiltDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/TiltDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class TiltDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "TILT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "tilt"; - - public const string DefaultUnits = Devices.Units.MICRO_RADIAN; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MICRO_RADIAN; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Angular displacement."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public TiltDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public TiltDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public TiltDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ToolAssetIdDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ToolAssetIdDataItem.g.cs index 420ca13c2..b82c4ffb0 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ToolAssetIdDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ToolAssetIdDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class ToolAssetIdDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "TOOL_ASSET_ID"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "toolAssetId"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Identifier of an individual tool asset."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ToolAssetIdDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public ToolAssetIdDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ToolAssetIdDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ToolCuttingItemDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ToolCuttingItemDataItem.g.cs index 5e1f037c4..95c26b532 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ToolCuttingItemDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ToolCuttingItemDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class ToolCuttingItemDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "TOOL_CUTTING_ITEM"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "toolCuttingItem"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Indices of the currently active cutting tool edge."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version23; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version23; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ToolCuttingItemDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public ToolCuttingItemDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ToolCuttingItemDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ToolGroupDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ToolGroupDataItem.g.cs index fade61484..f57192302 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ToolGroupDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ToolGroupDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class ToolGroupDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "TOOL_GROUP"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "toolGroup"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Identifier for the tool group associated with a specific tool. Commonly used to designate spare tools."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ToolGroupDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public ToolGroupDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ToolGroupDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ToolIdDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ToolIdDataItem.g.cs index 67b676911..133fe5c76 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ToolIdDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ToolIdDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class ToolIdDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "TOOL_ID"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "toolId"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Identifier of the tool currently in use for a given `Path`.**DEPRECATED** in *Version 1.2.0*. See `TOOL_NUMBER`."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; + + /// + /// The maximum MTConnect Version that this DataItem is valid for; set when the type has been deprecated. + /// public override System.Version MaximumVersion => MTConnectVersions.Version12; - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ToolIdDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public ToolIdDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ToolIdDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ToolNumberDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ToolNumberDataItem.g.cs index 45496996d..4983e2296 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ToolNumberDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ToolNumberDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class ToolNumberDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "TOOL_NUMBER"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "toolNumber"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Identifier assigned by the Controller component to a cutting tool when in use by a piece of equipment."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ToolNumberDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public ToolNumberDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ToolNumberDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ToolOffsetDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ToolOffsetDataItem.g.cs index 54882dfc4..2f5871a84 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ToolOffsetDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ToolOffsetDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class ToolOffsetDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "TOOL_OFFSET"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "toolOffset"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Reference to the tool offset variables applied to the active cutting tool."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ToolOffsetDataItem() { Category = CategoryId; @@ -45,6 +75,11 @@ public ToolOffsetDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public ToolOffsetDataItem( string parentId, SubTypes subType @@ -59,8 +94,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -73,6 +114,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ToolOffsetsDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ToolOffsetsDataItem.g.cs index 32432999b..d910bf8f1 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ToolOffsetsDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ToolOffsetsDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class ToolOffsetsDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "TOOL_OFFSETS"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "toolOffsets"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.TABLE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.TABLE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Properties of each addressable tool offset."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version22; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version22; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ToolOffsetsDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public ToolOffsetsDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ToolOffsetsDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/TorqueDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/TorqueDataItem.g.cs index 6068ac7c7..819d9cda9 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/TorqueDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/TorqueDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class TorqueDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "TORQUE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "torque"; - - public const string DefaultUnits = Devices.Units.NEWTON_METER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.NEWTON_METER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Turning force exerted on an object or by an object."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public TorqueDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public TorqueDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public TorqueDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/TransferCountDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/TransferCountDataItem.g.cs index 21108cf80..2b3ec7215 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/TransferCountDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/TransferCountDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class TransferCountDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "TRANSFER_COUNT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "transferCount"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Accumulation of the number of times an operation has attempted to, or is planned to attempt to, transfer materials, parts, or other items from one location to another."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version18; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version18; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -66,6 +93,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public TransferCountDataItem() { Category = CategoryId; @@ -75,6 +105,11 @@ public TransferCountDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public TransferCountDataItem( string parentId, SubTypes subType @@ -89,8 +124,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -109,6 +150,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/TranslationDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/TranslationDataItem.g.cs index 04c10113b..d5ca8d201 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/TranslationDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/TranslationDataItem.g.cs @@ -10,18 +10,50 @@ namespace MTConnect.Devices.DataItems /// public class TranslationDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "TRANSLATION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "translation"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - public const string DefaultUnits = Devices.Units.MILLIMETER_3D; + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER_3D; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Three space linear displacement of an object or coordinate system relative to a cartesian coordinate system."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public TranslationDataItem() { Category = CategoryId; @@ -31,13 +63,17 @@ public TranslationDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public TranslationDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/UncertaintyDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/UncertaintyDataItem.g.cs index f7999b850..20b010b83 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/UncertaintyDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/UncertaintyDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class UncertaintyDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "UNCERTAINTY"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "uncertainty"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Uncertainty specified by UncertaintyType."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version22; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version22; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public UncertaintyDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public UncertaintyDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public UncertaintyDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/UncertaintyTypeDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/UncertaintyTypeDataItem.g.cs index 7d30b1242..59a35010a 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/UncertaintyTypeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/UncertaintyTypeDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class UncertaintyTypeDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "UNCERTAINTY_TYPE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "uncertaintyType"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Method used to compute standard uncertainty."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version22; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version22; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public UncertaintyTypeDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public UncertaintyTypeDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public UncertaintyTypeDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/UnloadCountDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/UnloadCountDataItem.g.cs index 02d4d888b..e23cf970c 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/UnloadCountDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/UnloadCountDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class UnloadCountDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "UNLOAD_COUNT"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "unloadCount"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Accumulation of the number of times an operation has attempted to, or is planned to attempt to, unload materials, parts, or other items."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version18; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version18; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -66,6 +93,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public UnloadCountDataItem() { Category = CategoryId; @@ -75,6 +105,11 @@ public UnloadCountDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public UnloadCountDataItem( string parentId, SubTypes subType @@ -89,8 +124,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -109,6 +150,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/UserDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/UserDataItem.g.cs index fcc24108b..7693458c0 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/UserDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/UserDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class UserDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "USER"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "user"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Identifier of the person currently responsible for operating the piece of equipment."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public UserDataItem() { Category = CategoryId; @@ -50,6 +75,11 @@ public UserDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public UserDataItem( string parentId, SubTypes subType @@ -64,8 +94,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +115,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ValveStateDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ValveStateDataItem.g.cs index ac613cdc0..c272275ff 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ValveStateDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ValveStateDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class ValveStateDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "VALVE_STATE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "valveState"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "State of a valve is one of open, closed, or transitioning between the states."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version18; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version18; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ValveStateDataItem() { Category = CategoryId; @@ -50,6 +80,11 @@ public ValveStateDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public ValveStateDataItem( string parentId, SubTypes subType @@ -64,8 +99,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -78,6 +119,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/VariableDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/VariableDataItem.g.cs index 6c44da1d2..713efec74 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/VariableDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/VariableDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class VariableDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "VARIABLE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "variable"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Data whose meaning may change over time due to changes in the operation of a piece of equipment or the process being executed on that piece of equipment."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public VariableDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public VariableDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public VariableDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/VelocityDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/VelocityDataItem.g.cs index 89c352992..1c40ce12e 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/VelocityDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/VelocityDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class VelocityDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "VELOCITY"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "velocity"; - - public const string DefaultUnits = Devices.Units.MILLIMETER_PER_SECOND; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER_PER_SECOND; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Rate of change of position of a Component."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public VelocityDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public VelocityDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public VelocityDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ViscosityDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ViscosityDataItem.g.cs index b396b5dc9..7ae55c75c 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ViscosityDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ViscosityDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class ViscosityDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "VISCOSITY"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "viscosity"; - - public const string DefaultUnits = Devices.Units.PASCAL_SECOND; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.PASCAL_SECOND; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Fluid's resistance to flow."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ViscosityDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public ViscosityDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ViscosityDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/VoltAmpereDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/VoltAmpereDataItem.g.cs index 16088acc0..f3a6561d9 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/VoltAmpereDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/VoltAmpereDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class VoltAmpereDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "VOLT_AMPERE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "voltAmpere"; - - public const string DefaultUnits = Devices.Units.VOLT_AMPERE; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.VOLT_AMPERE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Apparent power in an electrical circuit, equal to the product of root-mean-square (RMS) voltage and RMS current (commonly referred to as VA)."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public VoltAmpereDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public VoltAmpereDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public VoltAmpereDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/VoltAmpereReactiveDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/VoltAmpereReactiveDataItem.g.cs index 4626e9056..d63e9c699 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/VoltAmpereReactiveDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/VoltAmpereReactiveDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class VoltAmpereReactiveDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "VOLT_AMPERE_REACTIVE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "voltAmpereReactive"; - - public const string DefaultUnits = Devices.Units.VOLT_AMPERE_REACTIVE; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.VOLT_AMPERE_REACTIVE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Reactive power in an AC electrical circuit (commonly referred to as VAR)."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version12; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version12; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public VoltAmpereReactiveDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public VoltAmpereReactiveDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public VoltAmpereReactiveDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/VoltageACDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/VoltageACDataItem.g.cs index 1e94646c8..fbc21c019 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/VoltageACDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/VoltageACDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class VoltageACDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "VOLTAGE_AC"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "voltageAc"; - - public const string DefaultUnits = Devices.Units.VOLT; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.VOLT; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Electrical potential between two points in an electrical circuit in which the current periodically reverses direction."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public VoltageACDataItem() { Category = CategoryId; @@ -50,6 +80,11 @@ public VoltageACDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public VoltageACDataItem( string parentId, SubTypes subType @@ -64,8 +99,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +120,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/VoltageDCDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/VoltageDCDataItem.g.cs index 932a0ea25..c71108560 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/VoltageDCDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/VoltageDCDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class VoltageDCDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "VOLTAGE_DC"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "voltageDc"; - - public const string DefaultUnits = Devices.Units.VOLT; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.VOLT; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Electrical potential between two points in an electrical circuit in which the current is unidirectional."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -41,6 +68,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public VoltageDCDataItem() { Category = CategoryId; @@ -50,6 +80,11 @@ public VoltageDCDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public VoltageDCDataItem( string parentId, SubTypes subType @@ -64,8 +99,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -79,6 +120,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/VoltageDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/VoltageDataItem.g.cs index f5a79cd3e..4562f0f3c 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/VoltageDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/VoltageDataItem.g.cs @@ -10,18 +10,50 @@ namespace MTConnect.Devices.DataItems /// public class VoltageDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "VOLTAGE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "voltage"; - - public const string DefaultUnits = Devices.Units.VOLT; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.VOLT; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Electrical potential between two points.**DEPRECATED** in *Version 1.6*. Replaced by `VOLTAGE_AC` and `VOLTAGE_DC`."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; + + /// + /// The maximum MTConnect Version that this DataItem is valid for; set when the type has been deprecated. + /// public override System.Version MaximumVersion => MTConnectVersions.Version16; - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -46,6 +78,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public VoltageDataItem() { Category = CategoryId; @@ -55,6 +90,11 @@ public VoltageDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public VoltageDataItem( string parentId, SubTypes subType @@ -69,8 +109,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -85,6 +131,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/VolumeFluidDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/VolumeFluidDataItem.g.cs index 4978f5757..8e39e9cc9 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/VolumeFluidDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/VolumeFluidDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class VolumeFluidDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "VOLUME_FLUID"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "volumeFluid"; - - public const string DefaultUnits = Devices.Units.MILLILITER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLILITER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Fluid volume of an object or container."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -56,6 +83,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public VolumeFluidDataItem() { Category = CategoryId; @@ -65,6 +95,11 @@ public VolumeFluidDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public VolumeFluidDataItem( string parentId, SubTypes subType @@ -79,8 +114,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -97,6 +138,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/VolumeSpatialDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/VolumeSpatialDataItem.g.cs index 48b0d1961..67d5acc14 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/VolumeSpatialDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/VolumeSpatialDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class VolumeSpatialDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "VOLUME_SPATIAL"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "volumeSpatial"; - - public const string DefaultUnits = Devices.Units.CUBIC_MILLIMETER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.CUBIC_MILLIMETER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Geometric volume of an object or container."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -56,6 +83,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public VolumeSpatialDataItem() { Category = CategoryId; @@ -65,6 +95,11 @@ public VolumeSpatialDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public VolumeSpatialDataItem( string parentId, SubTypes subType @@ -79,8 +114,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -97,6 +138,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/WaitStateDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/WaitStateDataItem.g.cs index 59682f0cf..adc653d94 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/WaitStateDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/WaitStateDataItem.g.cs @@ -15,18 +15,45 @@ namespace MTConnect.Devices.DataItems /// public class WaitStateDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "WAIT_STATE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "waitState"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.VALUE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Indication of the reason that Execution is reporting a value of `WAIT`."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version15; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version15; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public WaitStateDataItem() { Category = CategoryId; @@ -36,13 +63,17 @@ public WaitStateDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public WaitStateDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } /// diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/WaterHardnessDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/WaterHardnessDataItem.g.cs index a06ad1f71..d1e785246 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/WaterHardnessDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/WaterHardnessDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class WaterHardnessDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "WATER_HARDNESS"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "waterHardness"; - - public const string DefaultUnits = Devices.Units.MILLIGRAM_PER_LITER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIGRAM_PER_LITER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Concentration of calcium carbonate (CaCO3) in water"; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version27; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public WaterHardnessDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public WaterHardnessDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public WaterHardnessDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/WattageDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/WattageDataItem.g.cs index f176d5b1e..af9f16a00 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/WattageDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/WattageDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class WattageDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "WATTAGE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "wattage"; - - public const string DefaultUnits = Devices.Units.WATT; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.WATT; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Power flowing through or dissipated by an electrical circuit or piece of equipment."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version10; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version10; + /// + /// The set of subType values defined for this DataItem by the MTConnect Standard. + /// public enum SubTypes { /// @@ -36,6 +63,9 @@ public enum SubTypes } + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public WattageDataItem() { Category = CategoryId; @@ -45,6 +75,11 @@ public WattageDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this DataItem belongs to. + /// The subType to assign to this DataItem. public WattageDataItem( string parentId, SubTypes subType @@ -59,8 +94,14 @@ SubTypes subType Units = DefaultUnits; } + /// + /// The MTConnect Standard description of this DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -73,6 +114,9 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/WireDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/WireDataItem.g.cs index 171ea9635..149417b2a 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/WireDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/WireDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class WireDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "WIRE"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "wire"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Identifier for the type of wire used as the cutting mechanism in Electrical Discharge Machining or similar processes."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public WireDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public WireDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public WireDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/WorkOffsetDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/WorkOffsetDataItem.g.cs index 1efca5f15..2dd8df43c 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/WorkOffsetDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/WorkOffsetDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class WorkOffsetDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "WORK_OFFSET"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "workOffset"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Reference to offset variables for a work piece or part."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version14; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version14; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public WorkOffsetDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public WorkOffsetDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public WorkOffsetDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/WorkOffsetsDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/WorkOffsetsDataItem.g.cs index f1fb6a185..34cf9deb1 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/WorkOffsetsDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/WorkOffsetsDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class WorkOffsetsDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "WORK_OFFSETS"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "workOffsets"; - public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.TABLE; - + + /// + /// The default representation for this DataItem as defined by the MTConnect Standard. + /// + public const DataItemRepresentation DefaultRepresentation = DataItemRepresentation.TABLE; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Properties of each addressable work offset."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version22; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version22; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public WorkOffsetsDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public WorkOffsetsDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public WorkOffsetsDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - Representation = DefaultRepresentation; + Representation = DefaultRepresentation; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/WorkholdingIdDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/WorkholdingIdDataItem.g.cs index 3c4bad3cb..60ef9156c 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/WorkholdingIdDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/WorkholdingIdDataItem.g.cs @@ -10,18 +10,40 @@ namespace MTConnect.Devices.DataItems /// public class WorkholdingIdDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "WORKHOLDING_ID"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "workholdingId"; - - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Identifier for the current workholding or part clamp in use by a piece of equipment.**DEPRECATION WARNING**: Recommend using `FIXTURE_ID` instead."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version11; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version11; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public WorkholdingIdDataItem() { Category = CategoryId; @@ -31,13 +53,17 @@ public WorkholdingIdDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public WorkholdingIdDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/XDimensionDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/XDimensionDataItem.g.cs index c25b8c230..17cd8c938 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/XDimensionDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/XDimensionDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class XDimensionDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "X_DIMENSION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "xDimension"; - - public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Dimension of an entity relative to the X direction of the referenced coordinate system."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public XDimensionDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public XDimensionDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public XDimensionDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/YDimensionDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/YDimensionDataItem.g.cs index 78e58a60b..4c0b9e48a 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/YDimensionDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/YDimensionDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class YDimensionDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "Y_DIMENSION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "yDimension"; - - public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Dimension of an entity relative to the Y direction of the referenced coordinate system."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public YDimensionDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public YDimensionDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public YDimensionDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/DataItems/ZDimensionDataItem.g.cs b/libraries/MTConnect.NET-Common/Devices/DataItems/ZDimensionDataItem.g.cs index abd969370..9046348c6 100644 --- a/libraries/MTConnect.NET-Common/Devices/DataItems/ZDimensionDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DataItems/ZDimensionDataItem.g.cs @@ -10,18 +10,45 @@ namespace MTConnect.Devices.DataItems /// public class ZDimensionDataItem : DataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.SAMPLE; + + /// + /// The MTConnect type value that identifies this DataItem. + /// public const string TypeId = "Z_DIMENSION"; + + /// + /// The default name assigned to an instance of this DataItem. + /// public const string NameId = "zDimension"; - - public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The default units for this DataItem as defined by the MTConnect Standard. + /// + public const string DefaultUnits = Devices.Units.MILLIMETER; + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Dimension of an entity relative to the Z direction of the referenced coordinate system."; - + + /// + /// The description of this DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version16; + + /// + /// The minimum MTConnect Version that introduced this DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version16; + /// + /// Initializes a new instance with its category, type, and name set to the defaults for this DataItem. + /// public ZDimensionDataItem() { Category = CategoryId; @@ -31,13 +58,17 @@ public ZDimensionDataItem() Units = DefaultUnits; } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this DataItem belongs to. public ZDimensionDataItem(string deviceId) { Id = CreateId(deviceId, NameId); Category = CategoryId; Type = TypeId; Name = NameId; - + Units = DefaultUnits; } } diff --git a/libraries/MTConnect.NET-Common/Devices/Description.g.cs b/libraries/MTConnect.NET-Common/Devices/Description.g.cs index 0e2cb5996..7bfa4657d 100644 --- a/libraries/MTConnect.NET-Common/Devices/Description.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Description.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices /// public class Description : IDescription { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Descriptive content."; @@ -17,22 +20,22 @@ public class Description : IDescription /// Name of the manufacturer of the physical or logical part of a piece of equipment represented by this element. /// public string Manufacturer { get; set; } - + /// /// Model description of the physical part or logical function of a piece of equipment represented by this element. /// public string Model { get; set; } - + /// /// Serial number associated with a piece of equipment. /// public string SerialNumber { get; set; } - + /// /// Identifier where a manufacturing function takes place. /// public string Station { get; set; } - + /// /// Description of the element. /// diff --git a/libraries/MTConnect.NET-Common/Devices/DescriptionDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/DescriptionDescriptions.g.cs index d001b72bc..deb061aa9 100644 --- a/libraries/MTConnect.NET-Common/Devices/DescriptionDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DescriptionDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each property of Description as defined by the MTConnect Standard. + /// public static class DescriptionDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Device.cs b/libraries/MTConnect.NET-Common/Devices/Device.cs index 715a6f449..5c543ca37 100644 --- a/libraries/MTConnect.NET-Common/Devices/Device.cs +++ b/libraries/MTConnect.NET-Common/Devices/Device.cs @@ -10,10 +10,16 @@ namespace MTConnect.Devices { public partial class Device : IDevice { + /// + /// The MTConnect type identifier for a Device element. + /// public const string TypeId = "Device"; private static readonly Version DefaultMaximumVersion = null; private static readonly Version DefaultMinimumVersion = MTConnectVersions.Version10; + /// + /// The MTConnect entity classification for this object, which is always . + /// public MTConnectEntityType EntityType => MTConnectEntityType.Device; @@ -27,6 +33,9 @@ public partial class Device : IDevice /// public string Iso841Class { get; set; } + /// + /// The DataItems defined directly on this Device. + /// public IEnumerable DataItems { get; set; } /// @@ -84,31 +93,52 @@ public partial class Device : IDevice public virtual Version MinimumVersion => DefaultMinimumVersion; - public string ComponentIdFormat { get; set; } + /// + /// The pattern used to generate Ids for child Components added to this Device. + /// + public string ComponentIdFormat { get; set; } - public string CompositionIdFormat { get; set; } + /// + /// The pattern used to generate Ids for child Compositions added to this Device. + /// + public string CompositionIdFormat { get; set; } - public string DataItemIdFormat { get; set; } + /// + /// The pattern used to generate Ids for DataItems added to this Device. + /// + public string DataItemIdFormat { get; set; } - public Device() + /// + /// Initializes a new Device with empty child collections and the default Id-format patterns. + /// + public Device() { Type = TypeId; DataItems = new List(); Components = new List(); Compositions = new List(); - DataItemIdFormat = Component._defaultDataItemIdFormat; - CompositionIdFormat = Component._defaultCompositionIdFormat; - ComponentIdFormat = Component._defaultComponentIdFormat; - } + DataItemIdFormat = Component._defaultDataItemIdFormat; + CompositionIdFormat = Component._defaultCompositionIdFormat; + ComponentIdFormat = Component._defaultComponentIdFormat; + } + /// + /// Computes a content hash for this Device that changes whenever its hashed members change. + /// + /// A SHA-1 hash string identifying the current state of this Device. public string GenerateHash() { return GenerateHash(this); } + /// + /// Computes a content hash for the specified Device from its hashed members and child entities. + /// + /// The Device to hash. + /// A SHA-1 hash string, or null when is null. public static string GenerateHash(IDevice device) { if (device != null) @@ -162,6 +192,11 @@ public static string GenerateHash(IDevice device) return null; } + /// + /// Computes a content hash for the entire Device tree, combining the Device's hash with every descendant's hash. + /// + /// The Device whose full subtree is hashed. + /// A SHA-1 hash string covering the Device and all of its descendants. public static string CreateDeviceHash(IDevice device) { var s = ObjectExtensions.GetHashPropertyString(device); @@ -210,35 +245,35 @@ private static List GetComponents(IComponent component) return l.Count > 0 ? l : null; } - /// - /// Return the first Component matching the Type - /// - public IComponent GetComponent(string type, string name = null, SearchType searchType = SearchType.AnyLevel) - { - if (!string.IsNullOrEmpty(type)) - { - IEnumerable components = null; - switch (searchType) - { - case SearchType.Child: components = Components; break; - case SearchType.AnyLevel: components = GetComponents(); break; - } - - if (!components.IsNullOrEmpty()) - { - if (!string.IsNullOrEmpty(name)) - { - return components.FirstOrDefault(o => o.Type == type && o.Name == name); - } - else - { - return components.FirstOrDefault(o => o.Type == type); - } - } - } - - return null; - } + /// + /// Return the first Component matching the Type + /// + public IComponent GetComponent(string type, string name = null, SearchType searchType = SearchType.AnyLevel) + { + if (!string.IsNullOrEmpty(type)) + { + IEnumerable components = null; + switch (searchType) + { + case SearchType.Child: components = Components; break; + case SearchType.AnyLevel: components = GetComponents(); break; + } + + if (!components.IsNullOrEmpty()) + { + if (!string.IsNullOrEmpty(name)) + { + return components.FirstOrDefault(o => o.Type == type && o.Name == name); + } + else + { + return components.FirstOrDefault(o => o.Type == type); + } + } + } + + return null; + } /// /// Return the first Component matching the Type @@ -262,31 +297,31 @@ public IComponent GetComponent(string name = null, SearchType search /// Return All Components matching the Type /// public IEnumerable GetComponents(string type, string name = null, SearchType searchType = SearchType.AnyLevel) - { - if (!string.IsNullOrEmpty(type)) - { - IEnumerable components = null; - switch (searchType) - { - case SearchType.Child: components = Components; break; - case SearchType.AnyLevel: components = GetComponents(); break; - } - - if (!components.IsNullOrEmpty()) - { - if (!string.IsNullOrEmpty(name)) - { - return components.Where(o => o.Type == type && o.Name == name); - } - else - { - return components.Where(o => o.Type == type); - } - } - } - - return null; - } + { + if (!string.IsNullOrEmpty(type)) + { + IEnumerable components = null; + switch (searchType) + { + case SearchType.Child: components = Components; break; + case SearchType.AnyLevel: components = GetComponents(); break; + } + + if (!components.IsNullOrEmpty()) + { + if (!string.IsNullOrEmpty(name)) + { + return components.Where(o => o.Type == type && o.Name == name); + } + else + { + return components.Where(o => o.Type == type); + } + } + } + + return null; + } /// /// Return All Components matching the Type @@ -315,15 +350,15 @@ public void AddComponent(IComponent component) { if (component != null) { - component.Parent = this; + component.Parent = this; - // Set ID - if (!string.IsNullOrEmpty(Id) && string.IsNullOrEmpty(component.Id)) - { - Component.ResetIds(component); - } + // Set ID + if (!string.IsNullOrEmpty(Id) && string.IsNullOrEmpty(component.Id)) + { + Component.ResetIds(component); + } - var components = new List(); + var components = new List(); if (!Components.IsNullOrEmpty()) { @@ -339,12 +374,12 @@ public void AddComponent(IComponent component) if (organizer != null) { organizer.Parent = this; - organizer.Id = Component.CreateContainerId(organizer, ComponentIdFormat); - organizer.AddComponent(component); + organizer.Id = Component.CreateContainerId(organizer, ComponentIdFormat); + organizer.AddComponent(component); components.Add(organizer); } } - else + else { var organizer = (Component)components.FirstOrDefault(o => o.Type == organizerType); if (organizer != null) @@ -746,36 +781,36 @@ public IDataItem GetDataItemByKey(string dataItemKey) return null; } - /// - /// Return the first DataItem matching the Type - /// - public IDataItem GetDataItemByType(string type, SearchType searchType = SearchType.Child) - { - if (!string.IsNullOrEmpty(type)) - { - IEnumerable dataItems = null; - switch (searchType) - { - case SearchType.Child: dataItems = DataItems; break; - case SearchType.AnyLevel: dataItems = GetDataItems(); break; - } - - if (!dataItems.IsNullOrEmpty()) - { - return dataItems.FirstOrDefault(o => o.Type == type.ToUnderscoreUpper()); - } - } - - return null; - } - - /// - /// Return the first DataItem matching the Type and SubType - /// - public IDataItem GetDataItemByType(string type, string subType, SearchType searchType = SearchType.Child) - { - if (!string.IsNullOrEmpty(type)) - { + /// + /// Return the first DataItem matching the Type + /// + public IDataItem GetDataItemByType(string type, SearchType searchType = SearchType.Child) + { + if (!string.IsNullOrEmpty(type)) + { + IEnumerable dataItems = null; + switch (searchType) + { + case SearchType.Child: dataItems = DataItems; break; + case SearchType.AnyLevel: dataItems = GetDataItems(); break; + } + + if (!dataItems.IsNullOrEmpty()) + { + return dataItems.FirstOrDefault(o => o.Type == type.ToUnderscoreUpper()); + } + } + + return null; + } + + /// + /// Return the first DataItem matching the Type and SubType + /// + public IDataItem GetDataItemByType(string type, string subType, SearchType searchType = SearchType.Child) + { + if (!string.IsNullOrEmpty(type)) + { IEnumerable dataItems = null; switch (searchType) { @@ -783,14 +818,14 @@ public IDataItem GetDataItemByType(string type, string subType, SearchType searc case SearchType.AnyLevel: dataItems = GetDataItems(); break; } - if (!dataItems.IsNullOrEmpty()) - { - return dataItems.FirstOrDefault(o => o.Type == type.ToUnderscoreUpper() && o.SubType == subType.ToUnderscoreUpper()); - } - } + if (!dataItems.IsNullOrEmpty()) + { + return dataItems.FirstOrDefault(o => o.Type == type.ToUnderscoreUpper() && o.SubType == subType.ToUnderscoreUpper()); + } + } - return null; - } + return null; + } /// /// Return the first DataItem matching the Type @@ -814,47 +849,47 @@ public IDataItem GetDataItem(string subType = null, SearchType search /// Return All DataItems matching the Type /// public IEnumerable GetDataItemsByType(string type, SearchType searchType = SearchType.Child) - { - if (!string.IsNullOrEmpty(type)) - { - IEnumerable dataItems = null; - switch (searchType) - { - case SearchType.Child: dataItems = DataItems; break; - case SearchType.AnyLevel: dataItems = GetDataItems(); break; - } - - if (!dataItems.IsNullOrEmpty()) - { - return dataItems.Where(o => o.Type == type); - } - } - - return null; - } - - /// - /// Return All DataItems matching the Type and SubType - /// - public IEnumerable GetDataItemsByType(string type, string subType, SearchType searchType = SearchType.Child) - { - if (!string.IsNullOrEmpty(type)) - { - IEnumerable dataItems = null; - switch (searchType) - { - case SearchType.Child: dataItems = DataItems; break; - case SearchType.AnyLevel: dataItems = GetDataItems(); break; - } - - if (!dataItems.IsNullOrEmpty()) - { - return dataItems.Where(o => o.Type == type.ToUnderscoreUpper() && o.SubType == subType.ToUnderscoreUpper()); - } - } - - return null; - } + { + if (!string.IsNullOrEmpty(type)) + { + IEnumerable dataItems = null; + switch (searchType) + { + case SearchType.Child: dataItems = DataItems; break; + case SearchType.AnyLevel: dataItems = GetDataItems(); break; + } + + if (!dataItems.IsNullOrEmpty()) + { + return dataItems.Where(o => o.Type == type); + } + } + + return null; + } + + /// + /// Return All DataItems matching the Type and SubType + /// + public IEnumerable GetDataItemsByType(string type, string subType, SearchType searchType = SearchType.Child) + { + if (!string.IsNullOrEmpty(type)) + { + IEnumerable dataItems = null; + switch (searchType) + { + case SearchType.Child: dataItems = DataItems; break; + case SearchType.AnyLevel: dataItems = GetDataItems(); break; + } + + if (!dataItems.IsNullOrEmpty()) + { + return dataItems.Where(o => o.Type == type.ToUnderscoreUpper() && o.SubType == subType.ToUnderscoreUpper()); + } + } + + return null; + } /// /// Return All DataItems matching the Type and SubType @@ -883,11 +918,11 @@ public void AddDataItem(IDataItem dataItem) { if (dataItem != null) { - ((DataItem)dataItem).Container = this; + ((DataItem)dataItem).Container = this; - if (!string.IsNullOrEmpty(Id) && string.IsNullOrEmpty(dataItem.Id)) Component.ResetId(this, dataItem); + if (!string.IsNullOrEmpty(Id) && string.IsNullOrEmpty(dataItem.Id)) Component.ResetId(this, dataItem); - var dataItems = new List(); + var dataItems = new List(); if (!DataItems.IsNullOrEmpty()) { @@ -899,6 +934,13 @@ public void AddDataItem(IDataItem dataItem) } } + /// + /// Creates a DataItem from the given category, type, and optional subtype and adds it to this Device. + /// + /// The category (Sample, Event, or Condition) of the DataItem. + /// The Type that defines what the DataItem represents. + /// An optional SubType that further refines the Type. + /// An optional explicit Id; when omitted an Id is generated from the format pattern. public void AddDataItem(DataItemCategory category, string type, string subType = null, string dataItemId = null) { if (!string.IsNullOrEmpty(type)) @@ -950,21 +992,21 @@ public void AddDataItems(IEnumerable dataItems) { if (!dataItems.IsNullOrEmpty()) { - foreach (var dataItem in dataItems) - { - AddDataItem(dataItem); - } + foreach (var dataItem in dataItems) + { + AddDataItem(dataItem); + } - //var newDataItems = new List(); + //var newDataItems = new List(); - //if (!DataItems.IsNullOrEmpty()) - //{ - // newDataItems.AddRange(DataItems); - //} + //if (!DataItems.IsNullOrEmpty()) + //{ + // newDataItems.AddRange(DataItems); + //} - //newDataItems.AddRange(dataItems); - //DataItems = newDataItems; - } + //newDataItems.AddRange(dataItems); + //DataItems = newDataItems; + } } @@ -993,6 +1035,13 @@ public void RemoveDataItem(string dataItemId) #endregion + /// + /// Produces a typed copy of the specified Device adjusted for the target MTConnect version, + /// recursively processing its child entities and dropping members not valid in that version. + /// + /// The source Device to process. + /// The target MTConnect Standard version; when null, the latest version is assumed. + /// The version-adjusted Device, or null when it is not valid in that version. public static Device Process(IDevice device, Version mtconnectVersion = null) { if (device != null) diff --git a/libraries/MTConnect.NET-Common/Devices/Device.g.cs b/libraries/MTConnect.NET-Common/Devices/Device.g.cs index bb2693711..3d5eb9919 100644 --- a/libraries/MTConnect.NET-Common/Devices/Device.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Device.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices /// public partial class Device : IDevice { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Component composed of a piece of equipment that produces observation about itself."; @@ -17,67 +20,67 @@ public partial class Device : IDevice /// Condensed message digest from a secure one-way hash function. FIPS PUB 180-4 /// public string Hash { get; set; } - + /// /// MTConnect version of the Device Information Model used to configure the information to be published for a piece of equipment in an MTConnect Response Document. /// public System.Version MTConnectVersion { get; set; } - + /// /// Name of an element or a piece of equipment. /// public string Name { get; set; } - + /// /// Universally unique identifier for the element. /// public string Uuid { get; set; } - + /// /// Logical or physical entity that provides a capability. /// public System.Collections.Generic.IEnumerable Components { get; set; } - + /// /// Functional part of a piece of equipment contained within a Component. /// public System.Collections.Generic.IEnumerable Compositions { get; set; } - + /// /// Technical information about an entity describing its physical layout, functional characteristics, and relationships with other entities. /// public MTConnect.Devices.Configurations.IConfiguration Configuration { get; set; } - + /// /// Specifies the CoordinateSystem for this Component and its children. /// public string CoordinateSystemIdRef { get; set; } - + /// /// Descriptive content. /// public MTConnect.Devices.IDescription Description { get; set; } - + /// /// Unique identifier for the Component. /// public string Id { get; set; } - + /// /// Common name associated with Component. /// public string NativeName { get; set; } - + /// /// Pointer to information that is associated with another entity defined elsewhere in the MTConnectDevices entity for a piece of equipment. /// public System.Collections.Generic.IEnumerable References { get; set; } - + /// /// Interval in milliseconds between the completion of the reading of the data associated with the Component until the beginning of the next sampling of that data.This information may be used by client software applications to understand how often information from a Component is expected to be refreshed.The refresh rate for data from all child Component entities will be thesampleInterval provided for the child Component. /// public double SampleInterval { get; set; } - + /// /// SampleInterval. /// diff --git a/libraries/MTConnect.NET-Common/Devices/DeviceDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/DeviceDescriptions.g.cs index a946f0458..396c813e2 100644 --- a/libraries/MTConnect.NET-Common/Devices/DeviceDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/DeviceDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each property of Device as defined by the MTConnect Standard. + /// public static class DeviceDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/DevicesResponseDocument.cs b/libraries/MTConnect.NET-Common/Devices/DevicesResponseDocument.cs index fd680ed28..95e3d11eb 100644 --- a/libraries/MTConnect.NET-Common/Devices/DevicesResponseDocument.cs +++ b/libraries/MTConnect.NET-Common/Devices/DevicesResponseDocument.cs @@ -26,11 +26,21 @@ public class DevicesResponseDocument : IDevicesResponseDocument public virtual IEnumerable Devices { get; set; } + /// + /// The Interfaces declared across the Devices in this document. + /// public IEnumerable Interfaces { get; set; } + /// + /// The MTConnect Standard version this Devices document conforms to. + /// public Version Version { get; set; } + /// + /// Flattens and returns every Component across all Devices in this document. + /// + /// The combined Components from every Device. public IEnumerable GetComponents() { var components = new List(); @@ -47,6 +57,10 @@ public IEnumerable GetComponents() return components; } + /// + /// Flattens and returns every DataItem across all Devices in this document. + /// + /// The combined DataItems from every Device. public IEnumerable GetDataItems() { var dataItems = new List(); diff --git a/libraries/MTConnect.NET-Common/Devices/EntryDefinition.g.cs b/libraries/MTConnect.NET-Common/Devices/EntryDefinition.g.cs index c2756eb19..2b807d0ad 100644 --- a/libraries/MTConnect.NET-Common/Devices/EntryDefinition.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/EntryDefinition.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices /// public class EntryDefinition : IEntryDefinition { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Semantic definition of an Entry."; @@ -17,32 +20,32 @@ public class EntryDefinition : IEntryDefinition /// Semantic definition of a Cell. /// public System.Collections.Generic.IEnumerable CellDefinitions { get; set; } - + /// /// Textual description for EntryDefinition. /// public string Description { get; set; } - + /// /// Unique identification of the Entry in the Definition. key. /// public string Key { get; set; } - + /// /// Key. /// public string KeyType { get; set; } - + /// /// SubType. See DataItem. /// public string SubType { get; set; } - + /// /// Type. See DataItem Types. /// public string Type { get; set; } - + /// /// Units. See Value Properties of DataItem. /// diff --git a/libraries/MTConnect.NET-Common/Devices/EntryDefinitionDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/EntryDefinitionDescriptions.g.cs index 787ff8e06..568cbf5c8 100644 --- a/libraries/MTConnect.NET-Common/Devices/EntryDefinitionDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/EntryDefinitionDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each property of EntryDefinition as defined by the MTConnect Standard. + /// public static class EntryDefinitionDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/Filter.g.cs b/libraries/MTConnect.NET-Common/Devices/Filter.g.cs index 750041ce8..672b82be2 100644 --- a/libraries/MTConnect.NET-Common/Devices/Filter.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Filter.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices /// public class Filter : IFilter { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Provides a means to control when an agent records updated information for a DataItem."; @@ -17,7 +20,7 @@ public class Filter : IFilter /// Type of Filter. /// public MTConnect.Devices.DataItemFilterType Type { get; set; } - + /// /// /// diff --git a/libraries/MTConnect.NET-Common/Devices/FilterDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/FilterDescriptions.g.cs index 4a546d155..65ca8fe5e 100644 --- a/libraries/MTConnect.NET-Common/Devices/FilterDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/FilterDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each property of Filter as defined by the MTConnect Standard. + /// public static class FilterDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/IAbstractDataItemRelationship.cs b/libraries/MTConnect.NET-Common/Devices/IAbstractDataItemRelationship.cs index f5411cc12..47e27789c 100644 --- a/libraries/MTConnect.NET-Common/Devices/IAbstractDataItemRelationship.cs +++ b/libraries/MTConnect.NET-Common/Devices/IAbstractDataItemRelationship.cs @@ -11,6 +11,10 @@ public partial interface IAbstractDataItemRelationship string Hash { get; } + /// + /// Computes a content hash for this relationship that changes whenever its hashed properties change. + /// + /// A SHA-1 hash string identifying the current state of this relationship. string GenerateHash(); } } diff --git a/libraries/MTConnect.NET-Common/Devices/IComponent.cs b/libraries/MTConnect.NET-Common/Devices/IComponent.cs index 56721da3e..be0a47318 100644 --- a/libraries/MTConnect.NET-Common/Devices/IComponent.cs +++ b/libraries/MTConnect.NET-Common/Devices/IComponent.cs @@ -12,6 +12,9 @@ public partial interface IComponent : IContainer /// string Type { get; } + /// + /// Gets whether this Component is an organizer type that only groups other Components. + /// bool IsOrganizer { get; } @@ -82,10 +85,10 @@ public partial interface IComponent : IContainer /// IDataItem GetDataItemByType(string type, SearchType searchType = SearchType.Child); - /// - /// Return the first DataItem matching the Type and SubType - /// - IDataItem GetDataItemByType(string type, string subType, SearchType searchType = SearchType.Child); + /// + /// Return the first DataItem matching the Type and SubType + /// + IDataItem GetDataItemByType(string type, string subType, SearchType searchType = SearchType.Child); /// /// Return the first DataItem matching the Type and SubType @@ -97,15 +100,15 @@ public partial interface IComponent : IContainer /// IEnumerable GetDataItemsByType(string type, SearchType searchType = SearchType.Child); - /// - /// Return All DataItems matching the Type and SubType - /// - IEnumerable GetDataItemsByType(string type, string subType, SearchType searchType = SearchType.Child); + /// + /// Return All DataItems matching the Type and SubType + /// + IEnumerable GetDataItemsByType(string type, string subType, SearchType searchType = SearchType.Child); /// /// Return All DataItems matching the Type and SubType /// IEnumerable GetDataItems(string subType = null, SearchType searchType = SearchType.Child) where TDataItem : IDataItem; - + } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/IContainer.cs b/libraries/MTConnect.NET-Common/Devices/IContainer.cs index 02dcfff29..8f8999d43 100644 --- a/libraries/MTConnect.NET-Common/Devices/IContainer.cs +++ b/libraries/MTConnect.NET-Common/Devices/IContainer.cs @@ -73,10 +73,19 @@ public partial interface IContainer : IMTConnectEntity Version MinimumVersion { get; } - string DataItemIdFormat { get; } + /// + /// The pattern used to generate Ids for DataItems added to this container. + /// + string DataItemIdFormat { get; } - string CompositionIdFormat { get; } + /// + /// The pattern used to generate Ids for child Compositions added to this container. + /// + string CompositionIdFormat { get; } - string ComponentIdFormat { get; } - } + /// + /// The pattern used to generate Ids for child Components added to this container. + /// + string ComponentIdFormat { get; } + } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/IDevice.cs b/libraries/MTConnect.NET-Common/Devices/IDevice.cs index 0a272e275..614a1d8a6 100644 --- a/libraries/MTConnect.NET-Common/Devices/IDevice.cs +++ b/libraries/MTConnect.NET-Common/Devices/IDevice.cs @@ -16,6 +16,10 @@ public partial interface IDevice : IComponent, IContainer string Type { get; } + /// + /// Computes a content hash for this Device that changes whenever its hashed members change. + /// + /// A SHA-1 hash string identifying the current state of this Device. string GenerateHash(); } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/IDevicesDocument.cs b/libraries/MTConnect.NET-Common/Devices/IDevicesDocument.cs index ff76d85c9..3ea7984ad 100644 --- a/libraries/MTConnect.NET-Common/Devices/IDevicesDocument.cs +++ b/libraries/MTConnect.NET-Common/Devices/IDevicesDocument.cs @@ -37,8 +37,16 @@ public interface IDevicesResponseDocument Version Version { get; } + /// + /// Flattens and returns every Component across all Devices in this document. + /// + /// The combined Components from every Device. IEnumerable GetComponents(); + /// + /// Flattens and returns every DataItem across all Devices in this document. + /// + /// The combined DataItems from every Device. IEnumerable GetDataItems(); } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/IOrganizerComponent.cs b/libraries/MTConnect.NET-Common/Devices/IOrganizerComponent.cs index 97636bdb4..040ffdc8a 100644 --- a/libraries/MTConnect.NET-Common/Devices/IOrganizerComponent.cs +++ b/libraries/MTConnect.NET-Common/Devices/IOrganizerComponent.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Marker interface identifying a Component whose only role is to organize and group child Components. + /// public interface IOrganizerComponent { } diff --git a/libraries/MTConnect.NET-Common/Devices/NativeUnitAbbreviations.cs b/libraries/MTConnect.NET-Common/Devices/NativeUnitAbbreviations.cs index f2fcd4bbd..5cbde62eb 100644 --- a/libraries/MTConnect.NET-Common/Devices/NativeUnitAbbreviations.cs +++ b/libraries/MTConnect.NET-Common/Devices/NativeUnitAbbreviations.cs @@ -8,6 +8,11 @@ namespace MTConnect.Devices /// public static class NativeUnitAbbreviations { + /// + /// Returns the short display abbreviation for the given MTConnect NativeUnits value. + /// + /// The MTConnect NativeUnits identifier. + /// The display abbreviation, or null when the NativeUnits value is not recognized. public static string Get(string units) { switch (units) diff --git a/libraries/MTConnect.NET-Common/Devices/NativeUnits.g.cs b/libraries/MTConnect.NET-Common/Devices/NativeUnits.g.cs index f648f6561..ce2ef5c49 100644 --- a/libraries/MTConnect.NET-Common/Devices/NativeUnits.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/NativeUnits.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// NativeUnits string constants as defined by the MTConnect Standard. + /// public static class NativeUnits { /// diff --git a/libraries/MTConnect.NET-Common/Devices/NativeUnitsDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/NativeUnitsDescriptions.g.cs index 5f3e0e4d4..f08957ae8 100644 --- a/libraries/MTConnect.NET-Common/Devices/NativeUnitsDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/NativeUnitsDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each string constant as defined by the MTConnect Standard. + /// public static class NativeUnitsDescriptions { /// @@ -226,6 +229,9 @@ public static class NativeUnitsDescriptions public const string TORR = "Pressure in torr."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(string value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Devices/Organizers.cs b/libraries/MTConnect.NET-Common/Devices/Organizers.cs index aaae3047c..d4e4abf2b 100644 --- a/libraries/MTConnect.NET-Common/Devices/Organizers.cs +++ b/libraries/MTConnect.NET-Common/Devices/Organizers.cs @@ -8,6 +8,10 @@ namespace MTConnect.Devices { + /// + /// Defines the organizer Component types and which child Component types each organizer groups, + /// providing lookups from a child Component type to its organizing Component type. + /// public static class Organizers { private static readonly IEnumerable _components = new List diff --git a/libraries/MTConnect.NET-Common/Devices/References/ComponentReference.g.cs b/libraries/MTConnect.NET-Common/Devices/References/ComponentReference.g.cs index af67b7e43..c6acd15db 100644 --- a/libraries/MTConnect.NET-Common/Devices/References/ComponentReference.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/References/ComponentReference.g.cs @@ -10,8 +10,10 @@ namespace MTConnect.Devices.References /// public class ComponentReference : Reference, IComponentReference { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Reference that is a pointer to all of the information associated with another entity defined for a piece of equipment."; - } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/References/DataItemReference.g.cs b/libraries/MTConnect.NET-Common/Devices/References/DataItemReference.g.cs index 8b3a4a4d7..c5a8eb2cf 100644 --- a/libraries/MTConnect.NET-Common/Devices/References/DataItemReference.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/References/DataItemReference.g.cs @@ -10,8 +10,10 @@ namespace MTConnect.Devices.References /// public class DataItemReference : Reference, IDataItemReference { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Reference that is a pointer to a DataItem associated with another entity defined for a piece of equipment."; - } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/References/Reference.cs b/libraries/MTConnect.NET-Common/Devices/References/Reference.cs index 0b166dcdd..9cb0d8e1c 100644 --- a/libraries/MTConnect.NET-Common/Devices/References/Reference.cs +++ b/libraries/MTConnect.NET-Common/Devices/References/Reference.cs @@ -5,6 +5,9 @@ namespace MTConnect.Devices.References { public abstract partial class Reference { + /// + /// A human-readable description of the concrete Reference type, defaulting to the type's description text. + /// public virtual string TypeDescription => DescriptionText; } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Devices/References/Reference.g.cs b/libraries/MTConnect.NET-Common/Devices/References/Reference.g.cs index ad9a63644..5242e059c 100644 --- a/libraries/MTConnect.NET-Common/Devices/References/Reference.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/References/Reference.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices.References /// public abstract partial class Reference : IReference { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Pointer to information that is associated with another entity defined elsewhere in the MTConnectDevices entity for a piece of equipment."; @@ -17,17 +20,17 @@ public abstract partial class Reference : IReference /// Id that contains the information to be associated with this entity. /// public string DataItemId { get; set; } - + /// /// Pointer to the `id` of an entity that contains the information to be associated with this entity. /// public string IdRef { get; set; } - + /// /// name of an element or a piece of equipment. /// public string Name { get; set; } - + /// /// Id that contains the information to be associated with this entity. /// diff --git a/libraries/MTConnect.NET-Common/Devices/References/ReferenceAttributeDescriptions.cs b/libraries/MTConnect.NET-Common/Devices/References/ReferenceAttributeDescriptions.cs index 7f70db398..f89abdd66 100644 --- a/libraries/MTConnect.NET-Common/Devices/References/ReferenceAttributeDescriptions.cs +++ b/libraries/MTConnect.NET-Common/Devices/References/ReferenceAttributeDescriptions.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.References { + /// + /// Human-readable descriptions of the attributes shared by Reference elements. + /// public static class ReferenceAttributeDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/References/ReferenceDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/References/ReferenceDescriptions.g.cs index 8e9196259..c9922758b 100644 --- a/libraries/MTConnect.NET-Common/Devices/References/ReferenceDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/References/ReferenceDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices.References { + /// + /// Description text for each property of Reference as defined by the MTConnect Standard. + /// public static class ReferenceDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/SearchType.cs b/libraries/MTConnect.NET-Common/Devices/SearchType.cs index 86ec00f75..d435223cf 100644 --- a/libraries/MTConnect.NET-Common/Devices/SearchType.cs +++ b/libraries/MTConnect.NET-Common/Devices/SearchType.cs @@ -3,9 +3,15 @@ namespace MTConnect.Devices { - public enum SearchType - { - Child, - AnyLevel - } + /// + /// Controls how deep a Component or DataItem search descends into the Device hierarchy. + /// + public enum SearchType + { + /// Search only the immediate children of the starting container. + Child, + + /// Search the entire subtree of the starting container at any depth. + AnyLevel + } } diff --git a/libraries/MTConnect.NET-Common/Devices/Source.g.cs b/libraries/MTConnect.NET-Common/Devices/Source.g.cs index be0177fc8..532862167 100644 --- a/libraries/MTConnect.NET-Common/Devices/Source.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Source.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices /// public class Source : ISource { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public const string DescriptionText = "Identifies the Component, DataItem, or Composition from which a measured value originates."; @@ -17,17 +20,17 @@ public class Source : ISource /// Identifier of the Component that represents the physical part of a piece of equipment where the data represented by the DataItem originated. /// public string ComponentId { get; set; } - + /// /// Identifier of the Composition that represents the physical part of a piece of equipment where the data represented by the DataItem originated. /// public string CompositionId { get; set; } - + /// /// Identifier of the DataItem that represents the originally measured value of the data referenced by this DataItem. /// public string DataItemId { get; set; } - + /// /// Identifier of the source entity. /// diff --git a/libraries/MTConnect.NET-Common/Devices/SourceDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/SourceDescriptions.g.cs index a540388ab..6367f48ab 100644 --- a/libraries/MTConnect.NET-Common/Devices/SourceDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/SourceDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each property of Source as defined by the MTConnect Standard. + /// public static class SourceDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/SpecificationRelationship.g.cs b/libraries/MTConnect.NET-Common/Devices/SpecificationRelationship.g.cs index ca9d1ef5b..ff8596539 100644 --- a/libraries/MTConnect.NET-Common/Devices/SpecificationRelationship.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/SpecificationRelationship.g.cs @@ -10,6 +10,9 @@ namespace MTConnect.Devices /// public class SpecificationRelationship : AbstractDataItemRelationship, ISpecificationRelationship { + /// + /// The description of this type as defined by the MTConnect Standard. + /// public new const string DescriptionText = "IdRef."; diff --git a/libraries/MTConnect.NET-Common/Devices/SpecificationRelationshipDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/SpecificationRelationshipDescriptions.g.cs index ba9710e6f..bd16d4b5b 100644 --- a/libraries/MTConnect.NET-Common/Devices/SpecificationRelationshipDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/SpecificationRelationshipDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each property of SpecificationRelationship as defined by the MTConnect Standard. + /// public static class SpecificationRelationshipDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/Devices/SpecificationRelationshipType.g.cs b/libraries/MTConnect.NET-Common/Devices/SpecificationRelationshipType.g.cs index 74f2e98b2..2b6b69c22 100644 --- a/libraries/MTConnect.NET-Common/Devices/SpecificationRelationshipType.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/SpecificationRelationshipType.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// SpecificationRelationshipType controlled vocabulary as defined by the MTConnect Standard. + /// public enum SpecificationRelationshipType { /// diff --git a/libraries/MTConnect.NET-Common/Devices/SpecificationRelationshipTypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/SpecificationRelationshipTypeDescriptions.g.cs index 98d0a20c3..068830ddb 100644 --- a/libraries/MTConnect.NET-Common/Devices/SpecificationRelationshipTypeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/SpecificationRelationshipTypeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class SpecificationRelationshipTypeDescriptions { /// @@ -11,6 +14,9 @@ public static class SpecificationRelationshipTypeDescriptions public const string LIMIT = "Referenced Specification provides process limits."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(SpecificationRelationshipType value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Devices/UnitAbbreviations.cs b/libraries/MTConnect.NET-Common/Devices/UnitAbbreviations.cs index 491cd970e..46e30134c 100644 --- a/libraries/MTConnect.NET-Common/Devices/UnitAbbreviations.cs +++ b/libraries/MTConnect.NET-Common/Devices/UnitAbbreviations.cs @@ -8,6 +8,11 @@ namespace MTConnect.Devices /// public static class UnitAbbreviations { + /// + /// Returns the short display abbreviation for the given MTConnect Units value. + /// + /// The MTConnect Units identifier. + /// The display abbreviation, or null when the Units value is not recognized. public static string Get(string units) { switch (units) diff --git a/libraries/MTConnect.NET-Common/Devices/Units.g.cs b/libraries/MTConnect.NET-Common/Devices/Units.g.cs index ab5b6facd..77f70e100 100644 --- a/libraries/MTConnect.NET-Common/Devices/Units.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/Units.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Units string constants as defined by the MTConnect Standard. + /// public static partial class Units { /// diff --git a/libraries/MTConnect.NET-Common/Devices/UnitsDescriptions.g.cs b/libraries/MTConnect.NET-Common/Devices/UnitsDescriptions.g.cs index 2c15a435c..ed0101c84 100644 --- a/libraries/MTConnect.NET-Common/Devices/UnitsDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Devices/UnitsDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Devices { + /// + /// Description text for each string constant as defined by the MTConnect Standard. + /// public static class UnitsDescriptions { /// @@ -271,6 +274,9 @@ public static class UnitsDescriptions public const string WATT_SECOND = "Electrical energy in watt-second"; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(string value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Devices/ValidationResult.cs b/libraries/MTConnect.NET-Common/Devices/ValidationResult.cs index 888048c7c..11152c46d 100644 --- a/libraries/MTConnect.NET-Common/Devices/ValidationResult.cs +++ b/libraries/MTConnect.NET-Common/Devices/ValidationResult.cs @@ -3,13 +3,27 @@ namespace MTConnect.Devices.DataItems { + /// + /// The outcome of validating a DataItem value or Observation, carrying a pass/fail flag and an optional message. + /// public struct ValidationResult { + /// + /// Indicates whether validation succeeded. + /// public bool IsValid { get; set; } + /// + /// An optional message explaining the validation outcome, typically the reason for a failure. + /// public string Message { get; set; } + /// + /// Initializes a new validation result with the given outcome and optional message. + /// + /// Whether validation succeeded. + /// An optional explanatory message. public ValidationResult(bool isValid, string message = null) { IsValid = isValid; diff --git a/libraries/MTConnect.NET-Common/Errors/Error.cs b/libraries/MTConnect.NET-Common/Errors/Error.cs index bca719db3..41147b735 100644 --- a/libraries/MTConnect.NET-Common/Errors/Error.cs +++ b/libraries/MTConnect.NET-Common/Errors/Error.cs @@ -23,8 +23,16 @@ public class Error : IError public string Value { get; set; } + /// + /// Initializes an empty Error, leaving the code and description to be set by a deserializer or caller. + /// public Error() { } + /// + /// Initializes an Error with the given code and optional descriptive text. + /// + /// The error category encountered by the Agent. + /// An optional textual description of the error. public Error(ErrorCode errorCode, string value = null) { ErrorCode = errorCode; diff --git a/libraries/MTConnect.NET-Common/Errors/ErrorText.cs b/libraries/MTConnect.NET-Common/Errors/ErrorText.cs index 905d80e4b..feb3cf5bf 100644 --- a/libraries/MTConnect.NET-Common/Errors/ErrorText.cs +++ b/libraries/MTConnect.NET-Common/Errors/ErrorText.cs @@ -3,19 +3,59 @@ namespace MTConnect.Errors { + /// + /// Canonical, spec-derived message text used when an Agent rejects a sample/current request because a sequence parameter is malformed or outside the buffer range. + /// public class ErrorText { + /// + /// Message reported when the from parameter is negative or non-numeric, making the request invalid. + /// public const string InvalidRequestNegativeFrom = "If the value provided for the from parameter is a negative number or is not a, the Request MUST be determined to be invalid."; + + /// + /// Message reported when the to parameter is negative or non-numeric, making the request invalid. + /// public const string InvalidRequestNegativeTo = "If the value provided for the to parameter is a negative number or is not a, the Request MUST be determined to be invalid."; + + /// + /// Message reported when the at parameter is negative or non-numeric, making the request invalid. + /// public const string InvalidRequestNegativeAt = "If the value provided for the at parameter is a negative number or is not a, the Request MUST be determined to be invalid."; + + /// + /// Message reported (with a 400 status and INVALID_REQUEST code) when to is given together with a negative count. + /// public const string InvalidRequestNegativeCount = "If the to parameter is given and the count parameter is less than zero, the Agent MUST return a 400 HTTP Status Code and MUST publish an MTConnectErrors Response Document with an INVALID_REQUEST errorCode."; + /// + /// Message reported (with a 400 status and INVALID_REQUEST code) when the to parameter is less than the from parameter. + /// public const string InvalidRequestToLessThanFrom = "If the to parameter is less than the from parameter, the Agent MUST return a 400 HTTP Status Code and MUST publish an MTConnectErrors Response Document with an INVALID_REQUEST errorCode."; + + /// + /// Message reported when the at parameter is combined with the interval parameter, a contradictory pairing that would repeatedly return identical data. + /// public const string InvalidRequestAtIntervalConjunction = "The at parameter MUST NOT be used in conjunction with the interval parameter since this would cause an Agent to repeatedly return the same data."; + /// + /// Message reported (with a 404 status and OUT_OF_RANGE code) when from falls outside the firstSequence..lastSequence window. + /// public const string OutOfRangeFrom = "If the from parameter is less than the firstSequence or greater than lastSequence, the Agent MUST return a 404 HTTP Status Code and MUST publish an MTConnectErrors Response Document with an OUT_OF_RANGE errorCode."; + + /// + /// Message reported (with a 404 status and OUT_OF_RANGE code) when to falls outside the firstSequence..lastSequence window. + /// public const string OutOfRangeTo = "If the to parameter is less than the firstSequence or greater than lastSequence, the Agent MUST return a 404 HTTP Status Code and MUST publish an MTConnectErrors Response Document with an OUT_OF_RANGE errorCode."; + + /// + /// Message reported when the at parameter falls outside the firstSequence..lastSequence window, making the request invalid. + /// public const string OutOfRangeAt = "If the value provided for the at parameter is either lower than the value of firstSequence or greater than the value of lastSequence, the Request MUST be determined to be invalid."; + + /// + /// Message reported (with a 404 status and OUT_OF_RANGE code) when the magnitude of count exceeds the buffer size or is zero. + /// public const string OutOfRangeCount = "If the absolute value of count is greater than the size of the buffer or equal to zero(0), the Agent MUST return a 404 HTTP Status Code and MUST publish an MTConnectErrors Response Document with an OUT_OF_RANGE errorCode."; } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-Common/Extensions/AssemblyExtensions.cs b/libraries/MTConnect.NET-Common/Extensions/AssemblyExtensions.cs index eb9b4dd3f..8fcfcc30f 100644 --- a/libraries/MTConnect.NET-Common/Extensions/AssemblyExtensions.cs +++ b/libraries/MTConnect.NET-Common/Extensions/AssemblyExtensions.cs @@ -8,6 +8,9 @@ namespace MTConnect.Extensions { + /// + /// Reflection helpers for querying the types contained in an assembly while tolerating partial type-load failures. + /// public static class AssemblyExtensions { /// diff --git a/libraries/MTConnect.NET-Common/Extensions/ListExtensions.cs b/libraries/MTConnect.NET-Common/Extensions/ListExtensions.cs index 4d77be564..be2e61926 100644 --- a/libraries/MTConnect.NET-Common/Extensions/ListExtensions.cs +++ b/libraries/MTConnect.NET-Common/Extensions/ListExtensions.cs @@ -7,6 +7,9 @@ namespace MTConnect { + /// + /// Convenience extensions for working with enumerable sequences, optimizing for the common collection and array cases. + /// public static class ListExtensions { /// diff --git a/libraries/MTConnect.NET-Common/Extensions/ObjectExtensions.cs b/libraries/MTConnect.NET-Common/Extensions/ObjectExtensions.cs index 0a056d282..16dd6d33d 100644 --- a/libraries/MTConnect.NET-Common/Extensions/ObjectExtensions.cs +++ b/libraries/MTConnect.NET-Common/Extensions/ObjectExtensions.cs @@ -8,19 +8,34 @@ namespace MTConnect { + /// + /// Loosely-typed conversion and byte-buffer helpers used when coercing observation values and message payloads whose runtime type is not known in advance. + /// public static class ObjectExtensions { + /// + /// Returns true when the value's string form parses as a double, treating null as non-numeric. + /// + /// The value to test. public static bool IsNumeric(this object value) { if (value != null) return double.TryParse(value.ToString(), out _); return false; } + /// + /// Returns true when the integer is odd. + /// + /// The integer to test. public static bool IsOdd(this int value) { return value % 2 != 0; } + /// + /// Coerces the value to a bool, passing through an actual bool and otherwise parsing its string form; returns false when null, empty, or unparseable. + /// + /// The value to convert. public static bool ToBoolean(this object o) { if (o is bool) return (bool)o; @@ -30,6 +45,10 @@ public static bool ToBoolean(this object o) else return false; } + /// + /// Coerces the value to an int, passing through an actual int and otherwise parsing its string form; returns -1 when null, empty, or unparseable. + /// + /// The value to convert. public static int ToInt(this object o) { if (o is int) return (int)o; @@ -39,6 +58,10 @@ public static int ToInt(this object o) else return -1; } + /// + /// Coerces the value to a uint, passing through an actual uint and otherwise parsing its string form; returns 0 when null, empty, or unparseable. + /// + /// The value to convert. public static uint ToUInt(this object o) { if (o is uint) return (uint)o; @@ -48,6 +71,10 @@ public static uint ToUInt(this object o) else return 0; } + /// + /// Coerces the value to a long, passing through an actual long and otherwise parsing its string form; returns -1 when null, empty, or unparseable. + /// + /// The value to convert. public static long ToLong(this object o) { if (o is long) return (long)o; @@ -57,6 +84,10 @@ public static long ToLong(this object o) else return -1; } + /// + /// Coerces the value to a ulong, passing through an actual ulong and otherwise parsing its string form; returns 0 when null, empty, or unparseable. + /// + /// The value to convert. public static ulong ToULong(this object o) { if (o is ulong) return (ulong)o; @@ -66,6 +97,10 @@ public static ulong ToULong(this object o) else return 0; } + /// + /// Coerces the value to a double, passing through an actual double and otherwise parsing its string form; returns -1 when null, empty, or unparseable. + /// + /// The value to convert. public static double ToDouble(this object o) { if (o is double) return (double)o; @@ -75,6 +110,11 @@ public static double ToDouble(this object o) else return -1; } + /// + /// Parses the value's string form to a double rounded to the given number of decimal places; returns -1 when null, empty, or unparseable. + /// + /// The value to convert. + /// The number of fractional digits to round the result to. public static double ToDouble(this object o, int decimalPlaces = int.MaxValue) { var s = o?.ToString(); @@ -85,6 +125,10 @@ public static double ToDouble(this object o, int decimalPlaces = int.MaxValue) else return -1; } + /// + /// Counts the digits in the integer part of the number by repeated division by ten (fractional digits are ignored; values below 1 yield 0). + /// + /// The number whose integer-part digit count is wanted. public static int GetDigitCount(this double num) { int digits = 0; @@ -96,6 +140,10 @@ public static int GetDigitCount(this double num) return digits; } + /// + /// Counts the digits after the decimal point in the number's default string representation; returns 0 when there is no decimal point. + /// + /// The number whose fractional digit count is wanted. public static int GetDigitCountAfterDecimal(this double value) { bool start = false; @@ -115,6 +163,11 @@ public static int GetDigitCountAfterDecimal(this double value) return count; } + /// + /// Returns the digit positioned characters to the left of the decimal point in the number's string form; returns 0 when that position falls outside the string. + /// + /// The number to inspect. + /// The offset to the left of the decimal point (1 selects the units digit). public static int GetDigitBeforeDecimal(this double value, int index) { var s = value.ToString(); @@ -128,6 +181,11 @@ public static int GetDigitBeforeDecimal(this double value, int index) return 0; } + /// + /// Returns the digit positioned characters to the right of the decimal point in the number's string form; returns 0 when that position falls outside the string. + /// + /// The number to inspect. + /// The offset to the right of the decimal point (1 selects the first fractional digit). public static int GetDigitAfterDecimal(this double value, int index) { var s = value.ToString(); @@ -141,6 +199,12 @@ public static int GetDigitAfterDecimal(this double value, int index) return 0; } + /// + /// Builds a per-property "name:value" string array over the object's public scalar properties (value types, string, and DateTime), used as the basis for content hashing. + /// The "Hash" property and any names in are excluded; returns null when the object is null or has no properties. + /// + /// The object whose properties contribute to the hash. + /// Property names to exclude so they do not affect the hash. public static string[] GetHashPropertyList(object obj, IEnumerable ignorePropertyNames = null) { if (obj != null) @@ -176,6 +240,11 @@ public static string[] GetHashPropertyList(object obj, IEnumerable ignor return null; } + /// + /// Joins the object's hashable "name:value" pairs (see ) into a single pipe-delimited string suitable for hashing. + /// + /// The object whose properties contribute to the hash. + /// Property names to exclude so they do not affect the hash. public static string GetHashPropertyString(object obj, IEnumerable ignorePropertyNames = null) { var s = ""; @@ -192,6 +261,11 @@ public static string GetHashPropertyString(object obj, IEnumerable ignor return s.TrimEnd('|'); } + /// + /// Performs an element-by-element equality comparison of two byte arrays, treating reference-equal (including both null) as equal and any null/length mismatch as unequal. + /// + /// The first byte array. + /// The second byte array. public static bool ByteArraysEqual(byte[] b1, byte[] b2) { if (b1 == b2) return true; @@ -204,6 +278,11 @@ public static bool ByteArraysEqual(byte[] b1, byte[] b2) return true; } + /// + /// Returns a copy of with any leading and trailing bytes that appear in removed; returns null when either argument is null or empty. + /// + /// The buffer to trim. + /// The set of byte values to strip from both ends. public static byte[] TrimBytes(byte[] inputBytes, byte[] trimBytes) { if (inputBytes != null && inputBytes.Length > 0 && trimBytes != null && trimBytes.Length > 0) @@ -221,6 +300,12 @@ public static byte[] TrimBytes(byte[] inputBytes, byte[] trimBytes) return null; } + /// + /// Shifts in place to drop any leading bytes that appear in and returns the number of bytes removed. + /// The array length is left unchanged; only the returned count delimits the meaningful prefix. + /// + /// The buffer to trim in place. + /// The set of byte values to strip from the start. public static int TrimStartBytes(ref byte[] inputBytes, byte[] trimBytes) { if (inputBytes != null && inputBytes.Length > 0 && trimBytes != null && trimBytes.Length > 0) @@ -256,6 +341,11 @@ public static int TrimStartBytes(ref byte[] inputBytes, byte[] trimBytes) return 0; } + /// + /// Returns a new, length-adjusted copy of with leading bytes that appear in removed; returns null when either argument is null or empty. + /// + /// The buffer to trim. + /// The set of byte values to strip from the start. public static byte[] TrimStartBytes(byte[] inputBytes, byte[] trimBytes) { if (inputBytes != null && inputBytes.Length > 0 && trimBytes != null && trimBytes.Length > 0) @@ -292,6 +382,11 @@ public static byte[] TrimStartBytes(byte[] inputBytes, byte[] trimBytes) return null; } + /// + /// Returns a new, length-adjusted copy of with trailing bytes that appear in removed; returns null when either argument is null or empty. + /// + /// The buffer to trim. + /// The set of byte values to strip from the end. public static byte[] TrimEndBytes(byte[] inputBytes, byte[] trimBytes) { if (inputBytes != null && inputBytes.Length > 0 && trimBytes != null && trimBytes.Length > 0) diff --git a/libraries/MTConnect.NET-Common/Extensions/StringFunctions.cs b/libraries/MTConnect.NET-Common/Extensions/StringFunctions.cs index 6740b375d..af7933ea1 100644 --- a/libraries/MTConnect.NET-Common/Extensions/StringFunctions.cs +++ b/libraries/MTConnect.NET-Common/Extensions/StringFunctions.cs @@ -10,6 +10,10 @@ namespace MTConnect { + /// + /// String casing, word-splitting, and hashing helpers used to normalize identifiers between document formats and to derive stable content hashes. + /// The MD5/SHA1/Random instances are cached per thread to avoid repeated allocation under concurrent serialization. + /// public static class StringFunctions { private static readonly Encoding _utf8 = Encoding.UTF8; @@ -60,6 +64,10 @@ private static Random Random } } + /// + /// Splits the string into words (see ) and concatenates them with each word's first character uppercased and no separator, producing PascalCase; returns null when the input is null or empty. + /// + /// The string to convert. public static string ToPascalCase(this string s) { if (!string.IsNullOrEmpty(s)) @@ -79,6 +87,10 @@ public static string ToPascalCase(this string s) return null; } + /// + /// Splits the string into words and concatenates them with each word's first character uppercased and no separator; behaves identically to . Returns null when the input is null or empty. + /// + /// The string to convert. public static string ToTitleCase(this string s) { if (!string.IsNullOrEmpty(s)) @@ -98,6 +110,10 @@ public static string ToTitleCase(this string s) return null; } + /// + /// Splits the string into words and concatenates them with the first word lowercased and every subsequent word's first character uppercased, producing camelCase; returns null when the input is null or empty. + /// + /// The string to convert. public static string ToCamelCase(this string s) { if (!string.IsNullOrEmpty(s)) @@ -118,6 +134,10 @@ public static string ToCamelCase(this string s) return null; } + /// + /// Splits the string into its constituent words, preferring spaces, then underscores, then uppercase boundaries as the delimiter; returns a single-element array when none apply. + /// + /// The string to split. public static string[] SplitOnWord(this string s) { if (!string.IsNullOrEmpty(s)) @@ -146,6 +166,10 @@ public static string[] SplitOnWord(this string s) return new string[] { s }; } + /// + /// Splits the string at each uppercase letter (except the first character) into separate words; returns the string unsplit when it is entirely uppercase, or null when null or empty. + /// + /// The string to split on uppercase boundaries. public static string[] SplitOnUppercase(this string s) { if (!string.IsNullOrEmpty(s)) @@ -175,6 +199,10 @@ public static string[] SplitOnUppercase(this string s) return null; } + /// + /// Returns the string with its first character uppercased and the remainder lowercased; returns null for null input and the fully-uppercased single character for one-character input. + /// + /// The string to recapitalize. public static string UppercaseFirstCharacter(this string s) { if (s == null) return null; @@ -193,6 +221,10 @@ public static string UppercaseFirstCharacter(this string s) return s.ToUpper(); } + /// + /// Returns the string with only its first character lowercased and the remainder unchanged; returns null for null input and the fully-lowercased single character for one-character input. + /// + /// The string to recapitalize. public static string LowercaseFirstCharacter(this string s) { if (s == null) return null; @@ -212,6 +244,11 @@ public static string LowercaseFirstCharacter(this string s) } + /// + /// Converts the string to lowercase snake_case, splitting on spaces or (when is true) on uppercase boundaries; an all-uppercase input is simply lowercased, and null is returned when no split applies or the input is null or empty. + /// + /// The string to convert. + /// When true and the string has no spaces, word boundaries are inferred from uppercase letters. public static string ToUnderscore(this string s, bool splitOnUppercase = true) { if (!string.IsNullOrEmpty(s)) @@ -244,6 +281,11 @@ public static string ToUnderscore(this string s, bool splitOnUppercase = true) return null; } + /// + /// Converts the string to uppercase SNAKE_CASE, splitting on spaces or (when is true) on uppercase boundaries; an all-uppercase input is simply uppercased, and null is returned when no split applies or the input is null or empty. + /// + /// The string to convert. + /// When true and the string has no spaces, word boundaries are inferred from uppercase letters. public static string ToUnderscoreUpper(this string s, bool splitOnUppercase = true) { if (!string.IsNullOrEmpty(s)) @@ -276,6 +318,10 @@ public static string ToUnderscoreUpper(this string s, bool splitOnUppercase = tr return null; } + /// + /// Generates a random string of the given length drawn from uppercase letters and digits, using the per-thread cached Random (not cryptographically secure). + /// + /// The number of characters to generate. public static string RandomString(int length) { const string chars = "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"; @@ -283,6 +329,10 @@ public static string RandomString(int length) .Select(s => s[Random.Next(s.Length)]).ToArray()); } + /// + /// Parses the string as a DateTime, returning DateTime.MinValue when it cannot be parsed. + /// + /// The string to parse. public static DateTime ToDateTime(this string s) { if (DateTime.TryParse(s, out var dateTime)) @@ -293,6 +343,10 @@ public static DateTime ToDateTime(this string s) return DateTime.MinValue; } + /// + /// Computes the MD5 digest of the UTF-8 bytes of the string and returns it as a lowercase hex string; returns null if hashing throws. + /// + /// The string to hash. public static string ToMD5Hash(this string s) { try @@ -305,6 +359,10 @@ public static string ToMD5Hash(this string s) return null; } + /// + /// Computes the MD5 digest of the byte buffer and returns it as a lowercase hex string; returns null when the buffer is null or hashing throws. + /// + /// The buffer to hash. public static string ToMD5Hash(this byte[] bytes) { if (bytes != null) @@ -320,6 +378,10 @@ public static string ToMD5Hash(this byte[] bytes) return null; } + /// + /// Formats an already-computed hash digest as a lowercase hex string without re-hashing; returns null when the buffer is null or formatting throws. + /// + /// The raw digest bytes to render as hex. public static string ToMD5HashString(this byte[] hashBytes) { if (hashBytes != null) @@ -334,6 +396,10 @@ public static string ToMD5HashString(this byte[] hashBytes) return null; } + /// + /// Computes the raw MD5 digest of the UTF-8 bytes of the string; returns null if hashing throws. + /// + /// The string to hash. public static byte[] ToMD5HashBytes(this string s) { try @@ -345,6 +411,10 @@ public static byte[] ToMD5HashBytes(this string s) return null; } + /// + /// Computes the raw MD5 digest of the byte buffer; returns null when the buffer is null or hashing throws. + /// + /// The buffer to hash. public static byte[] ToMD5HashBytes(this byte[] bytes) { if (bytes != null) @@ -358,6 +428,10 @@ public static byte[] ToMD5HashBytes(this byte[] bytes) return null; } + /// + /// Computes an order-sensitive rolling MD5 over the lines: each line is hashed, concatenated after the running hash, and re-hashed, so the result depends on both the content and sequence of lines. Returns null for a null or empty array. + /// + /// The ordered lines to fold into a single hash. public static string ToMD5Hash(string[] lines) { if (lines != null && lines.Length > 0) @@ -378,6 +452,10 @@ public static string ToMD5Hash(string[] lines) return null; } + /// + /// Folds an array of digest buffers into a single MD5 digest by repeatedly concatenating the running result with the next buffer and re-hashing; a single-element array is returned unchanged, and null/empty input returns null. + /// + /// The ordered digest buffers to combine. public static byte[] ToMD5HashBytes(byte[][] hashBytes) { if (hashBytes != null && hashBytes.Length > 0) @@ -406,6 +484,10 @@ public static byte[] ToMD5HashBytes(byte[][] hashBytes) } + /// + /// Computes the SHA-1 digest of the UTF-8 bytes of the string and returns it as a lowercase hex string; returns null if hashing throws. + /// + /// The string to hash. public static string ToSHA1Hash(this string s) { try @@ -418,6 +500,10 @@ public static string ToSHA1Hash(this string s) return null; } + /// + /// Computes the SHA-1 digest of the byte buffer and returns it as a lowercase hex string; returns null when the buffer is null or hashing throws. + /// + /// The buffer to hash. public static string ToSHA1Hash(this byte[] bytes) { if (bytes != null) @@ -433,6 +519,10 @@ public static string ToSHA1Hash(this byte[] bytes) return null; } + /// + /// Formats an already-computed SHA-1 digest as a lowercase hex string without re-hashing; returns null when the buffer is null or formatting throws. + /// + /// The raw digest bytes to render as hex. public static string ToSHA1HashString(this byte[] hashBytes) { if (hashBytes != null) @@ -447,6 +537,10 @@ public static string ToSHA1HashString(this byte[] hashBytes) return null; } + /// + /// Computes the raw SHA-1 digest of the UTF-8 bytes of the string; returns null if hashing throws. + /// + /// The string to hash. public static byte[] ToSHA1HashBytes(this string s) { try @@ -458,6 +552,10 @@ public static byte[] ToSHA1HashBytes(this string s) return null; } + /// + /// Computes the raw SHA-1 digest of the byte buffer; returns null when the buffer is null or hashing throws. + /// + /// The buffer to hash. public static byte[] ToSHA1HashBytes(this byte[] bytes) { if (bytes != null) @@ -471,6 +569,10 @@ public static byte[] ToSHA1HashBytes(this byte[] bytes) return null; } + /// + /// Computes an order-sensitive rolling SHA-1 over the lines: each line is hashed, concatenated after the running hash, and re-hashed, so the result depends on both content and sequence. Returns null for a null or empty array. + /// + /// The ordered lines to fold into a single hash. public static string ToSHA1Hash(string[] lines) { if (lines != null && lines.Length > 0) @@ -491,6 +593,11 @@ public static string ToSHA1Hash(string[] lines) return null; } + /// + /// Iterates the digest buffers, concatenating the running result with each next buffer and re-hashing it with SHA-1; for a single-element array the element is returned unchanged, and null/empty input returns null. + /// Note: for multi-element input the value returned is the last source buffer rather than the accumulated hash. + /// + /// The ordered digest buffers to combine. public static byte[] ToSHA1HashBytes(byte[][] hashBytes) { if (hashBytes != null && hashBytes.Length > 0) @@ -519,6 +626,10 @@ public static byte[] ToSHA1HashBytes(byte[][] hashBytes) } + /// + /// Formats a byte count as a human-readable size using binary (1024) steps and one decimal place, ranging from "B" to "EB" and preserving the sign of a negative count. + /// + /// The number of bytes to format. public static string ToFileSize(this long byteCount) { string[] suf = { "B", "KB", "MB", "GB", "TB", "PB", "EB" }; //Longs run out around EB @@ -530,6 +641,10 @@ public static string ToFileSize(this long byteCount) return (Math.Sign(byteCount) * num).ToString() + suf[place]; } + /// + /// Formats a decimal byte count as a human-readable size by truncating to a long and delegating to . + /// + /// The number of bytes to format. public static string ToFileSize(this decimal byteCount) { var x = (long)byteCount; @@ -537,6 +652,10 @@ public static string ToFileSize(this decimal byteCount) } + /// + /// Heuristically determines whether the string contains HTML by testing for a matched open/close tag pair; returns false for null or empty input. + /// + /// The string to inspect. public static bool IsHtml(this string s) { if (!string.IsNullOrEmpty(s)) @@ -548,6 +667,11 @@ public static bool IsHtml(this string s) return false; } + /// + /// Parses the string into the enum value of type case-insensitively, returning default(T) when is not an enum or the value does not match a member. + /// + /// The target enum type. + /// The string to parse into an enum member. public static T ConvertEnum(this string value) where T : struct { if (value != null && typeof(T).IsEnum) @@ -561,6 +685,10 @@ public static T ConvertEnum(this string value) where T : struct return default; } + /// + /// Derives a 64-bit hash from the string by MD5-hashing its default-encoded bytes and XOR-folding the digest into eight-byte words, yielding a compact non-cryptographic key. + /// + /// The string to reduce to a 64-bit hash. public static ulong GetUInt64Hash(this string text) { using (var md5 = MD5.Create()) diff --git a/libraries/MTConnect.NET-Common/Extensions/TimeSpanExtensions.cs b/libraries/MTConnect.NET-Common/Extensions/TimeSpanExtensions.cs index 6312ec2ab..570fa4827 100644 --- a/libraries/MTConnect.NET-Common/Extensions/TimeSpanExtensions.cs +++ b/libraries/MTConnect.NET-Common/Extensions/TimeSpanExtensions.cs @@ -5,8 +5,15 @@ namespace MTConnect { + /// + /// Extensions for measuring elapsed time at sub-millisecond resolution from a high-frequency Stopwatch. + /// public static class TimeSpanExtensions { + /// + /// Returns the elapsed time of the stopwatch in fractional milliseconds, computed from its tick count and frequency for resolution finer than ElapsedMilliseconds; returns -1 when the stopwatch is null. + /// + /// The stopwatch to read; may be null. public static double GetElapsedMilliseconds(this Stopwatch stpw) { if (stpw != null) diff --git a/libraries/MTConnect.NET-Common/Formatters/EntityFormatter.cs b/libraries/MTConnect.NET-Common/Formatters/EntityFormatter.cs index b73a1dcca..3e364dc07 100644 --- a/libraries/MTConnect.NET-Common/Formatters/EntityFormatter.cs +++ b/libraries/MTConnect.NET-Common/Formatters/EntityFormatter.cs @@ -14,12 +14,19 @@ namespace MTConnect.Formatters { + /// + /// Static facade that discovers and caches the implementations available across loaded assemblies and dispatches entity serialization/deserialization to the one matching a requested document format, timing each operation. + /// public static class EntityFormatter { private static readonly ConcurrentDictionary _formatters = new ConcurrentDictionary(); private static bool _firstRead = true; + /// + /// Returns the MIME content type produced by the entity formatter registered for the given format, or null when no such formatter exists. + /// + /// The identifier of the document format. public static string GetContentType(string documentFormatterId) { // Get the Formatter with the specified ID @@ -33,6 +40,12 @@ public static string GetContentType(string documentFormatterId) } + /// + /// Serializes a device using the entity formatter for the given format, returning an error result when no matching formatter exists. The result's response duration is set to the elapsed time. + /// + /// The identifier of the document format. + /// The device to serialize. + /// Optional format-specific key/value options. public static FormatWriteResult Format(string documentFormatterId, IDevice device, IEnumerable> options = null) { var stpw = Stopwatch.StartNew(); @@ -53,6 +66,12 @@ public static FormatWriteResult Format(string documentFormatterId, IDevice devic return result; } + /// + /// Serializes a single observation using the entity formatter for the given format, returning an error result when no matching formatter exists. The result's response duration is set to the elapsed time. + /// + /// The identifier of the document format. + /// The observation to serialize. + /// Optional format-specific key/value options. public static FormatWriteResult Format(string documentFormatterId, IObservation observation, IEnumerable> options = null) { var stpw = Stopwatch.StartNew(); @@ -73,6 +92,12 @@ public static FormatWriteResult Format(string documentFormatterId, IObservation return result; } + /// + /// Serializes a batch of observations using the entity formatter for the given format, returning an error result when no matching formatter exists. The result's response duration is set to the elapsed time. + /// + /// The identifier of the document format. + /// The observations to serialize. + /// Optional format-specific key/value options. public static FormatWriteResult Format(string documentFormatterId, IEnumerable observations, IEnumerable> options = null) { var stpw = Stopwatch.StartNew(); @@ -93,6 +118,12 @@ public static FormatWriteResult Format(string documentFormatterId, IEnumerable + /// Serializes an asset using the entity formatter for the given format, returning an error result when no matching formatter exists. The result's response duration is set to the elapsed time. + /// + /// The identifier of the document format. + /// The asset to serialize. + /// Optional format-specific key/value options. public static FormatWriteResult Format(string documentFormatterId, IAsset asset, IEnumerable> options = null) { var stpw = Stopwatch.StartNew(); @@ -114,6 +145,11 @@ public static FormatWriteResult Format(string documentFormatterId, IAsset asset, } + /// + /// Deserializes a device from the given content stream using the entity formatter for the given format; returns an error result when no matching formatter exists. + /// + /// The identifier of the document format. + /// The serialized device content. public static FormatReadResult CreateDevice(string documentFormatterId, Stream content) { // Get the Formatter with the specified ID @@ -127,6 +163,11 @@ public static FormatReadResult CreateDevice(string documentFormatterId, return FormatReadResult.Error(null, $"Entity Formatter Not found for \"{documentFormatterId}\""); } + /// + /// Deserializes a component from the given content stream using the entity formatter for the given format; returns an error result when no matching formatter exists. + /// + /// The identifier of the document format. + /// The serialized component content. public static FormatReadResult CreateComponent(string documentFormatterId, Stream content) { // Get the Formatter with the specified ID @@ -140,6 +181,11 @@ public static FormatReadResult CreateComponent(string documentFormat return FormatReadResult.Error(null, $"Entity Formatter Not found for \"{documentFormatterId}\""); } + /// + /// Deserializes a composition from the given content stream using the entity formatter for the given format; returns an error result when no matching formatter exists. + /// + /// The identifier of the document format. + /// The serialized composition content. public static FormatReadResult CreateComposition(string documentFormatterId, Stream content) { // Get the Formatter with the specified ID @@ -153,6 +199,11 @@ public static FormatReadResult CreateComposition(string documentFo return FormatReadResult.Error(null, $"Entity Formatter Not found for \"{documentFormatterId}\""); } + /// + /// Deserializes a data item from the given content stream using the entity formatter for the given format; returns an error result when no matching formatter exists. + /// + /// The identifier of the document format. + /// The serialized data item content. public static FormatReadResult CreateDataItem(string documentFormatterId, Stream content) { // Get the Formatter with the specified ID @@ -166,6 +217,12 @@ public static FormatReadResult CreateDataItem(string documentFormatte return FormatReadResult.Error(null, $"Entity Formatter Not found for \"{documentFormatterId}\""); } + /// + /// Deserializes an asset of the given type from the content stream using the entity formatter for the given format; returns an error result when no matching formatter exists. + /// + /// The identifier of the document format. + /// The MTConnect asset type to deserialize as. + /// The serialized asset content. public static FormatReadResult CreateAsset(string documentFormatterId, string assetType, Stream content) { // Get the Formatter with the specified ID diff --git a/libraries/MTConnect.NET-Common/Formatters/FormatReadResult.cs b/libraries/MTConnect.NET-Common/Formatters/FormatReadResult.cs index 7ecb8a4db..daad78de0 100644 --- a/libraries/MTConnect.NET-Common/Formatters/FormatReadResult.cs +++ b/libraries/MTConnect.NET-Common/Formatters/FormatReadResult.cs @@ -6,23 +6,56 @@ namespace MTConnect.Formatters { + /// + /// The outcome of deserializing a document into an entity of type , carrying the parsed content, a success flag, and any diagnostic messages. + /// + /// The deserialized entity type. public struct FormatReadResult : IFormatReadResult { + /// + /// The deserialized entity, or the type default when deserialization failed. + /// public T Content { get; set; } + /// + /// The runtime type of . + /// public Type ContentType => typeof(T); + /// + /// Indicates whether deserialization succeeded. + /// public bool Success { get; set; } + /// + /// Informational messages produced during deserialization. + /// public IEnumerable Messages { get; set; } + /// + /// Non-fatal warnings produced during deserialization. + /// public IEnumerable Warnings { get; set; } + /// + /// Errors that caused or accompanied a failed deserialization. + /// public IEnumerable Errors { get; set; } + /// + /// The time taken to produce the result, in milliseconds. + /// public double ResponseDuration { get; set; } + /// + /// Initializes a read result from its constituent parts; the response duration starts at zero. + /// + /// The deserialized entity. + /// Whether deserialization succeeded. + /// Optional informational messages. + /// Optional non-fatal warnings. + /// Optional errors. public FormatReadResult(T content, bool success = true, IEnumerable messages = null, IEnumerable warnings = null, IEnumerable errors = null) { Content = content; @@ -34,6 +67,11 @@ public FormatReadResult(T content, bool success = true, IEnumerable mess } + /// + /// Creates a successful result with an optional single informational message. + /// + /// The deserialized entity. + /// An optional informational message. public static FormatReadResult Successful(T content, string message = null) { var messages = new List(); @@ -42,12 +80,22 @@ public static FormatReadResult Successful(T content, string message = null) return new FormatReadResult(content, true, messages); } + /// + /// Creates a successful result carrying a collection of informational messages. + /// + /// The deserialized entity. + /// The informational messages. public static FormatReadResult Successful(T content, IEnumerable messages) { return new FormatReadResult(content, true, messages); } + /// + /// Creates a result that succeeded but carries an optional single warning. + /// + /// The deserialized entity. + /// An optional warning message. public static FormatReadResult Warning(T content, string warning = null) { var warnings = new List(); @@ -56,12 +104,22 @@ public static FormatReadResult Warning(T content, string warning = null) return new FormatReadResult(content, true, null, warnings); } + /// + /// Creates a result that succeeded but carries a collection of warnings. + /// + /// The deserialized entity. + /// The warning messages. public static FormatReadResult Warning(T content, IEnumerable warnings) { return new FormatReadResult(content, true, null, warnings); } + /// + /// Creates a failed result that still carries the partially parsed content and an optional single error. + /// + /// The partially parsed entity, if any. + /// An optional error message. public static FormatReadResult Error(T content, string error = null) { var errors = new List(); @@ -70,11 +128,20 @@ public static FormatReadResult Error(T content, string error = null) return new FormatReadResult(content, false, null, null, errors); } + /// + /// Creates a failed result that still carries the partially parsed content and a collection of errors. + /// + /// The partially parsed entity, if any. + /// The error messages. public static FormatReadResult Error(T content, IEnumerable errors) { return new FormatReadResult(content, false, null, null, errors); } + /// + /// Creates a failed result with no content, carrying only the supplied errors. + /// + /// The error messages. public static FormatReadResult Error(IEnumerable errors = null) { return new FormatReadResult(default, false, null, null, errors); diff --git a/libraries/MTConnect.NET-Common/Formatters/FormatWriteResult.cs b/libraries/MTConnect.NET-Common/Formatters/FormatWriteResult.cs index 5d6f886f8..1c47db26e 100644 --- a/libraries/MTConnect.NET-Common/Formatters/FormatWriteResult.cs +++ b/libraries/MTConnect.NET-Common/Formatters/FormatWriteResult.cs @@ -6,23 +6,56 @@ namespace MTConnect.Formatters { + /// + /// The outcome of serializing an entity to a document, carrying the produced content stream, its content type, a success flag, and any diagnostic messages. + /// public struct FormatWriteResult { + /// + /// The serialized output stream, or null when serialization failed. + /// public Stream Content { get; set; } + /// + /// The MIME content type of . + /// public string ContentType { get; set; } + /// + /// Indicates whether serialization succeeded. + /// public bool Success { get; set; } + /// + /// Informational messages produced during serialization. + /// public IEnumerable Messages { get; set; } + /// + /// Non-fatal warnings produced during serialization. + /// public IEnumerable Warnings { get; set; } + /// + /// Errors that caused or accompanied a failed serialization. + /// public IEnumerable Errors { get; set; } + /// + /// The time taken to produce the result, in milliseconds. + /// public double ResponseDuration { get; set; } + /// + /// Initializes a write result from its constituent parts; the response duration starts at zero. + /// + /// The serialized output stream. + /// The MIME content type of the output. + /// Whether serialization succeeded. + /// Optional informational messages. + /// Optional non-fatal warnings. + /// Optional errors. public FormatWriteResult(Stream content, string contentType, bool success = true, IEnumerable messages = null, IEnumerable warnings = null, IEnumerable errors = null) { Content = content; @@ -35,6 +68,12 @@ public FormatWriteResult(Stream content, string contentType, bool success = true } + /// + /// Creates a successful result with optional single informational message. + /// + /// The serialized output stream. + /// The MIME content type. + /// An optional informational message. public static FormatWriteResult Successful(Stream content, string contentType, string message = null) { var messages = new List(); @@ -43,12 +82,24 @@ public static FormatWriteResult Successful(Stream content, string contentType, s return new FormatWriteResult(content, contentType, true, messages); } + /// + /// Creates a successful result carrying a collection of informational messages. + /// + /// The serialized output stream. + /// The MIME content type. + /// The informational messages. public static FormatWriteResult Successful(Stream content, string contentType, IEnumerable messages) { return new FormatWriteResult(content, contentType, true, messages); } + /// + /// Creates a result that succeeded but carries an optional single warning. + /// + /// The serialized output stream. + /// The MIME content type. + /// An optional warning message. public static FormatWriteResult Warning(Stream content, string contentType, string warning = null) { var warnings = new List(); @@ -57,12 +108,24 @@ public static FormatWriteResult Warning(Stream content, string contentType, stri return new FormatWriteResult(content, contentType, true, null, warnings); } + /// + /// Creates a result that succeeded but carries a collection of warnings. + /// + /// The serialized output stream. + /// The MIME content type. + /// The warning messages. public static FormatWriteResult Warning(Stream content, string contentType, IEnumerable warnings) { return new FormatWriteResult(content, contentType, true, null, warnings); } + /// + /// Creates a failed result with the produced content and an optional single error. + /// + /// The partial output stream, if any. + /// The MIME content type. + /// An optional error message. public static FormatWriteResult Error(Stream content, string contentType, string error = null) { var errors = new List(); @@ -71,11 +134,21 @@ public static FormatWriteResult Error(Stream content, string contentType, string return new FormatWriteResult(content, contentType, false, null, null, errors); } + /// + /// Creates a failed result with the produced content and a collection of errors. + /// + /// The partial output stream, if any. + /// The MIME content type. + /// The error messages. public static FormatWriteResult Error(Stream content, string contentType, IEnumerable errors) { return new FormatWriteResult(content, contentType, false, null, null, errors); } + /// + /// Creates a failed result with no content, carrying only the supplied errors. + /// + /// The error messages. public static FormatWriteResult Error(IEnumerable errors = null) { return new FormatWriteResult(null, null, false, null, null, errors); diff --git a/libraries/MTConnect.NET-Common/Formatters/IEntityFormatter.cs b/libraries/MTConnect.NET-Common/Formatters/IEntityFormatter.cs index 65a0b61a7..982f15918 100644 --- a/libraries/MTConnect.NET-Common/Formatters/IEntityFormatter.cs +++ b/libraries/MTConnect.NET-Common/Formatters/IEntityFormatter.cs @@ -9,30 +9,85 @@ namespace MTConnect.Formatters { + /// + /// Serializes and deserializes individual MTConnect entities (devices, observations, assets, and device-model elements) for a specific document format. + /// public interface IEntityFormatter { + /// + /// The unique identifier of the document format this formatter implements. + /// string Id { get; } + /// + /// The MIME content type produced by this formatter. + /// string ContentType { get; } + /// + /// Serializes a single device. + /// + /// The device to serialize. + /// Optional format-specific key/value options. FormatWriteResult Format(IDevice device, IEnumerable> options = null); + /// + /// Serializes a single observation. + /// + /// The observation to serialize. + /// Optional format-specific key/value options. FormatWriteResult Format(IObservation observation, IEnumerable> options = null); + /// + /// Serializes a batch of observations. + /// + /// The observations to serialize. + /// Optional format-specific key/value options. FormatWriteResult Format(IEnumerable observations, IEnumerable> options = null); + /// + /// Serializes a single asset. + /// + /// The asset to serialize. + /// Optional format-specific key/value options. FormatWriteResult Format(IAsset asset, IEnumerable> options = null); + /// + /// Deserializes a device from the given content stream. + /// + /// The serialized device content. + /// Optional format-specific key/value options. FormatReadResult CreateDevice(Stream content, IEnumerable> options = null); + /// + /// Deserializes a component from the given content stream. + /// + /// The serialized component content. + /// Optional format-specific key/value options. FormatReadResult CreateComponent(Stream content, IEnumerable> options = null); + /// + /// Deserializes a composition from the given content stream. + /// + /// The serialized composition content. + /// Optional format-specific key/value options. FormatReadResult CreateComposition(Stream content, IEnumerable> options = null); + /// + /// Deserializes a data item from the given content stream. + /// + /// The serialized data item content. + /// Optional format-specific key/value options. FormatReadResult CreateDataItem(Stream content, IEnumerable> options = null); + /// + /// Deserializes an asset of the given type from the given content stream. + /// + /// The MTConnect asset type to deserialize as. + /// The serialized asset content. + /// Optional format-specific key/value options. FormatReadResult CreateAsset(string assetType, Stream content, IEnumerable> options = null); } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Formatters/IFormatReadResult.cs b/libraries/MTConnect.NET-Common/Formatters/IFormatReadResult.cs index 6529e3024..b9d76ba8c 100644 --- a/libraries/MTConnect.NET-Common/Formatters/IFormatReadResult.cs +++ b/libraries/MTConnect.NET-Common/Formatters/IFormatReadResult.cs @@ -6,18 +6,39 @@ namespace MTConnect.Formatters { + /// + /// The non-generic view of a deserialization outcome, exposing the parsed content type, success flag, and diagnostic messages independently of the parsed entity type. + /// public interface IFormatReadResult { + /// + /// The runtime type of the deserialized content. + /// Type ContentType { get; } + /// + /// Indicates whether deserialization succeeded. + /// bool Success { get; } + /// + /// Informational messages produced during deserialization. + /// IEnumerable Messages { get; } + /// + /// Non-fatal warnings produced during deserialization. + /// IEnumerable Warnings { get; } + /// + /// Errors that caused or accompanied a failed deserialization. + /// IEnumerable Errors { get; } + /// + /// The time taken to produce the result, in milliseconds. + /// double ResponseDuration { get; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Formatters/IInputFormatter.cs b/libraries/MTConnect.NET-Common/Formatters/IInputFormatter.cs index ee3111307..91ca7174f 100644 --- a/libraries/MTConnect.NET-Common/Formatters/IInputFormatter.cs +++ b/libraries/MTConnect.NET-Common/Formatters/IInputFormatter.cs @@ -8,24 +8,63 @@ namespace MTConnect.Formatters { + /// + /// Serializes and deserializes adapter input payloads (device, observation, and asset inputs) for a specific wire format. + /// public interface IInputFormatter { + /// + /// The unique identifier of the input format this formatter implements. + /// string Id { get; } + /// + /// The MIME content type produced by this formatter. + /// string ContentType { get; } + /// + /// Serializes a device input definition. + /// + /// The device input to serialize. + /// Optional format-specific key/value options. FormatWriteResult Format(IDeviceInput device, IEnumerable> options = null); + /// + /// Serializes a batch of observation inputs. + /// + /// The observation inputs to serialize. + /// Optional format-specific key/value options. FormatWriteResult Format(IEnumerable observations, IEnumerable> options = null); + /// + /// Serializes a batch of asset inputs. + /// + /// The asset inputs to serialize. + /// Optional format-specific key/value options. FormatWriteResult Format(IEnumerable assets, IEnumerable> options = null); + /// + /// Deserializes a device definition from the given payload. + /// + /// The serialized device payload. + /// Optional format-specific key/value options. FormatReadResult CreateDevice(byte[] content, IEnumerable> options = null); + /// + /// Deserializes a batch of observation inputs from the given payload. + /// + /// The serialized observations payload. + /// Optional format-specific key/value options. FormatReadResult> CreateObservations(byte[] content, IEnumerable> options = null); + /// + /// Deserializes a batch of assets from the given payload. + /// + /// The serialized assets payload. + /// Optional format-specific key/value options. FormatReadResult> CreateAssets(byte[] content, IEnumerable> options = null); } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Formatters/IPathFormatter.cs b/libraries/MTConnect.NET-Common/Formatters/IPathFormatter.cs index 93a7240c9..d98115830 100644 --- a/libraries/MTConnect.NET-Common/Formatters/IPathFormatter.cs +++ b/libraries/MTConnect.NET-Common/Formatters/IPathFormatter.cs @@ -6,11 +6,22 @@ namespace MTConnect.Formatters { + /// + /// Resolves a path expression (such as an XPath) against a Devices document to the set of matching DataItem IDs, for a particular document format. + /// public interface IPathFormatter { + /// + /// The unique identifier of the document format this path formatter applies to. + /// string Id { get; } + /// + /// Evaluates the given path expression against the supplied Devices document and returns the IDs of the DataItems it selects. + /// + /// The Devices document to evaluate the path against. + /// The format-specific path expression. IEnumerable GetDataItemIds(IDevicesResponseDocument devicesDocument, string path); } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Formatters/IResponseDocumentFormatter.cs b/libraries/MTConnect.NET-Common/Formatters/IResponseDocumentFormatter.cs index 8f82fa4fe..ce185f6d9 100644 --- a/libraries/MTConnect.NET-Common/Formatters/IResponseDocumentFormatter.cs +++ b/libraries/MTConnect.NET-Common/Formatters/IResponseDocumentFormatter.cs @@ -11,28 +11,77 @@ namespace MTConnect.Formatters { + /// + /// Serializes and deserializes complete MTConnect response documents (Devices, Streams, Assets, and Error) for a specific document format. + /// public interface IResponseDocumentFormatter { + /// + /// The unique identifier of the document format this formatter implements. + /// string Id { get; } + /// + /// The MIME content type produced by this formatter. + /// string ContentType { get; } + /// + /// Serializes a Devices response document. + /// + /// The Devices document to serialize. + /// Optional format-specific key/value options. FormatWriteResult Format(IDevicesResponseDocument document, IEnumerable> options = null); + /// + /// Serializes a Streams response document, passed by reference to allow streaming serializers to release it as it is consumed. + /// + /// The Streams output document to serialize. + /// Optional format-specific key/value options. FormatWriteResult Format(ref IStreamsResponseOutputDocument document, IEnumerable> options = null); + /// + /// Serializes an Assets response document. + /// + /// The Assets document to serialize. + /// Optional format-specific key/value options. FormatWriteResult Format(IAssetsResponseDocument document, IEnumerable> options = null); + /// + /// Serializes an Error response document. + /// + /// The Error document to serialize. + /// Optional format-specific key/value options. FormatWriteResult Format(IErrorResponseDocument document, IEnumerable> options = null); + /// + /// Deserializes a Devices response document from the given content stream. + /// + /// The serialized Devices document content. + /// Optional format-specific key/value options. FormatReadResult CreateDevicesResponseDocument(Stream content, IEnumerable> options = null); + /// + /// Deserializes a Streams response document from the given content stream. + /// + /// The serialized Streams document content. + /// Optional format-specific key/value options. FormatReadResult CreateStreamsResponseDocument(Stream content, IEnumerable> options = null); + /// + /// Deserializes an Assets response document from the given content stream. + /// + /// The serialized Assets document content. + /// Optional format-specific key/value options. FormatReadResult CreateAssetsResponseDocument(Stream content, IEnumerable> options = null); + /// + /// Deserializes an Error response document from the given content stream. + /// + /// The serialized Error document content. + /// Optional format-specific key/value options. FormatReadResult CreateErrorResponseDocument(Stream content, IEnumerable> options = null); } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Formatters/InputFormatter.cs b/libraries/MTConnect.NET-Common/Formatters/InputFormatter.cs index 06336ef2e..ed2462bc8 100644 --- a/libraries/MTConnect.NET-Common/Formatters/InputFormatter.cs +++ b/libraries/MTConnect.NET-Common/Formatters/InputFormatter.cs @@ -13,12 +13,19 @@ namespace MTConnect.Formatters { + /// + /// Static facade that discovers and caches the implementations available across loaded assemblies and dispatches input serialization/deserialization to the one matching a requested format, timing each operation. + /// public static class InputFormatter { private static readonly ConcurrentDictionary _formatters = new ConcurrentDictionary(); private static bool _firstRead = true; + /// + /// Returns the MIME content type produced by the input formatter registered for the given format, or null when no such formatter exists. + /// + /// The identifier of the input format. public static string GetContentType(string documentFormatterId) { // Get the Formatter with the specified ID @@ -32,6 +39,12 @@ public static string GetContentType(string documentFormatterId) } + /// + /// Serializes a device input using the formatter for the given format, returning an error result when no matching formatter exists. The result's response duration is set to the elapsed time. + /// + /// The identifier of the input format. + /// The device input to serialize. + /// Optional format-specific key/value options. public static FormatWriteResult Format(string documentFormatterId, IDeviceInput device, IEnumerable> options = null) { var stpw = Stopwatch.StartNew(); @@ -52,6 +65,12 @@ public static FormatWriteResult Format(string documentFormatterId, IDeviceInput return result; } + /// + /// Serializes a batch of observation inputs using the formatter for the given format, returning an error result when no matching formatter exists. The result's response duration is set to the elapsed time. + /// + /// The identifier of the input format. + /// The observation inputs to serialize. + /// Optional format-specific key/value options. public static FormatWriteResult Format(string documentFormatterId, IEnumerable observations, IEnumerable> options = null) { var stpw = Stopwatch.StartNew(); @@ -72,6 +91,12 @@ public static FormatWriteResult Format(string documentFormatterId, IEnumerable + /// Serializes a batch of asset inputs using the formatter for the given format, returning an error result when no matching formatter exists. The result's response duration is set to the elapsed time. + /// + /// The identifier of the input format. + /// The asset inputs to serialize. + /// Optional format-specific key/value options. public static FormatWriteResult Format(string documentFormatterId, IEnumerable assets, IEnumerable> options = null) { var stpw = Stopwatch.StartNew(); @@ -93,6 +118,11 @@ public static FormatWriteResult Format(string documentFormatterId, IEnumerable + /// Deserializes a device from the given payload using the formatter for the given format; returns an error result when no matching formatter exists. + /// + /// The identifier of the input format. + /// The serialized device payload. public static FormatReadResult CreateDevice(string documentFormatterId, byte[] content) { // Get the Formatter with the specified ID @@ -106,6 +136,11 @@ public static FormatReadResult CreateDevice(string documentFormatterId, return FormatReadResult.Error(null, $"Input Formatter Not found for \"{documentFormatterId}\""); } + /// + /// Deserializes a batch of observation inputs from the given payload using the formatter for the given format; returns an error result when no matching formatter exists. + /// + /// The identifier of the input format. + /// The serialized observations payload. public static FormatReadResult> CreateObservations(string documentFormatterId, byte[] content) { // Get the Formatter with the specified ID @@ -119,6 +154,11 @@ public static FormatReadResult> CreateObservation return FormatReadResult>.Error(null, $"Input Formatter Not found for \"{documentFormatterId}\""); } + /// + /// Deserializes a batch of assets from the given payload using the formatter for the given format; returns an error result when no matching formatter exists. + /// + /// The identifier of the input format. + /// The serialized assets payload. public static FormatReadResult> CreateAssets(string documentFormatterId, byte[] content) { // Get the Formatter with the specified ID diff --git a/libraries/MTConnect.NET-Common/Formatters/PathFormatter.cs b/libraries/MTConnect.NET-Common/Formatters/PathFormatter.cs index 3131efb7e..c5fee5037 100644 --- a/libraries/MTConnect.NET-Common/Formatters/PathFormatter.cs +++ b/libraries/MTConnect.NET-Common/Formatters/PathFormatter.cs @@ -10,12 +10,21 @@ namespace MTConnect.Formatters { + /// + /// Static facade that discovers and caches the implementations available across loaded assemblies and dispatches path resolution to the one matching a requested document format. + /// public static class PathFormatter { private static readonly ConcurrentDictionary _formatters = new ConcurrentDictionary(); private static bool _firstRead = true; + /// + /// Resolves a path expression to matching DataItem IDs using the path formatter registered for the given document format; returns null when the path is empty or no matching formatter exists. + /// + /// The identifier of the document format whose path formatter should be used. + /// The Devices document to evaluate the path against. + /// The format-specific path expression. public static IEnumerable GetDataItemIds(string documentFormatterId, IDevicesResponseDocument devicesResponseDocument, string path) { if (!string.IsNullOrEmpty(path)) diff --git a/libraries/MTConnect.NET-Common/Formatters/ResponseDocumentFormatter.cs b/libraries/MTConnect.NET-Common/Formatters/ResponseDocumentFormatter.cs index 04863c8d1..744c6adea 100644 --- a/libraries/MTConnect.NET-Common/Formatters/ResponseDocumentFormatter.cs +++ b/libraries/MTConnect.NET-Common/Formatters/ResponseDocumentFormatter.cs @@ -14,12 +14,19 @@ namespace MTConnect.Formatters { + /// + /// Static facade that discovers and caches the implementations available across loaded assemblies and dispatches response-document serialization/deserialization to the one matching a requested document format, timing each operation. + /// public static class ResponseDocumentFormatter { private static readonly ConcurrentDictionary _formatters = new ConcurrentDictionary(); private static bool _firstRead = true; + /// + /// Returns the MIME content type produced by the response-document formatter registered for the given format, or null when no such formatter exists. + /// + /// The identifier of the document format. public static string GetContentType(string documentFormatterId) { // Get the Formatter with the specified ID @@ -33,6 +40,12 @@ public static string GetContentType(string documentFormatterId) } + /// + /// Serializes a Devices response document using the formatter for the given format, returning an error result when no matching formatter exists. The result's response duration is set to the elapsed time. + /// + /// The identifier of the document format. + /// The Devices document to serialize. + /// Optional format-specific key/value options. public static FormatWriteResult Format(string documentFormatterId, IDevicesResponseDocument document, IEnumerable> formatOptions = null) { var stpw = Stopwatch.StartNew(); @@ -53,6 +66,12 @@ public static FormatWriteResult Format(string documentFormatterId, IDevicesRespo return result; } + /// + /// Serializes a Streams response document using the formatter for the given format, returning an error result when no matching formatter exists. The document is passed by reference so streaming serializers may release it as it is consumed. The result's response duration is set to the elapsed time. + /// + /// The identifier of the document format. + /// The Streams output document to serialize. + /// Optional format-specific key/value options. public static FormatWriteResult Format(string documentFormatterId, ref IStreamsResponseOutputDocument document, IEnumerable> formatOptions = null) { var stpw = Stopwatch.StartNew(); @@ -73,6 +92,12 @@ public static FormatWriteResult Format(string documentFormatterId, ref IStreamsR return result; } + /// + /// Serializes an Assets response document using the formatter for the given format, returning an error result when no matching formatter exists. The result's response duration is set to the elapsed time. + /// + /// The identifier of the document format. + /// The Assets document to serialize. + /// Optional format-specific key/value options. public static FormatWriteResult Format(string documentFormatterId, IAssetsResponseDocument document, IEnumerable> formatOptions = null) { var stpw = Stopwatch.StartNew(); @@ -93,6 +118,12 @@ public static FormatWriteResult Format(string documentFormatterId, IAssetsRespon return result; } + /// + /// Serializes an Error response document using the formatter for the given format, returning an error result when no matching formatter exists. The result's response duration is set to the elapsed time. + /// + /// The identifier of the document format. + /// The Error document to serialize. + /// Optional format-specific key/value options. public static FormatWriteResult Format(string documentFormatterId, IErrorResponseDocument document, IEnumerable> formatOptions = null) { var stpw = Stopwatch.StartNew(); @@ -114,6 +145,11 @@ public static FormatWriteResult Format(string documentFormatterId, IErrorRespons } + /// + /// Deserializes a Devices response document from the given content stream using the formatter for the given format; returns an error result when no matching formatter exists. + /// + /// The identifier of the document format. + /// The serialized Devices document content. public static FormatReadResult CreateDevicesResponseDocument(string documentFormatterId, Stream content) { // Get the Formatter with the specified ID @@ -127,6 +163,11 @@ public static FormatReadResult CreateDevicesResponseDo return FormatReadResult.Error(null, $"Document Formatter Not found for \"{documentFormatterId}\""); } + /// + /// Deserializes a Streams response document from the given content stream using the formatter for the given format; returns an error result when no matching formatter exists. + /// + /// The identifier of the document format. + /// The serialized Streams document content. public static FormatReadResult CreateStreamsResponseDocument(string documentFormatterId, Stream content) { // Get the Formatter with the specified ID @@ -140,6 +181,11 @@ public static FormatReadResult CreateStreamsResponseDo return FormatReadResult.Error(null, $"Document Formatter Not found for \"{documentFormatterId}\""); } + /// + /// Deserializes an Assets response document from the given content stream using the formatter for the given format; returns an error result when no matching formatter exists. + /// + /// The identifier of the document format. + /// The serialized Assets document content. public static FormatReadResult CreateAssetsResponseDocument(string documentFormatterId, Stream content) { // Get the Formatter with the specified ID @@ -153,6 +199,11 @@ public static FormatReadResult CreateAssetsResponseDocu return FormatReadResult.Error(null, $"Document Formatter Not found for \"{documentFormatterId}\""); } + /// + /// Deserializes an Error response document from the given content stream using the formatter for the given format; returns an error result when no matching formatter exists. + /// + /// The identifier of the document format. + /// The serialized Error document content. public static FormatReadResult CreateErrorResponseDocument(string documentFormatterId, Stream content) { // Get the Formatter with the specified ID diff --git a/libraries/MTConnect.NET-Common/GarbageCollector.cs b/libraries/MTConnect.NET-Common/GarbageCollector.cs index c60fcb48a..fa6da6ec3 100644 --- a/libraries/MTConnect.NET-Common/GarbageCollector.cs +++ b/libraries/MTConnect.NET-Common/GarbageCollector.cs @@ -7,6 +7,9 @@ namespace MTConnect { + /// + /// Background coordinator that debounces explicit GC requests: callers signal a low- or high-priority need to collect, and a worker performs full collections no more often than the configured intervals, then tapers off with an exponentially backing-off "run" series so memory is reclaimed without thrashing. + /// public class GarbageCollector : IDisposable { private const int _interval = 250; @@ -31,6 +34,11 @@ public class GarbageCollector : IDisposable private bool _highPriorityCollect = false; + /// + /// Starts the background worker that performs debounced collections, with separate minimum spacings (in milliseconds) for low- and high-priority requests. + /// + /// Minimum milliseconds between collections triggered by low-priority requests. + /// Minimum milliseconds between collections triggered by high-priority requests. public GarbageCollector(int lowPriorityInterval = 10000, int highPriorityInterval = 500) { _lowPriorityInterval = lowPriorityInterval * 10000; // Convert ms to ticks @@ -39,6 +47,9 @@ public GarbageCollector(int lowPriorityInterval = 10000, int highPriorityInterva _ = Task.Run(Worker); } + /// + /// Signals the background worker to stop. + /// public void Dispose() { if (_stop != null) _stop.Cancel(); @@ -114,16 +125,27 @@ private async void Worker() } + /// + /// Lazily creates the shared singleton collector with the given intervals; subsequent calls have no effect. + /// + /// Minimum milliseconds between low-priority collections. + /// Minimum milliseconds between high-priority collections. public static void Initialize(int lowPriorityInterval = 30000, int highPriorityInterval = 500) { if (_instance == null) _instance = new GarbageCollector(lowPriorityInterval, highPriorityInterval); } + /// + /// Stops the shared singleton collector if it has been created. + /// public static void DisposeInstance() { if (_instance != null) _instance.Dispose(); } + /// + /// Requests a low-priority collection on the shared collector; the actual collection is deferred until the low-priority interval has elapsed. + /// public static void LowPriorityCollect() { if (_instance != null) @@ -135,6 +157,9 @@ public static void LowPriorityCollect() } } + /// + /// Requests a high-priority collection on the shared collector; collections are deferred only by the shorter high-priority interval and take precedence over low-priority requests. + /// public static void HighPriorityCollect() { if (_instance != null) diff --git a/libraries/MTConnect.NET-Common/Headers/MTConnectHeaderAttributeDescriptions.cs b/libraries/MTConnect.NET-Common/Headers/MTConnectHeaderAttributeDescriptions.cs index 13d91a9b0..493090a7b 100644 --- a/libraries/MTConnect.NET-Common/Headers/MTConnectHeaderAttributeDescriptions.cs +++ b/libraries/MTConnect.NET-Common/Headers/MTConnectHeaderAttributeDescriptions.cs @@ -3,6 +3,9 @@ namespace MTConnect.Headers { + /// + /// Canonical human-readable descriptions of the attributes carried on an MTConnect response document Header, used for documentation and tooltip generation. + /// public static class MTConnectHeaderAttributeDescriptions { /// diff --git a/libraries/MTConnect.NET-Common/IMTConnectEntity.cs b/libraries/MTConnect.NET-Common/IMTConnectEntity.cs index ed152ec34..c006dc290 100644 --- a/libraries/MTConnect.NET-Common/IMTConnectEntity.cs +++ b/libraries/MTConnect.NET-Common/IMTConnectEntity.cs @@ -3,10 +3,19 @@ namespace MTConnect { + /// + /// Common contract for any addressable entity in the MTConnect model, exposing its unique identity and its kind. + /// public interface IMTConnectEntity { + /// + /// The globally unique identifier of this entity. + /// string Uuid { get; } + /// + /// The category of this entity within the MTConnect model. + /// MTConnectEntityType EntityType { get; } } } diff --git a/libraries/MTConnect.NET-Common/Input/AssetInput.cs b/libraries/MTConnect.NET-Common/Input/AssetInput.cs index 802504e15..00d5304ff 100644 --- a/libraries/MTConnect.NET-Common/Input/AssetInput.cs +++ b/libraries/MTConnect.NET-Common/Input/AssetInput.cs @@ -6,6 +6,9 @@ namespace MTConnect.Input { + /// + /// An Information Model Input that associates an Asset with a Device for reporting to an Agent. + /// public class AssetInput : IAssetInput { private static readonly Encoding _utf8 = new UTF8Encoding(); @@ -64,6 +67,10 @@ public byte[] ChangeIdWithTimestamp } + /// + /// Initializes a new Asset Input from an Asset, taking its AssetId and Type and leaving the Device key unset. + /// + /// The Asset to report. A null argument leaves the new instance empty. public AssetInput(IAsset asset) { if (asset != null) @@ -74,6 +81,11 @@ public AssetInput(IAsset asset) } } + /// + /// Initializes a new Asset Input from an Asset and associates it with the specified Device. + /// + /// The UUID or Name of the Device the Asset is associated with. + /// The Asset to report. A null argument leaves the new instance empty. public AssetInput(string deviceKey, IAsset asset) { if (asset != null) @@ -85,6 +97,10 @@ public AssetInput(string deviceKey, IAsset asset) } } + /// + /// Initializes a new Asset Input by copying the Device key, AssetId, Type, Asset, and timestamp from an existing Asset Input. + /// + /// The source Asset Input to copy; a null argument leaves the new instance empty. public AssetInput(IAssetInput asset) { if (asset != null) diff --git a/libraries/MTConnect.NET-Common/Input/ConditionFaultStateObservationInput.cs b/libraries/MTConnect.NET-Common/Input/ConditionFaultStateObservationInput.cs index 9d83840bb..18a8e9eb8 100644 --- a/libraries/MTConnect.NET-Common/Input/ConditionFaultStateObservationInput.cs +++ b/libraries/MTConnect.NET-Common/Input/ConditionFaultStateObservationInput.cs @@ -90,19 +90,37 @@ public string Message } + /// + /// Initializes a new, empty FaultState with no DataItem key or level. + /// public ConditionFaultStateObservationInput() { } + /// + /// Initializes a new FaultState for the specified DataItem with no level set. + /// + /// The (ID, Name, or Source) of the Condition DataItem the FaultState applies to. public ConditionFaultStateObservationInput(string dataItemKey) { DataItemKey = dataItemKey; } + /// + /// Initializes a new FaultState for the specified DataItem at the given Condition level. + /// + /// The (ID, Name, or Source) of the Condition DataItem the FaultState applies to. + /// The Condition level of the FaultState. public ConditionFaultStateObservationInput(string dataItemKey, ConditionLevel level) { DataItemKey = dataItemKey; Level = level; } + /// + /// Initializes a new FaultState for the specified DataItem at the given Condition level and timestamp. + /// + /// The (ID, Name, or Source) of the Condition DataItem the FaultState applies to. + /// The Condition level of the FaultState. + /// The observation timestamp as UnixTime in milliseconds. public ConditionFaultStateObservationInput(string dataItemKey, ConditionLevel level, long timestamp) { DataItemKey = dataItemKey; @@ -110,6 +128,12 @@ public ConditionFaultStateObservationInput(string dataItemKey, ConditionLevel le Timestamp = timestamp; } + /// + /// Initializes a new FaultState for the specified DataItem at the given Condition level and timestamp. + /// + /// The (ID, Name, or Source) of the Condition DataItem the FaultState applies to. + /// The Condition level of the FaultState. + /// The observation timestamp, converted to UnixTime in milliseconds. public ConditionFaultStateObservationInput(string dataItemKey, ConditionLevel level, DateTime timestamp) { DataItemKey = dataItemKey; @@ -117,6 +141,10 @@ public ConditionFaultStateObservationInput(string dataItemKey, ConditionLevel le Timestamp = timestamp.ToUnixTime(); } + /// + /// Initializes a new FaultState by copying the Device key, DataItem key, timestamp, and values from an existing Observation. + /// + /// The source Observation to copy; a null argument leaves the new instance empty. public ConditionFaultStateObservationInput(IObservationInput observation) { if (observation != null) diff --git a/libraries/MTConnect.NET-Common/Input/ConditionObservationInput.cs b/libraries/MTConnect.NET-Common/Input/ConditionObservationInput.cs index a9e419091..af6c16583 100644 --- a/libraries/MTConnect.NET-Common/Input/ConditionObservationInput.cs +++ b/libraries/MTConnect.NET-Common/Input/ConditionObservationInput.cs @@ -110,31 +110,59 @@ public byte[] ChangeIdWithTimestamp public bool IsUnavailable { get; set; } + /// + /// Initializes a new, empty Condition Observation with no DataItem key or FaultStates. + /// public ConditionObservationInput() { } + /// + /// Initializes a new Condition Observation for the specified DataItem with no FaultStates. + /// + /// The (ID, Name, or Source) of the Condition DataItem the Observation applies to. public ConditionObservationInput(string dataItemKey) { DataItemKey = dataItemKey; } + /// + /// Initializes a new Condition Observation for the specified DataItem with a single FaultState at the given level. + /// + /// The (ID, Name, or Source) of the Condition DataItem the Observation applies to. + /// The Condition level of the initial FaultState. public ConditionObservationInput(string dataItemKey, ConditionLevel level) { DataItemKey = dataItemKey; AddFaultState(new ConditionFaultStateObservationInput(dataItemKey, level)); } + /// + /// Initializes a new Condition Observation for the specified DataItem with a single FaultState at the given level and timestamp. + /// + /// The (ID, Name, or Source) of the Condition DataItem the Observation applies to. + /// The Condition level of the initial FaultState. + /// The observation timestamp as UnixTime in milliseconds. public ConditionObservationInput(string dataItemKey, ConditionLevel level, long timestamp) { DataItemKey = dataItemKey; AddFaultState(new ConditionFaultStateObservationInput(dataItemKey, level, timestamp)); } + /// + /// Initializes a new Condition Observation for the specified DataItem with a single FaultState at the given level and timestamp. + /// + /// The (ID, Name, or Source) of the Condition DataItem the Observation applies to. + /// The Condition level of the initial FaultState. + /// The observation timestamp, converted to UnixTime in milliseconds. public ConditionObservationInput(string dataItemKey, ConditionLevel level, DateTime timestamp) { DataItemKey = dataItemKey; AddFaultState(new ConditionFaultStateObservationInput(dataItemKey, level, timestamp)); } + /// + /// Initializes a new Condition Observation by copying the Device key, DataItem key, and FaultStates from an existing Condition. + /// + /// The source Condition to copy; a null argument leaves the new instance empty. public ConditionObservationInput(IConditionObservationInput condition) { if (condition != null) @@ -414,6 +442,11 @@ public void AddFault(DateTime timestamp, string text = null, string nativeCode = /// /// Add a FaultState to the Condition while retaining any other FaultStates /// + /// + /// Adds a FaultState to the Condition, propagating the Device and DataItem keys and removing any prior FaultState + /// that shares its NativeCode. A WARNING or FAULT with no NativeCode replaces all existing FaultStates. + /// + /// The FaultState to add. A null argument is ignored. public void AddFaultState(IConditionFaultStateObservationInput faultState) { if (faultState != null) @@ -445,6 +478,10 @@ public void AddFaultState(IConditionFaultStateObservationInput faultState) } + /// + /// Removes every FaultState whose NativeCode matches the specified value and resets cached change identifiers. + /// + /// The NativeCode whose FaultStates are removed. public void ClearFaultStates(string nativeCode) { lock (_lock) @@ -467,6 +504,9 @@ public void ClearFaultStates(string nativeCode) _changeIdWithTimestamp = null; } + /// + /// Removes all FaultStates from the Condition and resets cached change identifiers. + /// public void ClearFaultStates() { lock (_lock) _faultStates = null; diff --git a/libraries/MTConnect.NET-Common/Input/DataSetObservationInput.cs b/libraries/MTConnect.NET-Common/Input/DataSetObservationInput.cs index 241cc4b17..081974215 100644 --- a/libraries/MTConnect.NET-Common/Input/DataSetObservationInput.cs +++ b/libraries/MTConnect.NET-Common/Input/DataSetObservationInput.cs @@ -46,14 +46,28 @@ public IEnumerable Entries } + /// + /// Initializes a new, empty Data Set Observation with no DataItem key or entries. + /// public DataSetObservationInput() { } + /// + /// Initializes a new Data Set Observation for the specified DataItem with the given entries. + /// + /// The (ID, Name, or Source) of the DataItem the Observation applies to. + /// The key-value pairs that make up the Data Set. public DataSetObservationInput(string dataItemKey, IEnumerable entries) { DataItemKey = dataItemKey; Entries = entries; } + /// + /// Initializes a new Data Set Observation for the specified DataItem with the given entries and timestamp. + /// + /// The (ID, Name, or Source) of the DataItem the Observation applies to. + /// The key-value pairs that make up the Data Set. + /// The observation timestamp as UnixTime in milliseconds. public DataSetObservationInput(string dataItemKey, IEnumerable entries, long timestamp) { DataItemKey = dataItemKey; @@ -61,6 +75,12 @@ public DataSetObservationInput(string dataItemKey, IEnumerable en Timestamp = timestamp; } + /// + /// Initializes a new Data Set Observation for the specified DataItem with the given entries and timestamp. + /// + /// The (ID, Name, or Source) of the DataItem the Observation applies to. + /// The key-value pairs that make up the Data Set. + /// The observation timestamp, converted to UnixTime in milliseconds. public DataSetObservationInput(string dataItemKey, IEnumerable entries, DateTime timestamp) { DataItemKey = dataItemKey; @@ -68,6 +88,10 @@ public DataSetObservationInput(string dataItemKey, IEnumerable en Timestamp = timestamp.ToUnixTime(); } + /// + /// Initializes a new Data Set Observation by copying the Device key, DataItem key, timestamp, and values from an existing Observation. + /// + /// The source Observation to copy; a null argument leaves the new instance empty. public DataSetObservationInput(IObservationInput observation) { if (observation != null) diff --git a/libraries/MTConnect.NET-Common/Input/DeviceInput.cs b/libraries/MTConnect.NET-Common/Input/DeviceInput.cs index 3147ef580..2ddbc778d 100644 --- a/libraries/MTConnect.NET-Common/Input/DeviceInput.cs +++ b/libraries/MTConnect.NET-Common/Input/DeviceInput.cs @@ -6,6 +6,9 @@ namespace MTConnect.Input { + /// + /// An Information Model Input that carries a Device definition for reporting to an Agent. + /// public class DeviceInput : IDeviceInput { private static readonly Encoding _utf8 = new UTF8Encoding(); @@ -54,6 +57,10 @@ public byte[] ChangeIdWithTimestamp } + /// + /// Initializes a new Device Input from a Device, using the Device UUID as the key. + /// + /// The Device to report. A null argument leaves the new instance empty. public DeviceInput(IDevice device) { if (device != null) @@ -63,6 +70,11 @@ public DeviceInput(IDevice device) } } + /// + /// Initializes a new Device Input from a Device with an explicit Device key. + /// + /// The UUID or Name used to identify the Device. + /// The Device to report. A null argument leaves the new instance empty. public DeviceInput(string deviceKey, IDevice device) { if (device != null) @@ -72,6 +84,10 @@ public DeviceInput(string deviceKey, IDevice device) } } + /// + /// Initializes a new Device Input by copying the Device key, Device, and timestamp from an existing Device Input. + /// + /// The source Device Input to copy; a null argument leaves the new instance empty. public DeviceInput(IDeviceInput device) { if (device != null) diff --git a/libraries/MTConnect.NET-Common/Input/IAssetInput.cs b/libraries/MTConnect.NET-Common/Input/IAssetInput.cs index cec49840b..9b8e4ec9c 100644 --- a/libraries/MTConnect.NET-Common/Input/IAssetInput.cs +++ b/libraries/MTConnect.NET-Common/Input/IAssetInput.cs @@ -5,6 +5,9 @@ namespace MTConnect.Input { + /// + /// An Information Model Input that associates an Asset with a Device for reporting to an Agent. + /// public interface IAssetInput { /// diff --git a/libraries/MTConnect.NET-Common/Input/IConditionFaultStateObservationInput.cs b/libraries/MTConnect.NET-Common/Input/IConditionFaultStateObservationInput.cs index 980f85e81..28a6afbee 100644 --- a/libraries/MTConnect.NET-Common/Input/IConditionFaultStateObservationInput.cs +++ b/libraries/MTConnect.NET-Common/Input/IConditionFaultStateObservationInput.cs @@ -5,6 +5,9 @@ namespace MTConnect.Input { + /// + /// A single FaultState that contributes to a Condition Observation, describing the level, identifying codes, qualifier, and message of one condition activation. + /// public interface IConditionFaultStateObservationInput : IObservationInput { /// diff --git a/libraries/MTConnect.NET-Common/Input/IConditionObservationInput.cs b/libraries/MTConnect.NET-Common/Input/IConditionObservationInput.cs index 78c30136f..eb052d5d7 100644 --- a/libraries/MTConnect.NET-Common/Input/IConditionObservationInput.cs +++ b/libraries/MTConnect.NET-Common/Input/IConditionObservationInput.cs @@ -5,6 +5,9 @@ namespace MTConnect.Input { + /// + /// An Information Model Input that describes Condition Streaming Data, composed of one or more FaultStates, reported by a piece of equipment. + /// public interface IConditionObservationInput { /// @@ -18,6 +21,9 @@ public interface IConditionObservationInput string DataItemKey { get; set; } + /// + /// The set of FaultStates that make up the current state of the Condition. + /// IEnumerable FaultStates { get; set; } /// diff --git a/libraries/MTConnect.NET-Common/Input/IDeviceInput.cs b/libraries/MTConnect.NET-Common/Input/IDeviceInput.cs index 99a12cc06..e73ba0786 100644 --- a/libraries/MTConnect.NET-Common/Input/IDeviceInput.cs +++ b/libraries/MTConnect.NET-Common/Input/IDeviceInput.cs @@ -5,6 +5,9 @@ namespace MTConnect.Input { + /// + /// An Information Model Input that carries a Device definition for reporting to an Agent. + /// public interface IDeviceInput { /// diff --git a/libraries/MTConnect.NET-Common/Input/IMTConnectDataSource.cs b/libraries/MTConnect.NET-Common/Input/IMTConnectDataSource.cs index b2fd44932..7c807c985 100644 --- a/libraries/MTConnect.NET-Common/Input/IMTConnectDataSource.cs +++ b/libraries/MTConnect.NET-Common/Input/IMTConnectDataSource.cs @@ -13,37 +13,92 @@ namespace MTConnect.Input /// public interface IMTConnectDataSource { + /// + /// The configuration that controls the polling interval and identifies the data source. + /// IDataSourceConfiguration Configuration { get; set; } + /// + /// Raised when the data source produces a new Observation to be written to the Adapter. + /// event EventHandler ObservationAdded; + /// + /// Raised when the data source produces a new Asset to be written to the Adapter. + /// event EventHandler AssetAdded; + /// + /// Raised when the data source produces a new Device to be written to the Adapter. + /// event EventHandler DeviceAdded; + /// + /// Starts the worker thread that polls the data source at the configured interval. + /// void Start(); + /// + /// Stops the worker thread and ends polling of the data source. + /// void Stop(); + /// + /// Queues an Observation for the specified DataItem using the current time as the timestamp. + /// + /// The (ID, Name, or Source) of the DataItem the Observation applies to. + /// The Result value to report. void AddObservation(string dataItemKey, object resultValue); + /// + /// Queues an Observation for the specified DataItem at the given timestamp. + /// + /// The (ID, Name, or Source) of the DataItem the Observation applies to. + /// The Result value to report. + /// The observation timestamp as UnixTime in milliseconds, or null to use the current time. void AddObservation(string dataItemKey, object resultValue, long? timestamp); + /// + /// Queues an Observation for the specified DataItem at the given timestamp. + /// + /// The (ID, Name, or Source) of the DataItem the Observation applies to. + /// The Result value to report. + /// The observation timestamp, or null to use the current time. void AddObservation(string dataItemKey, object resultValue, DateTime? timestamp); + /// + /// Queues a fully constructed Observation. + /// + /// The Observation to report. void AddObservation(IObservationInput observation); + /// + /// Queues an Asset for reporting to the Adapter. + /// + /// The Asset to report. void AddAsset(IAsset asset); + /// + /// Queues a fully constructed Asset Input for reporting to the Adapter. + /// + /// The Asset Input to report. void AddAsset(IAssetInput assetInput); + /// + /// Queues a Device for reporting to the Adapter. + /// + /// The Device to report. void AddDevice(IDevice device); + /// + /// Queues a fully constructed Device Input for reporting to the Adapter. + /// + /// The Device Input to report. void AddDevice(IDeviceInput deviceInput); } } diff --git a/libraries/MTConnect.NET-Common/Input/IObservationInput.cs b/libraries/MTConnect.NET-Common/Input/IObservationInput.cs index b8f7c6870..36cd745b6 100644 --- a/libraries/MTConnect.NET-Common/Input/IObservationInput.cs +++ b/libraries/MTConnect.NET-Common/Input/IObservationInput.cs @@ -58,10 +58,24 @@ public interface IObservationInput byte[] ChangeIdWithTimestamp { get; } + /// + /// Adds a value to the Observation using the specified ValueKey and raw value. + /// + /// The ValueKey that identifies the Representation component the value applies to. + /// The value to record. It is converted to its string representation when stored. void AddValue(string valueKey, object value); + /// + /// Adds a previously constructed to the Observation. + /// + /// The ValueKey and value pair to record. void AddValue(ObservationValue observationValue); + /// + /// Gets the value recorded for the specified ValueKey. + /// + /// The ValueKey that identifies the Representation component to retrieve. + /// The recorded value, or null when no value exists for the ValueKey. string GetValue(string valueKey); } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Input/MTConnectDataSource.cs b/libraries/MTConnect.NET-Common/Input/MTConnectDataSource.cs index 0f9f8240f..77133d167 100644 --- a/libraries/MTConnect.NET-Common/Input/MTConnectDataSource.cs +++ b/libraries/MTConnect.NET-Common/Input/MTConnectDataSource.cs @@ -20,33 +20,67 @@ public abstract class MTConnectDataSource : IMTConnectDataSource private bool _isStarted; + /// + /// The configuration that controls the polling interval and identifies the data source. + /// public IDataSourceConfiguration Configuration { get; set; } + /// + /// Raised when the data source produces a new Observation to be written to the Adapter. + /// public event EventHandler ObservationAdded; + /// + /// Raised when the data source produces a new Asset to be written to the Adapter. + /// public event EventHandler AssetAdded; + /// + /// Raised when the data source produces a new Device to be written to the Adapter. + /// public event EventHandler DeviceAdded; + /// + /// Raised when the data source emits a log message. + /// public event MTConnectLogEventHandler LogReceived; + /// + /// Initializes a new data source with a default . + /// public MTConnectDataSource() { Configuration = new DataSourceConfiguration(); } + /// + /// Called when the data source is started. Override to perform connection or initialization work. + /// protected virtual void OnStart() { } + /// + /// Called when the data source is stopped. Override to release resources or close connections. + /// protected virtual void OnStop() { } + /// + /// Called on each polling cycle. Override to perform synchronous reads from the data source. + /// protected virtual void OnRead() { } + /// + /// Called on each polling cycle after . Override to perform asynchronous reads from the data source. + /// + /// A task that completes when the read has finished. protected virtual Task OnReadAsync() { return Task.CompletedTask; } + /// + /// Starts the worker thread that polls the data source at the configured interval. No effect if already started. + /// public void Start() { if (!_isStarted) @@ -61,6 +95,9 @@ public void Start() } } + /// + /// Stops the worker thread and ends polling of the data source. No effect if not started. + /// public void Stop() { if (_isStarted) @@ -96,57 +133,99 @@ private async Task Worker() } - public void AddObservation(IDataItem dataItem, object resultValue) - { + /// + /// Queues an Observation for the specified DataItem using the current time as the timestamp. + /// + /// The DataItem the Observation applies to. Ignored when null or without an Id. + /// The Result value to report. + public void AddObservation(IDataItem dataItem, object resultValue) + { + if (dataItem != null && !string.IsNullOrEmpty(dataItem.Id)) + { + var observation = new ObservationInput(dataItem.Id, resultValue); + AddObservation(observation); + } + } + + /// + /// Queues an Observation for the specified DataItem at the given timestamp. + /// + /// The DataItem the Observation applies to. Ignored when null or without an Id. + /// The Result value to report. + /// The observation timestamp as UnixTime in milliseconds. + public void AddObservation(IDataItem dataItem, object resultValue, long? timestamp = null) + { + if (dataItem != null && !string.IsNullOrEmpty(dataItem.Id)) + { + var observation = new ObservationInput(dataItem.Id, resultValue, timestamp.Value); + AddObservation(observation); + } + } + + /// + /// Queues an Observation for the specified DataItem at the given timestamp. + /// + /// The DataItem the Observation applies to. Ignored when null or without an Id. + /// The Result value to report. + /// The observation timestamp. + public void AddObservation(IDataItem dataItem, object resultValue, DateTime? timestamp = null) + { if (dataItem != null && !string.IsNullOrEmpty(dataItem.Id)) { - var observation = new ObservationInput(dataItem.Id, resultValue); - AddObservation(observation); - } - } - - public void AddObservation(IDataItem dataItem, object resultValue, long? timestamp = null) - { - if (dataItem != null && !string.IsNullOrEmpty(dataItem.Id)) - { - var observation = new ObservationInput(dataItem.Id, resultValue, timestamp.Value); - AddObservation(observation); - } - } - - public void AddObservation(IDataItem dataItem, object resultValue, DateTime? timestamp = null) - { - if (dataItem != null && !string.IsNullOrEmpty(dataItem.Id)) - { - var observation = new ObservationInput(dataItem.Id, resultValue, timestamp.Value); - AddObservation(observation); - } - } - - public void AddObservation(string dataItemKey, object resultValue) + var observation = new ObservationInput(dataItem.Id, resultValue, timestamp.Value); + AddObservation(observation); + } + } + + /// + /// Queues an Observation for the specified DataItem key using the current time as the timestamp. + /// + /// The (ID, Name, or Source) of the DataItem the Observation applies to. + /// The Result value to report. + public void AddObservation(string dataItemKey, object resultValue) { var observation = new ObservationInput(dataItemKey, resultValue); AddObservation(observation); } + /// + /// Queues an Observation for the specified DataItem key at the given timestamp. + /// + /// The (ID, Name, or Source) of the DataItem the Observation applies to. + /// The Result value to report. + /// The observation timestamp as UnixTime in milliseconds. public void AddObservation(string dataItemKey, object resultValue, long? timestamp = null) { var observation = new ObservationInput(dataItemKey, resultValue, timestamp.Value); AddObservation(observation); } + /// + /// Queues an Observation for the specified DataItem key at the given timestamp. + /// + /// The (ID, Name, or Source) of the DataItem the Observation applies to. + /// The Result value to report. + /// The observation timestamp. public void AddObservation(string dataItemKey, object resultValue, DateTime? timestamp = null) { var observation = new ObservationInput(dataItemKey, resultValue, timestamp.Value); AddObservation(observation); } + /// + /// Queues a fully constructed Observation, raising . + /// + /// The Observation to report. public void AddObservation(IObservationInput observation) { if (ObservationAdded != null) ObservationAdded.Invoke(this, observation); } + /// + /// Queues an Asset for reporting to the Adapter. + /// + /// The Asset to report. Ignored when null. public void AddAsset(IAsset asset) { if (asset != null) @@ -155,12 +234,20 @@ public void AddAsset(IAsset asset) } } + /// + /// Queues a fully constructed Asset Input, raising . + /// + /// The Asset Input to report. public void AddAsset(IAssetInput asset) { if (AssetAdded != null) AssetAdded.Invoke(this, asset); } + /// + /// Queues a Device for reporting to the Adapter. + /// + /// The Device to report. Ignored when null. public void AddDevice(IDevice device) { if (device != null) @@ -169,12 +256,21 @@ public void AddDevice(IDevice device) } } + /// + /// Queues a fully constructed Device Input, raising . + /// + /// The Device Input to report. public void AddDevice(IDeviceInput device) { if (DeviceAdded != null) DeviceAdded.Invoke(this, device); } + /// + /// Emits a log message to subscribers of . + /// + /// The severity of the log message. + /// The log message text. protected void Log(MTConnectLogLevel logLevel, string message) { if (LogReceived != null) LogReceived.Invoke(this, logLevel, message); diff --git a/libraries/MTConnect.NET-Common/Input/ObservationInput.cs b/libraries/MTConnect.NET-Common/Input/ObservationInput.cs index 5129491e5..fd685b457 100644 --- a/libraries/MTConnect.NET-Common/Input/ObservationInput.cs +++ b/libraries/MTConnect.NET-Common/Input/ObservationInput.cs @@ -100,24 +100,42 @@ public byte[] ChangeIdWithTimestamp } + /// + /// Initializes a new, empty Observation with no DataItem key, values, or timestamp. + /// public ObservationInput() { } + /// + /// Initializes a new Observation for the specified DataItem with an unset timestamp. + /// + /// The (ID, Name, or Source) of the DataItem the Observation applies to. public ObservationInput(string dataItemKey) { DataItemKey = dataItemKey; Timestamp = 0; } + /// + /// Initializes a new Observation for the specified DataItem and records the value under the Result ValueKey. + /// + /// The (ID, Name, or Source) of the DataItem the Observation applies to. + /// The Result value. A null value is stored as an empty string. public ObservationInput(string dataItemKey, object value) { DataItemKey = dataItemKey; - Values = new List - { + Values = new List + { new ObservationValue(ValueKeys.Result, value != null ? value.ToString() : string.Empty) }; Timestamp = 0; } + /// + /// Initializes a new Observation for the specified DataItem, recording the value under the Result ValueKey at the given timestamp. + /// + /// The (ID, Name, or Source) of the DataItem the Observation applies to. + /// The Result value. A null value is stored as an empty string. + /// The observation timestamp as UnixTime in milliseconds. public ObservationInput(string dataItemKey, object value, long timestamp) { DataItemKey = dataItemKey; @@ -128,6 +146,12 @@ public ObservationInput(string dataItemKey, object value, long timestamp) Timestamp = timestamp; } + /// + /// Initializes a new Observation for the specified DataItem, recording the value under the Result ValueKey at the given timestamp. + /// + /// The (ID, Name, or Source) of the DataItem the Observation applies to. + /// The Result value. A null value is stored as an empty string. + /// The observation timestamp, converted to UnixTime in milliseconds. public ObservationInput(string dataItemKey, object value, DateTime timestamp) { DataItemKey = dataItemKey; @@ -138,6 +162,13 @@ public ObservationInput(string dataItemKey, object value, DateTime timestamp) Timestamp = timestamp.ToUnixTime(); } + /// + /// Initializes a new Observation for the specified DataItem, recording the value under an explicit ValueKey at the given timestamp. + /// + /// The (ID, Name, or Source) of the DataItem the Observation applies to. + /// The ValueKey identifying the Representation component the value applies to. + /// The value to record. A null value is stored as an empty string. + /// The observation timestamp as UnixTime in milliseconds. public ObservationInput(string dataItemKey, string valueKey, object value, long timestamp) { DataItemKey = dataItemKey; @@ -148,6 +179,13 @@ public ObservationInput(string dataItemKey, string valueKey, object value, long Timestamp = timestamp; } + /// + /// Initializes a new Observation for the specified DataItem, recording the value under an explicit ValueKey at the given timestamp. + /// + /// The (ID, Name, or Source) of the DataItem the Observation applies to. + /// The ValueKey identifying the Representation component the value applies to. + /// The value to record. A null value is stored as an empty string. + /// The observation timestamp, converted to UnixTime in milliseconds. public ObservationInput(string dataItemKey, string valueKey, object value, DateTime timestamp) { DataItemKey = dataItemKey; @@ -158,6 +196,10 @@ public ObservationInput(string dataItemKey, string valueKey, object value, DateT Timestamp = timestamp.ToUnixTime(); } + /// + /// Initializes a new Observation by copying the Device key, DataItem key, timestamp, and values from an existing Observation. + /// + /// The source Observation to copy. public ObservationInput(IObservationInput observationInput) { DeviceKey = observationInput.DeviceKey; @@ -166,6 +208,10 @@ public ObservationInput(IObservationInput observationInput) Values = observationInput.Values; } + /// + /// Initializes a new Observation from a reported , mapping its Device UUID, DataItem ID, timestamp, and values. + /// + /// The reported Observation to convert. public ObservationInput(IObservation observation) { DeviceKey = observation.DeviceUuid; @@ -175,6 +221,9 @@ public ObservationInput(IObservation observation) } + /// + /// Marks the Observation as Unavailable, setting the Result to the Unavailable constant and the flag. + /// public void Unavailable() { AddValue(ValueKeys.Result, Observation.Unavailable); @@ -182,11 +231,20 @@ public void Unavailable() } + /// + /// Adds a value to the Observation using the specified ValueKey and raw value. + /// + /// The ValueKey that identifies the Representation component the value applies to. + /// The value to record. public void AddValue(string valueKey, object value) { AddValue(new ObservationValue(valueKey, value)); } + /// + /// Adds a , replacing any existing value with the same ValueKey and resetting cached change identifiers. + /// + /// The ValueKey and value pair to record. Values with no content are not stored. public void AddValue(ObservationValue observationValue) { var x = new List(); @@ -208,6 +266,11 @@ public void AddValue(ObservationValue observationValue) _changeIdWithTimestamp = null; } + /// + /// Gets the value recorded for the specified ValueKey. + /// + /// The ValueKey that identifies the Representation component to retrieve. + /// The recorded value, or null when the ValueKey is empty or no matching value exists. public string GetValue(string valueKey) { if (!string.IsNullOrEmpty(valueKey) && !Values.IsNullOrEmpty()) @@ -219,6 +282,9 @@ public string GetValue(string valueKey) return null; } + /// + /// Removes all recorded values and resets cached change identifiers. + /// public void ClearValues() { Values = null; @@ -261,6 +327,13 @@ private static byte[] CreateChangeId(IObservationInput observationInput, bool in return null; } + /// + /// Formats a timestamp as an ISO 8601 string, optionally applying a time zone offset and appending a duration suffix. + /// + /// The timestamp as UnixTime in milliseconds. A non-positive value yields a duration-only or null result. + /// The optional sample period appended as @duration when greater than zero. + /// The optional time zone used to compute the offset; UTC is used when not specified. + /// The formatted timestamp string, or null when neither a timestamp nor a duration is provided. protected static string GetTimestampString(long timestamp, double duration = 0, TimeZoneInfo timeZoneInfo = null) { if (timestamp > 0) diff --git a/libraries/MTConnect.NET-Common/Input/TableObservationInput.cs b/libraries/MTConnect.NET-Common/Input/TableObservationInput.cs index 96906c7f5..f3a24f659 100644 --- a/libraries/MTConnect.NET-Common/Input/TableObservationInput.cs +++ b/libraries/MTConnect.NET-Common/Input/TableObservationInput.cs @@ -15,7 +15,7 @@ namespace MTConnect.Input public class TableObservationInput : ObservationInput { /// - /// Key-value pairs published as part of a Data Set observation + /// The rows published as part of a Table observation, each containing a set of Cell key-value pairs. /// public IEnumerable Entries { @@ -52,14 +52,28 @@ public IEnumerable Entries } + /// + /// Initializes a new, empty Table Observation with no DataItem key or rows. + /// public TableObservationInput() { } + /// + /// Initializes a new Table Observation for the specified DataItem with the given rows. + /// + /// The (ID, Name, or Source) of the DataItem the Observation applies to. + /// The rows that make up the Table. public TableObservationInput(string dataItemKey, IEnumerable entries) { DataItemKey = dataItemKey; Entries = entries; } + /// + /// Initializes a new Table Observation for the specified DataItem with the given rows and timestamp. + /// + /// The (ID, Name, or Source) of the DataItem the Observation applies to. + /// The rows that make up the Table. + /// The observation timestamp as UnixTime in milliseconds. public TableObservationInput(string dataItemKey, IEnumerable entries, long timestamp) { DataItemKey = dataItemKey; @@ -67,6 +81,12 @@ public TableObservationInput(string dataItemKey, IEnumerable entrie Timestamp = timestamp; } + /// + /// Initializes a new Table Observation for the specified DataItem with the given rows and timestamp. + /// + /// The (ID, Name, or Source) of the DataItem the Observation applies to. + /// The rows that make up the Table. + /// The observation timestamp, converted to UnixTime in milliseconds. public TableObservationInput(string dataItemKey, IEnumerable entries, DateTime timestamp) { DataItemKey = dataItemKey; @@ -74,6 +94,10 @@ public TableObservationInput(string dataItemKey, IEnumerable entrie Timestamp = timestamp.ToUnixTime(); } + /// + /// Initializes a new Table Observation by copying the Device key, DataItem key, timestamp, and values from an existing Observation. + /// + /// The source Observation to copy; a null argument leaves the new instance empty. public TableObservationInput(IObservationInput observation) { if (observation != null) diff --git a/libraries/MTConnect.NET-Common/Input/TimeSeriesObservationInput.cs b/libraries/MTConnect.NET-Common/Input/TimeSeriesObservationInput.cs index e137365cd..b51f50cd5 100644 --- a/libraries/MTConnect.NET-Common/Input/TimeSeriesObservationInput.cs +++ b/libraries/MTConnect.NET-Common/Input/TimeSeriesObservationInput.cs @@ -56,8 +56,17 @@ public IEnumerable Samples } + /// + /// Initializes a new, empty Time Series Observation with no DataItem key or samples. + /// public TimeSeriesObservationInput() { } + /// + /// Initializes a new Time Series Observation for the specified DataItem with the given samples and sample rate. + /// + /// The (ID, Name, or Source) of the DataItem the Observation applies to. + /// The values reported during the Observation, in time order. + /// The frequency at which the samples were observed. public TimeSeriesObservationInput(string dataItemKey, IEnumerable samples, double sampleRate) { DataItemKey = dataItemKey; @@ -65,6 +74,13 @@ public TimeSeriesObservationInput(string dataItemKey, IEnumerable sample SampleRate = sampleRate; } + /// + /// Initializes a new Time Series Observation for the specified DataItem with the given samples, sample rate, and timestamp. + /// + /// The (ID, Name, or Source) of the DataItem the Observation applies to. + /// The values reported during the Observation, in time order. + /// The frequency at which the samples were observed. + /// The observation timestamp as UnixTime in milliseconds. public TimeSeriesObservationInput(string dataItemKey, IEnumerable samples, double sampleRate, long timestamp) { DataItemKey = dataItemKey; @@ -73,6 +89,13 @@ public TimeSeriesObservationInput(string dataItemKey, IEnumerable sample Timestamp = timestamp; } + /// + /// Initializes a new Time Series Observation for the specified DataItem with the given samples, sample rate, and timestamp. + /// + /// The (ID, Name, or Source) of the DataItem the Observation applies to. + /// The values reported during the Observation, in time order. + /// The frequency at which the samples were observed. + /// The observation timestamp, converted to UnixTime in milliseconds. public TimeSeriesObservationInput(string dataItemKey, IEnumerable samples, double sampleRate, DateTime timestamp) { DataItemKey = dataItemKey; @@ -81,6 +104,10 @@ public TimeSeriesObservationInput(string dataItemKey, IEnumerable sample Timestamp = timestamp.ToUnixTime(); } + /// + /// Initializes a new Time Series Observation by copying the Device key, DataItem key, timestamp, and values from an existing Observation. + /// + /// The source Observation to copy; a null argument leaves the new instance empty. public TimeSeriesObservationInput(IObservationInput observation) { if (observation != null) diff --git a/libraries/MTConnect.NET-Common/Interfaces/BarFeederInterface.cs b/libraries/MTConnect.NET-Common/Interfaces/BarFeederInterface.cs index 417ee2422..44214b76f 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/BarFeederInterface.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/BarFeederInterface.cs @@ -5,22 +5,42 @@ namespace MTConnect.Interfaces { /// /// Interface that coordinates the operations between a bar feeder and another piece of equipment. - /// Bar feeder is a piece of equipment that pushes bar stock(i.e., long pieces of material of various shapes) into an associated piece of equipment – most typically a lathe or turning center. + /// Bar feeder is a piece of equipment that pushes bar stock (i.e., long pieces of material of various shapes) into an associated piece of equipment - most typically a lathe or turning center. /// - public class BarFeederInterface : Interface + public class BarFeederInterface : Interface { + /// + /// The fixed Component type identifier ("BarFeederInterface") written to the Type attribute and used to recognize this Interface during deserialization. + /// public const string TypeId = "BarFeederInterface"; + + /// + /// The lowercase element name ("barFeeder") used when this Interface is emitted in lower-camel-case document formats. + /// public const string NameId = "barFeeder"; - public new const string DescriptionText = "Interface that coordinates the operations between a bar feeder and another piece of equipment. Bar feeder is a piece of equipment that pushes bar stock(i.e., long pieces of material of various shapes) into an associated piece of equipment – most typically a lathe or turning center."; + /// + /// The canonical single-line human-readable description of this Interface; surfaced through . + /// + public new const string DescriptionText = "Interface that coordinates the operations between a bar feeder and another piece of equipment. Bar feeder is a piece of equipment that pushes bar stock (i.e., long pieces of material of various shapes) into an associated piece of equipment - most typically a lathe or turning center."; + + /// + /// Returns the human-readable description for this Interface (). + /// public override string TypeDescription => DescriptionText; + /// + /// The earliest MTConnect Standard version (1.3) in which the BarFeederInterface type is defined. + /// public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// Initializes a new BarFeederInterface, stamping the Component Type with . + /// public BarFeederInterface() { Type = TypeId; } } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-Common/Interfaces/CapabilityType.cs b/libraries/MTConnect.NET-Common/Interfaces/CapabilityType.cs index a5752da6d..e929de5e2 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/CapabilityType.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/CapabilityType.cs @@ -1,14 +1,36 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Interfaces { + /// + /// Classifies the kind of physical or logical capability a Collaborator advertises when negotiating an Interface handshake. + /// public enum CapabilityType { + /// + /// The maximum distance the equipment can extend to access or deliver material. + /// REACH, + + /// + /// The maximum mass the equipment can bear or transfer. + /// LOAD, + + /// + /// The maximum number of discrete items the equipment can hold or stage. + /// CAPACITY, + + /// + /// The maximum bulk volume the equipment can accommodate. + /// VOLUME, + + /// + /// The dimensional or positional tolerance the equipment can guarantee. + /// TOLERANCE } } diff --git a/libraries/MTConnect.NET-Common/Interfaces/ChuckInterface.cs b/libraries/MTConnect.NET-Common/Interfaces/ChuckInterface.cs index 14a34ab1a..2a9dd1062 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/ChuckInterface.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/ChuckInterface.cs @@ -5,22 +5,42 @@ namespace MTConnect.Interfaces { /// /// Interface that coordinates the operations between two pieces of equipment, one of which controls the operation of a chuck. - /// The piece of equipment that is controlling the chuck MUST provide the data item ChuckState as part of the set of information provided. + /// The piece of equipment that is controlling the chuck MUST provide the data item ChuckState as part of the set of information provided. /// - public class ChuckInterface : Interface + public class ChuckInterface : Interface { + /// + /// The fixed Component type identifier ("ChuckInterface") written to the Type attribute and used to recognize this Interface during deserialization. + /// public const string TypeId = "ChuckInterface"; + + /// + /// The lowercase element name ("chuck") used when this Interface is emitted in lower-camel-case document formats. + /// public const string NameId = "chuck"; - public new const string DescriptionText = "Interface that coordinates the operations between two pieces of equipment, one of which controls the operation of a chuck. The piece of equipment that is controlling the chuck MUST provide the data item ChuckState as part of the set of information provided."; + /// + /// The canonical single-line human-readable description of this Interface; surfaced through . + /// + public new const string DescriptionText = "Interface that coordinates the operations between two pieces of equipment, one of which controls the operation of a chuck. The piece of equipment that is controlling the chuck MUST provide the data item ChuckState as part of the set of information provided."; + + /// + /// Returns the human-readable description for this Interface (). + /// public override string TypeDescription => DescriptionText; + /// + /// The earliest MTConnect Standard version (1.3) in which the ChuckInterface type is defined. + /// public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// Initializes a new ChuckInterface, stamping the Component Type with . + /// public ChuckInterface() { Type = TypeId; } } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-Common/Interfaces/CloseChuckDataItem.g.cs b/libraries/MTConnect.NET-Common/Interfaces/CloseChuckDataItem.g.cs index 2d3d27329..b579f3821 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/CloseChuckDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/CloseChuckDataItem.g.cs @@ -10,17 +10,40 @@ namespace MTConnect.Interfaces /// public class CloseChuckDataItem : InterfaceDataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this Interface DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this Interface DataItem. + /// public const string TypeId = "CLOSE_CHUCK"; + + /// + /// The default name assigned to an instance of this Interface DataItem. + /// public const string NameId = "closeChuck"; - + + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Operating state of the service to close a chuck."; + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - + + /// + /// The minimum MTConnect Version that introduced this Interface DataItem. + /// public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// The set of subType values defined for this Interface DataItem by the MTConnect Standard. + /// public new enum SubTypes { /// @@ -35,6 +58,9 @@ public class CloseChuckDataItem : InterfaceDataItem } + /// + /// Initializes a new instance with its category and type set to the defaults for this Interface DataItem. + /// public CloseChuckDataItem() { Category = CategoryId; @@ -42,6 +68,11 @@ public CloseChuckDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this Interface DataItem belongs to. + /// The subType to assign to this Interface DataItem. public CloseChuckDataItem( string parentId, SubTypes subType @@ -55,8 +86,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this Interface DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public new static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -69,6 +106,9 @@ SubTypes subType return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public new static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Interfaces/CloseDoorDataItem.g.cs b/libraries/MTConnect.NET-Common/Interfaces/CloseDoorDataItem.g.cs index 720bc6fd7..9ab0583c9 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/CloseDoorDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/CloseDoorDataItem.g.cs @@ -10,17 +10,40 @@ namespace MTConnect.Interfaces /// public class CloseDoorDataItem : InterfaceDataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this Interface DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this Interface DataItem. + /// public const string TypeId = "CLOSE_DOOR"; + + /// + /// The default name assigned to an instance of this Interface DataItem. + /// public const string NameId = "closeDoor"; - + + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Operating state of the service to close a door."; + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - + + /// + /// The minimum MTConnect Version that introduced this Interface DataItem. + /// public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// The set of subType values defined for this Interface DataItem by the MTConnect Standard. + /// public new enum SubTypes { /// @@ -35,6 +58,9 @@ public class CloseDoorDataItem : InterfaceDataItem } + /// + /// Initializes a new instance with its category and type set to the defaults for this Interface DataItem. + /// public CloseDoorDataItem() { Category = CategoryId; @@ -42,6 +68,11 @@ public CloseDoorDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this Interface DataItem belongs to. + /// The subType to assign to this Interface DataItem. public CloseDoorDataItem( string parentId, SubTypes subType @@ -55,8 +86,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this Interface DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public new static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -69,6 +106,9 @@ SubTypes subType return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public new static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Interfaces/Collaborator.cs b/libraries/MTConnect.NET-Common/Interfaces/Collaborator.cs index a2a8b7eb9..2530aaa4c 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/Collaborator.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/Collaborator.cs @@ -1,16 +1,31 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Interfaces { + /// + /// Describes one participating piece of equipment in an Interface handshake, identifying it and stating whether and with what precedence it must take part. + /// public class Collaborator { + /// + /// The identifier of the collaborating equipment, correlated with the Component or device that fulfils this role in the Interface. + /// public string CollaboratorId { get; set; } + /// + /// The category of equipment (robot, conveyor, CNC, buffer) that this collaborator represents. + /// public CollaboratorType CollaboratorType { get; set; } + /// + /// When true, the handshake can proceed even if this collaborator is absent or does not respond. + /// public bool Optional { get; set; } + /// + /// The relative precedence of this collaborator when more than one is eligible to service the same request. + /// public Priority Priority { get; set; } } } diff --git a/libraries/MTConnect.NET-Common/Interfaces/CollaboratorType.cs b/libraries/MTConnect.NET-Common/Interfaces/CollaboratorType.cs index 1560ce412..91707d654 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/CollaboratorType.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/CollaboratorType.cs @@ -1,13 +1,31 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Interfaces { + /// + /// Enumerates the categories of equipment that can participate as a in an Interface handshake. + /// public enum CollaboratorType { + /// + /// An articulated or gantry robot that loads, unloads, or transfers material. + /// ROBOT, + + /// + /// A conveyor that transports material between stations. + /// CONVEYOR, + + /// + /// A computer numerical control machine tool. + /// CNC, + + /// + /// A buffer or staging area that temporarily holds material between operations. + /// BUFFER } } diff --git a/libraries/MTConnect.NET-Common/Interfaces/DoorInterface.cs b/libraries/MTConnect.NET-Common/Interfaces/DoorInterface.cs index 849fa7cf8..18b22ec80 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/DoorInterface.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/DoorInterface.cs @@ -5,22 +5,42 @@ namespace MTConnect.Interfaces { /// /// Interface that coordinates the operations between two pieces of equipment, one of which controls the operation of a door. - /// The piece of equipment that is controlling the door MUST provide data item DoorState as part of the set of information provided. + /// The piece of equipment that is controlling the door MUST provide data item DoorState as part of the set of information provided. /// - public class DoorInterface : Interface + public class DoorInterface : Interface { + /// + /// The fixed Component type identifier ("DoorInterface") written to the Type attribute and used to recognize this Interface during deserialization. + /// public const string TypeId = "DoorInterface"; + + /// + /// The lowercase element name ("door") used when this Interface is emitted in lower-camel-case document formats. + /// public const string NameId = "door"; - public new const string DescriptionText = "Interface that coordinates the operations between two pieces of equipment, one of which controls the operation of a door. The piece of equipment that is controlling the door MUST provide data item DoorState as part of the set of information provided."; + /// + /// The canonical single-line human-readable description of this Interface; surfaced through . + /// + public new const string DescriptionText = "Interface that coordinates the operations between two pieces of equipment, one of which controls the operation of a door. The piece of equipment that is controlling the door MUST provide data item DoorState as part of the set of information provided."; + + /// + /// Returns the human-readable description for this Interface (). + /// public override string TypeDescription => DescriptionText; + /// + /// The earliest MTConnect Standard version (1.3) in which the DoorInterface type is defined. + /// public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// Initializes a new DoorInterface, stamping the Component Type with . + /// public DoorInterface() { Type = TypeId; } } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-Common/Interfaces/InterfaceDataItem.cs b/libraries/MTConnect.NET-Common/Interfaces/InterfaceDataItem.cs index 535dffa65..09a3e8371 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/InterfaceDataItem.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/InterfaceDataItem.cs @@ -5,8 +5,14 @@ namespace MTConnect.Interfaces { + /// + /// Base class for DataItems that flow across an Interface, distinguishing whether the observation expresses a request for a task or a response to one. + /// public abstract class InterfaceDataItem : DataItem { + /// + /// The direction of an Interface DataItem relative to the handshake it participates in. + /// public enum SubTypes { /// @@ -22,8 +28,15 @@ public enum SubTypes + /// + /// The human-readable description of this DataItem's , resolved from its configured SubType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the human-readable description for the given Interface DataItem subtype, or null if the value is unrecognized. + /// + /// The subtype string (e.g. "REQUEST" or "RESPONSE") to describe. public static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -36,6 +49,10 @@ public static string GetSubTypeDescription(string subType) return null; } + /// + /// Returns the short SubType identifier ("req" or "rsp") emitted in documents for the given subtype, or null if unrecognized. + /// + /// The subtype to map to its document identifier. public static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Interfaces/InterfaceState.cs b/libraries/MTConnect.NET-Common/Interfaces/InterfaceState.cs index 749a71a16..b2007cc77 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/InterfaceState.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/InterfaceState.cs @@ -3,6 +3,9 @@ namespace MTConnect.Interfaces { + /// + /// The operational state of an Interface, controlling whether it participates in request/response handshakes. + /// public enum InterfaceState { /// diff --git a/libraries/MTConnect.NET-Common/Interfaces/InterfaceStateDataItem.g.cs b/libraries/MTConnect.NET-Common/Interfaces/InterfaceStateDataItem.g.cs index 7371df38d..6e46bb423 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/InterfaceStateDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/InterfaceStateDataItem.g.cs @@ -10,17 +10,40 @@ namespace MTConnect.Interfaces /// public class InterfaceStateDataItem : InterfaceDataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this Interface DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this Interface DataItem. + /// public const string TypeId = "INTERFACE_STATE"; + + /// + /// The default name assigned to an instance of this Interface DataItem. + /// public const string NameId = "interfaceState"; - + + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Operational state of an Interface."; - + + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - - public override System.Version MinimumVersion => MTConnectVersions.Version13; + + /// + /// The minimum MTConnect Version that introduced this Interface DataItem. + /// + public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// Initializes a new instance with its category and type set to the defaults for this Interface DataItem. + /// public InterfaceStateDataItem() { Category = CategoryId; @@ -28,6 +51,10 @@ public InterfaceStateDataItem() } + /// + /// Initializes a new instance scoped to the given device. + /// + /// The Id of the device this Interface DataItem belongs to. public InterfaceStateDataItem(string deviceId) { Id = CreateId(deviceId, NameId); @@ -36,4 +63,4 @@ public InterfaceStateDataItem(string deviceId) Name = NameId; } } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-Common/Interfaces/MaterialChangeDataItem.g.cs b/libraries/MTConnect.NET-Common/Interfaces/MaterialChangeDataItem.g.cs index 7d44a00aa..311b0a467 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/MaterialChangeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/MaterialChangeDataItem.g.cs @@ -10,17 +10,40 @@ namespace MTConnect.Interfaces /// public class MaterialChangeDataItem : InterfaceDataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this Interface DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this Interface DataItem. + /// public const string TypeId = "MATERIAL_CHANGE"; + + /// + /// The default name assigned to an instance of this Interface DataItem. + /// public const string NameId = "materialChange"; - + + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Operating state of the service to change the type of material or product being loaded or fed to a piece of equipment."; + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - + + /// + /// The minimum MTConnect Version that introduced this Interface DataItem. + /// public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// The set of subType values defined for this Interface DataItem by the MTConnect Standard. + /// public new enum SubTypes { /// @@ -35,6 +58,9 @@ public class MaterialChangeDataItem : InterfaceDataItem } + /// + /// Initializes a new instance with its category and type set to the defaults for this Interface DataItem. + /// public MaterialChangeDataItem() { Category = CategoryId; @@ -42,6 +68,11 @@ public MaterialChangeDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this Interface DataItem belongs to. + /// The subType to assign to this Interface DataItem. public MaterialChangeDataItem( string parentId, SubTypes subType @@ -55,8 +86,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this Interface DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public new static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -69,6 +106,9 @@ SubTypes subType return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public new static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Interfaces/MaterialFeedDataItem.g.cs b/libraries/MTConnect.NET-Common/Interfaces/MaterialFeedDataItem.g.cs index 82808028b..4d6c980f1 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/MaterialFeedDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/MaterialFeedDataItem.g.cs @@ -10,17 +10,40 @@ namespace MTConnect.Interfaces /// public class MaterialFeedDataItem : InterfaceDataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this Interface DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this Interface DataItem. + /// public const string TypeId = "MATERIAL_FEED"; + + /// + /// The default name assigned to an instance of this Interface DataItem. + /// public const string NameId = "materialFeed"; - + + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Operating state of the service to advance material or feed product to a piece of equipment from a continuous or bulk source."; + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - + + /// + /// The minimum MTConnect Version that introduced this Interface DataItem. + /// public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// The set of subType values defined for this Interface DataItem by the MTConnect Standard. + /// public new enum SubTypes { /// @@ -35,6 +58,9 @@ public class MaterialFeedDataItem : InterfaceDataItem } + /// + /// Initializes a new instance with its category and type set to the defaults for this Interface DataItem. + /// public MaterialFeedDataItem() { Category = CategoryId; @@ -42,6 +68,11 @@ public MaterialFeedDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this Interface DataItem belongs to. + /// The subType to assign to this Interface DataItem. public MaterialFeedDataItem( string parentId, SubTypes subType @@ -55,8 +86,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this Interface DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public new static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -69,6 +106,9 @@ SubTypes subType return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public new static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Interfaces/MaterialHandlerInterface.cs b/libraries/MTConnect.NET-Common/Interfaces/MaterialHandlerInterface.cs index 5be96f4ff..abe1b4308 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/MaterialHandlerInterface.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/MaterialHandlerInterface.cs @@ -4,22 +4,42 @@ namespace MTConnect.Interfaces { /// - /// Interface that coordinates the operations between a piece of equipment and another associated piece of equipment used to automatically handle various types of materials or services associated with the original piece of equipment. + /// Interface that coordinates the operations between a piece of equipment and another associated piece of equipment used to automatically handle various types of materials or services associated with the original piece of equipment. /// - public class MaterialHandlerInterface : Interface + public class MaterialHandlerInterface : Interface { + /// + /// The fixed Component type identifier ("MaterialHandlerInterface") written to the Type attribute and used to recognize this Interface during deserialization. + /// public const string TypeId = "MaterialHandlerInterface"; + + /// + /// The lowercase element name ("materialHandler") used when this Interface is emitted in lower-camel-case document formats. + /// public const string NameId = "materialHandler"; + + /// + /// The canonical single-line human-readable description of this Interface; surfaced through . + /// public new const string DescriptionText = "Interface that coordinates the operations between a piece of equipment and another associated piece of equipment used to automatically handle various types of materials or services associated with the original piece of equipment."; + /// + /// Returns the human-readable description for this Interface (). + /// public override string TypeDescription => DescriptionText; + /// + /// The earliest MTConnect Standard version (1.3) in which the MaterialHandlerInterface type is defined. + /// public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// Initializes a new MaterialHandlerInterface, stamping the Component Type with . + /// public MaterialHandlerInterface() { Type = TypeId; } } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-Common/Interfaces/MaterialLoadDataItem.g.cs b/libraries/MTConnect.NET-Common/Interfaces/MaterialLoadDataItem.g.cs index 0603498b1..2db9ccca4 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/MaterialLoadDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/MaterialLoadDataItem.g.cs @@ -10,17 +10,40 @@ namespace MTConnect.Interfaces /// public class MaterialLoadDataItem : InterfaceDataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this Interface DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this Interface DataItem. + /// public const string TypeId = "MATERIAL_LOAD"; + + /// + /// The default name assigned to an instance of this Interface DataItem. + /// public const string NameId = "materialLoad"; - + + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Operating state of the service to load a piece of material or product."; + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - + + /// + /// The minimum MTConnect Version that introduced this Interface DataItem. + /// public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// The set of subType values defined for this Interface DataItem by the MTConnect Standard. + /// public new enum SubTypes { /// @@ -35,6 +58,9 @@ public class MaterialLoadDataItem : InterfaceDataItem } + /// + /// Initializes a new instance with its category and type set to the defaults for this Interface DataItem. + /// public MaterialLoadDataItem() { Category = CategoryId; @@ -42,6 +68,11 @@ public MaterialLoadDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this Interface DataItem belongs to. + /// The subType to assign to this Interface DataItem. public MaterialLoadDataItem( string parentId, SubTypes subType @@ -55,8 +86,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this Interface DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public new static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -69,6 +106,9 @@ SubTypes subType return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public new static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Interfaces/MaterialRetractDataItem.g.cs b/libraries/MTConnect.NET-Common/Interfaces/MaterialRetractDataItem.g.cs index fc3f5699d..2815e0679 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/MaterialRetractDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/MaterialRetractDataItem.g.cs @@ -10,17 +10,40 @@ namespace MTConnect.Interfaces /// public class MaterialRetractDataItem : InterfaceDataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this Interface DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this Interface DataItem. + /// public const string TypeId = "MATERIAL_RETRACT"; + + /// + /// The default name assigned to an instance of this Interface DataItem. + /// public const string NameId = "materialRetract"; - + + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Operating state of the service to remove or retract material or product."; + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - + + /// + /// The minimum MTConnect Version that introduced this Interface DataItem. + /// public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// The set of subType values defined for this Interface DataItem by the MTConnect Standard. + /// public new enum SubTypes { /// @@ -35,6 +58,9 @@ public class MaterialRetractDataItem : InterfaceDataItem } + /// + /// Initializes a new instance with its category and type set to the defaults for this Interface DataItem. + /// public MaterialRetractDataItem() { Category = CategoryId; @@ -42,6 +68,11 @@ public MaterialRetractDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this Interface DataItem belongs to. + /// The subType to assign to this Interface DataItem. public MaterialRetractDataItem( string parentId, SubTypes subType @@ -55,8 +86,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this Interface DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public new static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -69,6 +106,9 @@ SubTypes subType return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public new static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Interfaces/MaterialUnloadDataItem.g.cs b/libraries/MTConnect.NET-Common/Interfaces/MaterialUnloadDataItem.g.cs index 69e0b9367..b37e3d926 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/MaterialUnloadDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/MaterialUnloadDataItem.g.cs @@ -10,17 +10,40 @@ namespace MTConnect.Interfaces /// public class MaterialUnloadDataItem : InterfaceDataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this Interface DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this Interface DataItem. + /// public const string TypeId = "MATERIAL_UNLOAD"; + + /// + /// The default name assigned to an instance of this Interface DataItem. + /// public const string NameId = "materialUnload"; - + + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Operating state of the service to unload a piece of material or product."; + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - + + /// + /// The minimum MTConnect Version that introduced this Interface DataItem. + /// public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// The set of subType values defined for this Interface DataItem by the MTConnect Standard. + /// public new enum SubTypes { /// @@ -35,6 +58,9 @@ public class MaterialUnloadDataItem : InterfaceDataItem } + /// + /// Initializes a new instance with its category and type set to the defaults for this Interface DataItem. + /// public MaterialUnloadDataItem() { Category = CategoryId; @@ -42,6 +68,11 @@ public MaterialUnloadDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this Interface DataItem belongs to. + /// The subType to assign to this Interface DataItem. public MaterialUnloadDataItem( string parentId, SubTypes subType @@ -55,8 +86,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this Interface DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public new static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -69,6 +106,9 @@ SubTypes subType return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public new static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Interfaces/OpenChuckDataItem.g.cs b/libraries/MTConnect.NET-Common/Interfaces/OpenChuckDataItem.g.cs index 7527290f5..515bf3b2e 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/OpenChuckDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/OpenChuckDataItem.g.cs @@ -10,17 +10,40 @@ namespace MTConnect.Interfaces /// public class OpenChuckDataItem : InterfaceDataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this Interface DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this Interface DataItem. + /// public const string TypeId = "OPEN_CHUCK"; + + /// + /// The default name assigned to an instance of this Interface DataItem. + /// public const string NameId = "openChuck"; - + + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Operating state of the service to open a chuck."; + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - + + /// + /// The minimum MTConnect Version that introduced this Interface DataItem. + /// public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// The set of subType values defined for this Interface DataItem by the MTConnect Standard. + /// public new enum SubTypes { /// @@ -35,6 +58,9 @@ public class OpenChuckDataItem : InterfaceDataItem } + /// + /// Initializes a new instance with its category and type set to the defaults for this Interface DataItem. + /// public OpenChuckDataItem() { Category = CategoryId; @@ -42,6 +68,11 @@ public OpenChuckDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this Interface DataItem belongs to. + /// The subType to assign to this Interface DataItem. public OpenChuckDataItem( string parentId, SubTypes subType @@ -55,8 +86,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this Interface DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public new static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -69,6 +106,9 @@ SubTypes subType return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public new static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Interfaces/OpenDoorDataItem.g.cs b/libraries/MTConnect.NET-Common/Interfaces/OpenDoorDataItem.g.cs index 2103ddbe4..283620d5c 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/OpenDoorDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/OpenDoorDataItem.g.cs @@ -10,17 +10,40 @@ namespace MTConnect.Interfaces /// public class OpenDoorDataItem : InterfaceDataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this Interface DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this Interface DataItem. + /// public const string TypeId = "OPEN_DOOR"; + + /// + /// The default name assigned to an instance of this Interface DataItem. + /// public const string NameId = "openDoor"; - + + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Operating state of the service to open a door."; + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - + + /// + /// The minimum MTConnect Version that introduced this Interface DataItem. + /// public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// The set of subType values defined for this Interface DataItem by the MTConnect Standard. + /// public new enum SubTypes { /// @@ -35,6 +58,9 @@ public class OpenDoorDataItem : InterfaceDataItem } + /// + /// Initializes a new instance with its category and type set to the defaults for this Interface DataItem. + /// public OpenDoorDataItem() { Category = CategoryId; @@ -42,6 +68,11 @@ public OpenDoorDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this Interface DataItem belongs to. + /// The subType to assign to this Interface DataItem. public OpenDoorDataItem( string parentId, SubTypes subType @@ -55,8 +86,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this Interface DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public new static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -69,6 +106,9 @@ SubTypes subType return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public new static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Interfaces/PartChangeDataItem.g.cs b/libraries/MTConnect.NET-Common/Interfaces/PartChangeDataItem.g.cs index 5eddfd8e7..bcb35b228 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/PartChangeDataItem.g.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/PartChangeDataItem.g.cs @@ -10,17 +10,40 @@ namespace MTConnect.Interfaces /// public class PartChangeDataItem : InterfaceDataItem { + /// + /// The MTConnect category (SAMPLE, EVENT, or CONDITION) of this Interface DataItem. + /// public const DataItemCategory CategoryId = DataItemCategory.EVENT; + + /// + /// The MTConnect type value that identifies this Interface DataItem. + /// public const string TypeId = "PART_CHANGE"; + + /// + /// The default name assigned to an instance of this Interface DataItem. + /// public const string NameId = "partChange"; - + + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public new const string DescriptionText = "Operating state of the service to change the part or product associated with a piece of equipment to a different part or product."; + /// + /// The description of this Interface DataItem as defined by the MTConnect Standard. + /// public override string TypeDescription => DescriptionText; - + + /// + /// The minimum MTConnect Version that introduced this Interface DataItem. + /// public override System.Version MinimumVersion => MTConnectVersions.Version13; + /// + /// The set of subType values defined for this Interface DataItem by the MTConnect Standard. + /// public new enum SubTypes { /// @@ -35,6 +58,9 @@ public class PartChangeDataItem : InterfaceDataItem } + /// + /// Initializes a new instance with its category and type set to the defaults for this Interface DataItem. + /// public PartChangeDataItem() { Category = CategoryId; @@ -42,6 +68,11 @@ public PartChangeDataItem() } + /// + /// Initializes a new instance for the given parent with the specified . + /// + /// The Id of the parent element this Interface DataItem belongs to. + /// The subType to assign to this Interface DataItem. public PartChangeDataItem( string parentId, SubTypes subType @@ -55,8 +86,14 @@ SubTypes subType } + /// + /// The MTConnect Standard description of this Interface DataItem's current subType. + /// public override string SubTypeDescription => GetSubTypeDescription(SubType); + /// + /// Returns the MTConnect Standard description for the specified , or null when it is unknown. + /// public new static string GetSubTypeDescription(string subType) { var s = subType.ConvertEnum(); @@ -69,6 +106,9 @@ SubTypes subType return null; } + /// + /// Returns the string identifier for the specified , or null when it is unknown. + /// public new static string GetSubTypeId(SubTypes subType) { switch (subType) diff --git a/libraries/MTConnect.NET-Common/Interfaces/Priority.cs b/libraries/MTConnect.NET-Common/Interfaces/Priority.cs index 116d0ee13..c9b8293ca 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/Priority.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/Priority.cs @@ -1,10 +1,16 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Interfaces { + /// + /// Expresses the relative precedence assigned to a when several are eligible to service the same Interface request. + /// public class Priority { + /// + /// The numeric precedence used to rank this collaborator against others competing to service the same request. + /// public int Value { get; set; } } } diff --git a/libraries/MTConnect.NET-Common/Interfaces/RequestState.cs b/libraries/MTConnect.NET-Common/Interfaces/RequestState.cs index 060ac9ddc..4604a4c39 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/RequestState.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/RequestState.cs @@ -3,6 +3,9 @@ namespace MTConnect.Interfaces { + /// + /// The state of the Requester side of an Interface handshake, tracking its progress from idle through an active service request to completion or failure. + /// public enum RequestState { /// diff --git a/libraries/MTConnect.NET-Common/Interfaces/ResponseState.cs b/libraries/MTConnect.NET-Common/Interfaces/ResponseState.cs index da16dae9e..5417316e7 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/ResponseState.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/ResponseState.cs @@ -3,6 +3,9 @@ namespace MTConnect.Interfaces { + /// + /// The state of the Responder side of an Interface handshake, tracking its progress from idle through accepting and performing a requested service to completion or failure. + /// public enum ResponseState { /// diff --git a/libraries/MTConnect.NET-Common/Interfaces/SubTaskRef.cs b/libraries/MTConnect.NET-Common/Interfaces/SubTaskRef.cs index 92a8303d5..ea3e46891 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/SubTaskRef.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/SubTaskRef.cs @@ -1,16 +1,31 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Interfaces { + /// + /// A reference from a task archetype to one of its constituent subtasks, describing how that subtask is sequenced and grouped relative to its siblings. + /// public class SubTaskRef { + /// + /// When true, this subtask may run concurrently with other subtasks in the same group rather than strictly in . + /// public bool Parallel { get; set; } + /// + /// The name of the group this subtask belongs to, used to cluster subtasks that are sequenced or parallelized together. + /// public string Group { get; set; } + /// + /// The position of this subtask within its group, determining sequential execution order. + /// public int Order { get; set; } + /// + /// When true, the parent task can complete even if this subtask is skipped or not performed. + /// public bool Optional { get; set; } } } diff --git a/libraries/MTConnect.NET-Common/Interfaces/TaskArchetypeAsset.cs b/libraries/MTConnect.NET-Common/Interfaces/TaskArchetypeAsset.cs index 436074bec..d0a5fd5a3 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/TaskArchetypeAsset.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/TaskArchetypeAsset.cs @@ -7,19 +7,38 @@ namespace MTConnect.Interfaces { + /// + /// Asset describing a reusable template for an Interface task: the kind of work, its precedence, and the subtasks it decomposes into. + /// Concrete task instances are derived from an archetype. + /// [XmlRoot("TaskArchetype")] public abstract class TaskArchetypeAsset : Asset { + /// + /// The fixed Asset type identifier ("TaskArchetype") written to the Type attribute and used to recognize this asset during deserialization. + /// public const string TypeId = "TaskArchetype"; + /// + /// The category of work this archetype represents (e.g. tool change, material load/unload, move material). + /// public TaskType TaskType { get; set; } + /// + /// The relative precedence applied when scheduling tasks created from this archetype against other pending tasks. + /// public Priority Priority { get; set; } + /// + /// The ordered set of child task archetypes this task decomposes into. + /// public IEnumerable SubTaskRef { get; set; } + /// + /// Initializes a new TaskArchetypeAsset, stamping the Asset Type with . + /// public TaskArchetypeAsset() { Type = TypeId; diff --git a/libraries/MTConnect.NET-Common/Interfaces/TaskAsset.cs b/libraries/MTConnect.NET-Common/Interfaces/TaskAsset.cs index 9d13cccf1..78437f651 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/TaskAsset.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/TaskAsset.cs @@ -7,25 +7,47 @@ namespace MTConnect.Interfaces { + /// + /// Asset representing a concrete instance of an Interface task, carrying its kind, current lifecycle state, and scheduling precedence. + /// [XmlRoot("Task")] public class TaskAsset : Asset { + /// + /// The fixed Asset type identifier ("Task") written to the Type attribute and used to recognize this asset during deserialization. + /// public const string TypeId = "Task"; + /// + /// The category of work this task performs (e.g. tool change, material load/unload, move material). + /// public TaskType TaskType { get; set; } + /// + /// The current point of this task in its lifecycle (e.g. committing, active, complete, failed). + /// public TaskState State { get; set; } + /// + /// The relative precedence used to schedule this task against other pending tasks. + /// public Priority Priority { get; set; } + /// + /// Initializes a new TaskAsset, stamping the Asset Type with . + /// public TaskAsset() { Type = TypeId; } + /// + /// Filters this asset by MTConnect version: returns the asset when the requested version is 1.3 or later (the version that introduced Task), otherwise null to exclude it. + /// + /// The MTConnect version the response document is being generated for. protected override IAsset OnProcess(Version mtconnectVersion) { if (mtconnectVersion != null && mtconnectVersion >= MTConnectVersions.Version13) diff --git a/libraries/MTConnect.NET-Common/Interfaces/TaskState.cs b/libraries/MTConnect.NET-Common/Interfaces/TaskState.cs index 9f2405eea..9735c396e 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/TaskState.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/TaskState.cs @@ -1,15 +1,41 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Interfaces { + /// + /// The lifecycle state of an Interface as it moves from inactive through preparation and commitment to completion or failure. + /// public enum TaskState { + /// + /// The task has been irrevocably accepted and is being carried out. + /// COMMITTED, + + /// + /// The task is in the process of being committed but the commitment is not yet final. + /// COMMITTING, + + /// + /// The task has finished successfully. + /// COMPLETE, + + /// + /// The task could not be completed because a failure was detected. + /// FAIL, + + /// + /// The task is defined but not currently being prepared or performed. + /// INACTIVE, + + /// + /// The task is being set up in anticipation of being committed. + /// PREPARING } } diff --git a/libraries/MTConnect.NET-Common/Interfaces/TaskType.cs b/libraries/MTConnect.NET-Common/Interfaces/TaskType.cs index a0411124d..178779489 100644 --- a/libraries/MTConnect.NET-Common/Interfaces/TaskType.cs +++ b/libraries/MTConnect.NET-Common/Interfaces/TaskType.cs @@ -1,12 +1,26 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Interfaces { + /// + /// Classifies the kind of work an Interface task or task archetype performs. + /// public enum TaskType { + /// + /// Remove finished or in-process material from a piece of equipment. + /// MATERIAL_UNLOAD, + + /// + /// Transport material between pieces of equipment or staging locations. + /// MOVE_MATERIAL, + + /// + /// Exchange the active tool on a piece of equipment. + /// TOOL_CHANGE } } diff --git a/libraries/MTConnect.NET-Common/Logging/MTConnectLogEventHandler.cs b/libraries/MTConnect.NET-Common/Logging/MTConnectLogEventHandler.cs index a049a267c..848fbdac4 100644 --- a/libraries/MTConnect.NET-Common/Logging/MTConnectLogEventHandler.cs +++ b/libraries/MTConnect.NET-Common/Logging/MTConnectLogEventHandler.cs @@ -3,5 +3,12 @@ namespace MTConnect.Logging { + /// + /// Callback raised when an MTConnect component emits a log entry, carrying the severity, message text, and an optional log channel identifier. + /// + /// The component that produced the log entry. + /// The severity of the entry. + /// The log message text. + /// An optional identifier for the originating log channel or category. public delegate void MTConnectLogEventHandler(object sender, MTConnectLogLevel logLevel, string message, string logId = null); } diff --git a/libraries/MTConnect.NET-Common/Logging/MTConnectLogLevel.cs b/libraries/MTConnect.NET-Common/Logging/MTConnectLogLevel.cs index 9dcddac3e..54fc03b3a 100644 --- a/libraries/MTConnect.NET-Common/Logging/MTConnectLogLevel.cs +++ b/libraries/MTConnect.NET-Common/Logging/MTConnectLogLevel.cs @@ -1,15 +1,41 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Logging { + /// + /// Severity of a log entry emitted by an MTConnect component, ordered from most to least severe. + /// public enum MTConnectLogLevel { + /// + /// An unrecoverable error that typically forces the component to stop. + /// Fatal, + + /// + /// A failure that prevents an operation from completing but does not stop the component. + /// Error, + + /// + /// An abnormal condition that does not prevent operation but warrants attention. + /// Warning, + + /// + /// A normal operational message describing significant activity. + /// Information, + + /// + /// Diagnostic detail useful while investigating behavior. + /// Debug, + + /// + /// The most verbose detail, tracing fine-grained execution flow. + /// Trace } } diff --git a/libraries/MTConnect.NET-Common/MTConnectEntityType.cs b/libraries/MTConnect.NET-Common/MTConnectEntityType.cs index 4246f0775..240bafe0e 100644 --- a/libraries/MTConnect.NET-Common/MTConnectEntityType.cs +++ b/libraries/MTConnect.NET-Common/MTConnectEntityType.cs @@ -1,15 +1,41 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect { + /// + /// The top-level kinds of entity in the MTConnect information model, used to classify an entity without inspecting its concrete type. + /// public enum MTConnectEntityType { + /// + /// A piece of equipment described by the device model. + /// Device, + + /// + /// A functional or physical part of a device. + /// Component, + + /// + /// A lower-level building block contained within a component. + /// Composition, + + /// + /// A definition of an item of streaming data produced by a device. + /// DataItem, + + /// + /// A reported value of a DataItem at a point in time. + /// Observation, + + /// + /// A piece of equipment-related information that is not streaming data, such as a cutting tool or file. + /// Asset } } diff --git a/libraries/MTConnect.NET-Common/MTConnectTimeZone.cs b/libraries/MTConnect.NET-Common/MTConnectTimeZone.cs index c1ac626cc..5fd657a56 100644 --- a/libraries/MTConnect.NET-Common/MTConnectTimeZone.cs +++ b/libraries/MTConnect.NET-Common/MTConnectTimeZone.cs @@ -8,17 +8,37 @@ namespace MTConnect { + /// + /// A named time zone identified by an abbreviation and a UTC offset, with helpers to resolve it to a system and to express UTC timestamps in that zone. + /// public class MTConnectTimeZone { private readonly static IEnumerable _timeZones = Init(); private readonly static string _offsetParsePattern = "^(?:UTC)?\\s?([-+])([0-9]{1,2})(?::([0-9]{2}))?$"; + /// + /// The short abbreviation for the zone (e.g. "CST"). + /// public string Abbreviation { get; set; } + + /// + /// The human-readable name of the zone (e.g. "Central Standard Time"). + /// public string Name { get; set; } + + /// + /// The UTC offset in the textual "UTC+H:MM" form. + /// public string Offset { get; set; } + /// + /// Initializes a time zone from its abbreviation, name, and UTC offset. + /// + /// The short abbreviation. + /// The human-readable name. + /// The UTC offset in "UTC+H:MM" form. public MTConnectTimeZone(string abbreviation, string name, string offset) { Abbreviation = abbreviation; @@ -26,11 +46,18 @@ public MTConnectTimeZone(string abbreviation, string name, string offset) Offset = offset; } + /// + /// Converts a UTC timestamp into a expressed in this zone, resolving to the best-matching system time zone. + /// + /// The UTC instant to convert. public DateTimeOffset ToTimestamp(DateTime utcTimestamp) { return GetTimestamp(utcTimestamp, ToTimeZoneInfo()); } + /// + /// Resolves this zone to the system whose base UTC offset matches, breaking ties by the closest standard-name match; returns null when no match is found. + /// public TimeZoneInfo ToTimeZoneInfo() { try @@ -50,6 +77,11 @@ public TimeZoneInfo ToTimeZoneInfo() return null; } + /// + /// Converts a UTC timestamp into a in the given time zone, normalizing the kind to Unspecified so the offset comes from the zone rather than local machine settings; falls back to the raw UTC value when no zone is supplied. + /// + /// The UTC instant to convert. + /// The target time zone, or null to use UTC. public static DateTimeOffset GetTimestamp(DateTime utcTimestamp, TimeZoneInfo timeZoneInfo) { if (timeZoneInfo != null) @@ -68,6 +100,10 @@ public static DateTimeOffset GetTimestamp(DateTime utcTimestamp, TimeZoneInfo ti } + /// + /// Looks up a known time zone by abbreviation first, then by an equivalent UTC offset; returns null when the input is empty or matches nothing. + /// + /// A zone abbreviation or a UTC offset string. public static MTConnectTimeZone Get(string input) { if (!string.IsNullOrEmpty(input)) diff --git a/libraries/MTConnect.NET-Common/MTConnectVersions.cs b/libraries/MTConnect.NET-Common/MTConnectVersions.cs index 3d069f7ff..4fc7d20aa 100644 --- a/libraries/MTConnect.NET-Common/MTConnectVersions.cs +++ b/libraries/MTConnect.NET-Common/MTConnectVersions.cs @@ -5,6 +5,9 @@ namespace MTConnect { + /// + /// Canonical instances for every MTConnect Standard release the library understands, used throughout for version gating of entities, attributes, and document shaping. + /// public static class MTConnectVersions { /// @@ -14,20 +17,49 @@ public static class MTConnectVersions /// public static Version Max => Version27; + /// MTConnect Standard v1.0. public static readonly Version Version10 = new Version(1, 0); + + /// MTConnect Standard v1.1. public static readonly Version Version11 = new Version(1, 1); + + /// MTConnect Standard v1.2. public static readonly Version Version12 = new Version(1, 2); + + /// MTConnect Standard v1.3. public static readonly Version Version13 = new Version(1, 3); + + /// MTConnect Standard v1.4. public static readonly Version Version14 = new Version(1, 4); + + /// MTConnect Standard v1.5. public static readonly Version Version15 = new Version(1, 5); + + /// MTConnect Standard v1.6. public static readonly Version Version16 = new Version(1, 6); + + /// MTConnect Standard v1.7. public static readonly Version Version17 = new Version(1, 7); + + /// MTConnect Standard v1.8. public static readonly Version Version18 = new Version(1, 8); + + /// MTConnect Standard v2.0. public static readonly Version Version20 = new Version(2, 0); + + /// MTConnect Standard v2.1. public static readonly Version Version21 = new Version(2, 1); + + /// MTConnect Standard v2.2 (introduces the asset Hash). public static readonly Version Version22 = new Version(2, 2); + + /// MTConnect Standard v2.3. public static readonly Version Version23 = new Version(2, 3); + + /// MTConnect Standard v2.4. public static readonly Version Version24 = new Version(2, 4); + + /// MTConnect Standard v2.5. public static readonly Version Version25 = new Version(2, 5); /// diff --git a/libraries/MTConnect.NET-Common/Millimeter3D.cs b/libraries/MTConnect.NET-Common/Millimeter3D.cs index 73ae94227..71cdc4b71 100644 --- a/libraries/MTConnect.NET-Common/Millimeter3D.cs +++ b/libraries/MTConnect.NET-Common/Millimeter3D.cs @@ -5,18 +5,36 @@ namespace MTConnect { + /// + /// A three-dimensional displacement expressed in millimetres, serialized as the MTConnect space-separated "X Y Z" string form. + /// public class Millimeter3D { private static readonly Regex _regex = new Regex(@"([0-9\.]*) ([0-9\.]*) ([0-9\.]*)"); + /// + /// The X displacement in millimetres. + /// public double X { get; set; } + /// + /// The Y displacement in millimetres. + /// public double Y { get; set; } + /// + /// The Z displacement in millimetres. + /// public double Z { get; set; } + /// + /// Initializes a millimetre displacement from its three components. + /// + /// The X displacement in millimetres. + /// The Y displacement in millimetres. + /// The Z displacement in millimetres. public Millimeter3D(double x, double y, double z) { X = x; @@ -24,11 +42,18 @@ public Millimeter3D(double x, double y, double z) Z = z; } + /// + /// Renders the displacement in the MTConnect space-separated "X Y Z" form. + /// public override string ToString() { return $"{X} {Y} {Z}"; } + /// + /// Parses a space-separated "X Y Z" string into a millimetre displacement; returns null when the input is empty or does not match the expected form. + /// + /// The space-separated component triple. public static Millimeter3D FromString(string input) { if (!string.IsNullOrEmpty(input)) diff --git a/libraries/MTConnect.NET-Common/Observations/ConditionLevelDescriptions.cs b/libraries/MTConnect.NET-Common/Observations/ConditionLevelDescriptions.cs index 6ac49caf4..0ad385917 100644 --- a/libraries/MTConnect.NET-Common/Observations/ConditionLevelDescriptions.cs +++ b/libraries/MTConnect.NET-Common/Observations/ConditionLevelDescriptions.cs @@ -29,6 +29,11 @@ public static class ConditionLevelDescriptions public const string FAULT = "The item has failed and intervention is required to return to a Normal condition. Transition to a Normal condition indicates that the Fault condition has been cleared. A Fault condition is something that always needs to be acknowledged before operation can continue."; + /// + /// Returns the descriptive text for the given Condition level. + /// + /// The Condition level to describe. + /// The description text, or an empty string for an unrecognized level. public static string Get(ConditionLevel level) { switch (level) diff --git a/libraries/MTConnect.NET-Common/Observations/ConditionObservation.cs b/libraries/MTConnect.NET-Common/Observations/ConditionObservation.cs index d93b7cdd1..7872e4375 100644 --- a/libraries/MTConnect.NET-Common/Observations/ConditionObservation.cs +++ b/libraries/MTConnect.NET-Common/Observations/ConditionObservation.cs @@ -88,6 +88,9 @@ public string Message public override bool IsUnavailable => GetValue(ValueKeys.Level) == Unavailable; + /// + /// Initializes a new Condition Observation with the Condition category and VALUE representation. + /// public ConditionObservation() { _category = DataItemCategory.CONDITION; @@ -95,6 +98,11 @@ public ConditionObservation() } + /// + /// Creates a Condition Observation for the given DataItem, copying its identifying metadata. + /// + /// The DataItem the Observation is created for. + /// The Condition Observation, or null when is null. public new static ConditionObservation Create(IDataItem dataItem) { if (dataItem != null) @@ -113,6 +121,11 @@ public ConditionObservation() return null; } + /// + /// Creates a Condition Observation from an existing Observation, copying its metadata and values. + /// + /// The source Observation to copy. + /// The Condition Observation, or null when is null. public static ConditionObservation Create(IObservation observation) { if (observation != null) @@ -136,6 +149,12 @@ public static ConditionObservation Create(IObservation observation) } + /// + /// Creates the Condition Observation subclass matching the given type and representation. + /// + /// The DataItem Type identifier. + /// The DataItem representation. + /// A type-specific Condition Observation, or a base ConditionObservation when the type is not recognized. public static ConditionObservation Create(string type, DataItemRepresentation representation) { if (!string.IsNullOrEmpty(type)) diff --git a/libraries/MTConnect.NET-Common/Observations/ConditionQualifierDescriptions.cs b/libraries/MTConnect.NET-Common/Observations/ConditionQualifierDescriptions.cs index 522c48c65..d51ebd26b 100644 --- a/libraries/MTConnect.NET-Common/Observations/ConditionQualifierDescriptions.cs +++ b/libraries/MTConnect.NET-Common/Observations/ConditionQualifierDescriptions.cs @@ -19,6 +19,11 @@ public static class ConditionQualifierDescriptions public const string HIGH = "A measured value that is greater than the expected value for the process variable"; + /// + /// Returns the descriptive text for the given Condition qualifier. + /// + /// The Condition qualifier to describe. + /// The description text, or an empty string for an unrecognized qualifier. public static string Get(ConditionQualifier qualifier) { switch (qualifier) diff --git a/libraries/MTConnect.NET-Common/Observations/DataSetEntry.cs b/libraries/MTConnect.NET-Common/Observations/DataSetEntry.cs index 23578a574..6d5806dbf 100644 --- a/libraries/MTConnect.NET-Common/Observations/DataSetEntry.cs +++ b/libraries/MTConnect.NET-Common/Observations/DataSetEntry.cs @@ -13,6 +13,9 @@ public class DataSetEntry : IDataSetEntry /// public string Key { get; set; } + /// + /// An optional human-readable description of the entry's . + /// public string KeyDescription { get; set; } /// @@ -26,14 +29,27 @@ public class DataSetEntry : IDataSetEntry public string Value { get; set; } + /// + /// Initializes a new, empty Data Set entry. + /// public DataSetEntry() { } + /// + /// Initializes a new Data Set entry with the given key and value. + /// + /// The unique key for the entry. + /// The entry's value; stringified when stored. public DataSetEntry(string key, object value) { Key = key; Value = value?.ToString(); } + /// + /// Initializes a new Data Set entry that marks a key as added or removed. + /// + /// The unique key for the entry. + /// Whether the key was removed from the set. public DataSetEntry(string key, bool removed) { Key = key; diff --git a/libraries/MTConnect.NET-Common/Observations/DataSetObservation.cs b/libraries/MTConnect.NET-Common/Observations/DataSetObservation.cs index 08b238d6f..863a95ce6 100644 --- a/libraries/MTConnect.NET-Common/Observations/DataSetObservation.cs +++ b/libraries/MTConnect.NET-Common/Observations/DataSetObservation.cs @@ -11,9 +11,17 @@ namespace MTConnect.Observations /// public static class DataSetObservation { + /// + /// The sentinel value stored for a Data Set key to mark that the key was removed from the set. + /// public const string EntryRemovedValue = "[!ENTRY_REMOVED!]"; + /// + /// Extracts the Data Set entries from a flat collection of Observation values. + /// + /// The Observation values to decode. + /// The decoded entries ordered by key, with removed keys flagged. public static IEnumerable GetEntries(IEnumerable values) { var entries = new List(); @@ -38,6 +46,11 @@ public static IEnumerable GetEntries(IEnumerable + /// Encodes a set of Data Set entries into the flat Observation values that represent them. + /// + /// The Data Set entries to encode. + /// The Observation values, with removed entries encoded using the removal sentinel. public static IEnumerable SetEntries(IEnumerable entries) { if (!entries.IsNullOrEmpty()) diff --git a/libraries/MTConnect.NET-Common/Observations/EventDataSetObservation.cs b/libraries/MTConnect.NET-Common/Observations/EventDataSetObservation.cs index b0eed3c6b..43f34f279 100644 --- a/libraries/MTConnect.NET-Common/Observations/EventDataSetObservation.cs +++ b/libraries/MTConnect.NET-Common/Observations/EventDataSetObservation.cs @@ -32,12 +32,19 @@ public IEnumerable Entries } + /// + /// Initializes a new Event Observation that reports a DATA_SET representation. + /// public EventDataSetObservation() : base() { _representation = Devices.DataItemRepresentation.DATA_SET; } + /// + /// Invalidates the cached Data Set entries so they are rebuilt the next time they are read. + /// + /// The value that was added. protected override void OnValueAdded(ObservationValue observationValue) { _entries = null; diff --git a/libraries/MTConnect.NET-Common/Observations/EventObservation.cs b/libraries/MTConnect.NET-Common/Observations/EventObservation.cs index c5be35254..faf5faa5a 100644 --- a/libraries/MTConnect.NET-Common/Observations/EventObservation.cs +++ b/libraries/MTConnect.NET-Common/Observations/EventObservation.cs @@ -28,12 +28,20 @@ public ResetTriggered ResetTriggered } + /// + /// Initializes a new Event Observation with the Event category. + /// public EventObservation() { _category = DataItemCategory.EVENT; } + /// + /// Creates an Event Observation for the given DataItem, copying its identifying metadata. + /// + /// The DataItem the Observation is created for. + /// The Event Observation, or null when is null. public new static EventObservation Create(IDataItem dataItem) { if (dataItem != null) @@ -52,6 +60,11 @@ public EventObservation() return null; } + /// + /// Creates an Event Observation from an existing Observation, copying its metadata and values. + /// + /// The source Observation to copy. + /// The Event Observation, or null when is null. public static EventObservation Create(IObservation observation) { if (observation != null) @@ -75,6 +88,12 @@ public static EventObservation Create(IObservation observation) } + /// + /// Creates the Event Observation subclass matching the given type and representation. + /// + /// The DataItem Type identifier. + /// The DataItem representation. + /// A type-specific Event Observation, or a base EventObservation when the type is not recognized. public static EventObservation Create(string type, DataItemRepresentation representation) { if (!string.IsNullOrEmpty(type)) diff --git a/libraries/MTConnect.NET-Common/Observations/EventTableObservation.cs b/libraries/MTConnect.NET-Common/Observations/EventTableObservation.cs index 600b747d7..fe939206b 100644 --- a/libraries/MTConnect.NET-Common/Observations/EventTableObservation.cs +++ b/libraries/MTConnect.NET-Common/Observations/EventTableObservation.cs @@ -32,12 +32,19 @@ public IEnumerable Entries } + /// + /// Initializes a new Event Observation that reports a TABLE representation. + /// public EventTableObservation() : base() { _representation = Devices.DataItemRepresentation.TABLE; } + /// + /// Invalidates the cached Table entries so they are rebuilt the next time they are read. + /// + /// The value that was added. protected override void OnValueAdded(ObservationValue observationValue) { _entries = null; diff --git a/libraries/MTConnect.NET-Common/Observations/EventValueObservation.cs b/libraries/MTConnect.NET-Common/Observations/EventValueObservation.cs index 896938c7e..011ee0ffe 100644 --- a/libraries/MTConnect.NET-Common/Observations/EventValueObservation.cs +++ b/libraries/MTConnect.NET-Common/Observations/EventValueObservation.cs @@ -18,6 +18,9 @@ public string Result } + /// + /// Initializes a new Event Observation that reports a single VALUE representation. + /// public EventValueObservation() : base() { _representation = Devices.DataItemRepresentation.VALUE; diff --git a/libraries/MTConnect.NET-Common/Observations/Events/ActuatorStateDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/ActuatorStateDescriptions.g.cs index 0dca6d000..8d0594c55 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/ActuatorStateDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/ActuatorStateDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class ActuatorStateDescriptions { /// @@ -16,6 +19,9 @@ public static class ActuatorStateDescriptions public const string INACTIVE = "Actuator is not operating."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(ActuatorState value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/AvailabilityDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/AvailabilityDescriptions.g.cs index 44fe611ec..5c193934d 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/AvailabilityDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/AvailabilityDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class AvailabilityDescriptions { /// @@ -16,6 +19,9 @@ public static class AvailabilityDescriptions public const string UNAVAILABLE = "Data source is either inactive or not capable of providing data."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(Availability value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/AxisCouplingDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/AxisCouplingDescriptions.g.cs index 9eb36aaa5..5e1724ccb 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/AxisCouplingDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/AxisCouplingDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class AxisCouplingDescriptions { /// @@ -26,6 +29,9 @@ public static class AxisCouplingDescriptions public const string SLAVE = "Axis is a slave to the CoupledAxes."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(AxisCoupling value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/AxisInterlockDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/AxisInterlockDescriptions.g.cs index c4cd1a207..71515617f 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/AxisInterlockDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/AxisInterlockDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class AxisInterlockDescriptions { /// @@ -16,6 +19,9 @@ public static class AxisInterlockDescriptions public const string INACTIVE = "Axis lockout function has not been activated, the axis may be powered, and the axis is capable of being controlled by another component."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(AxisInterlock value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/AxisStateDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/AxisStateDescriptions.g.cs index 7113a6b93..a311669d9 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/AxisStateDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/AxisStateDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class AxisStateDescriptions { /// @@ -26,6 +29,9 @@ public static class AxisStateDescriptions public const string STOPPED = "Axis is stopped."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(AxisState value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/BatteryStateDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/BatteryStateDescriptions.g.cs index c0caed6a0..195cc0eda 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/BatteryStateDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/BatteryStateDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class BatteryStateDescriptions { /// @@ -26,6 +29,9 @@ public static class BatteryStateDescriptions public const string DISCHARGED = "Component is at it's minimum charge level."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(BatteryState value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/BindingStateDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/BindingStateDescriptions.g.cs index e4e31d094..46e52c481 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/BindingStateDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/BindingStateDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class BindingStateDescriptions { /// @@ -21,6 +24,9 @@ public static class BindingStateDescriptions public const string COMMITTED = "State when a collaborator has successfully bound itself to a task"; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(BindingState value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/CharacteristicStatusDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/CharacteristicStatusDescriptions.g.cs index 886960ec7..d9e527eea 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/CharacteristicStatusDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/CharacteristicStatusDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class CharacteristicStatusDescriptions { /// @@ -46,6 +49,9 @@ public static class CharacteristicStatusDescriptions public const string UNDEFINED = "Status of measurement cannot be determined."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(CharacteristicStatus value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/ChuckInterlockDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/ChuckInterlockDescriptions.g.cs index 358337bbf..26aa561f1 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/ChuckInterlockDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/ChuckInterlockDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class ChuckInterlockDescriptions { /// @@ -16,6 +19,9 @@ public static class ChuckInterlockDescriptions public const string INACTIVE = "Chuck can be unclamped."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(ChuckInterlock value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/ChuckStateDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/ChuckStateDescriptions.g.cs index 4bfc59ce7..1a2b9adf6 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/ChuckStateDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/ChuckStateDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class ChuckStateDescriptions { /// @@ -21,6 +24,9 @@ public static class ChuckStateDescriptions public const string UNLATCHED = "Chuck is not closed to the point of a positive confirmation and not open to the point of a positive confirmation. It is in an intermediate position."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(ChuckState value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateAction.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateAction.g.cs index 99dafa7c5..b46c06519 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateAction.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateAction.g.cs @@ -1,10 +1,10 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2024 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Observations.Events { /// - /// + /// CompositionStateAction controlled vocabulary as defined by the MTConnect Standard. /// public enum CompositionStateAction { diff --git a/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateActionDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateActionDescriptions.g.cs index bc5991bb1..231d9b2e5 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateActionDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateActionDescriptions.g.cs @@ -1,8 +1,11 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2024 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class CompositionStateActionDescriptions { /// @@ -16,6 +19,9 @@ public static class CompositionStateActionDescriptions public const string INACTIVE = "Composition is not operating."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(CompositionStateAction value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateLateral.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateLateral.g.cs index 102e3d8a0..74ccb7810 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateLateral.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateLateral.g.cs @@ -1,22 +1,22 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2024 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Observations.Events { /// - /// + /// CompositionStateLateral controlled vocabulary as defined by the MTConnect Standard. /// public enum CompositionStateLateral { /// - /// Position of the Composition is oriented to the right to the point of a positive confirmation. + /// Position of the Composition is oriented to the left to the point of a positive confirmation. /// - RIGHT, + LEFT, /// - /// Position of the Composition is oriented to the left to the point of a positive confirmation. + /// Position of the Composition is oriented to the right to the point of a positive confirmation. /// - LEFT, + RIGHT, /// /// Position of the Composition is not oriented to the right to the point of a positive confirmation and is not oriented to the left to the point of a positive confirmation. It is in an intermediate position. diff --git a/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateLateralDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateLateralDescriptions.g.cs index 366f1d021..67ca10719 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateLateralDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateLateralDescriptions.g.cs @@ -1,19 +1,22 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2024 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class CompositionStateLateralDescriptions { /// - /// Position of the Composition is oriented to the right to the point of a positive confirmation. + /// Position of the Composition is oriented to the left to the point of a positive confirmation. /// - public const string RIGHT = "Position of the Composition is oriented to the right to the point of a positive confirmation."; + public const string LEFT = "Position of the Composition is oriented to the left to the point of a positive confirmation."; /// - /// Position of the Composition is oriented to the left to the point of a positive confirmation. + /// Position of the Composition is oriented to the right to the point of a positive confirmation. /// - public const string LEFT = "Position of the Composition is oriented to the left to the point of a positive confirmation."; + public const string RIGHT = "Position of the Composition is oriented to the right to the point of a positive confirmation."; /// /// Position of the Composition is not oriented to the right to the point of a positive confirmation and is not oriented to the left to the point of a positive confirmation. It is in an intermediate position. @@ -21,12 +24,15 @@ public static class CompositionStateLateralDescriptions public const string TRANSITIONING = "Position of the Composition is not oriented to the right to the point of a positive confirmation and is not oriented to the left to the point of a positive confirmation. It is in an intermediate position."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(CompositionStateLateral value) { switch (value) { - case CompositionStateLateral.RIGHT: return "Position of the Composition is oriented to the right to the point of a positive confirmation."; case CompositionStateLateral.LEFT: return "Position of the Composition is oriented to the left to the point of a positive confirmation."; + case CompositionStateLateral.RIGHT: return "Position of the Composition is oriented to the right to the point of a positive confirmation."; case CompositionStateLateral.TRANSITIONING: return "Position of the Composition is not oriented to the right to the point of a positive confirmation and is not oriented to the left to the point of a positive confirmation. It is in an intermediate position."; } diff --git a/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateMotion.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateMotion.g.cs index a436e4848..7267f6ecb 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateMotion.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateMotion.g.cs @@ -1,26 +1,26 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2024 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Observations.Events { /// - /// + /// CompositionStateMotion controlled vocabulary as defined by the MTConnect Standard. /// public enum CompositionStateMotion { /// - /// Position of the Composition is open to the point of a positive confirmation. + /// Position of the Composition is closed to the point of a positive confirmation. /// - OPEN, + CLOSED, /// - /// Position of the Composition is not open to thepoint of a positive confirmation and is not closed to the point of a positive confirmation. It is in an intermediate position. + /// Position of the Composition is open to the point of a positive confirmation. /// - UNLATCHED, + OPEN, /// - /// Position of the Composition is closed to the point of a positive confirmation. + /// Position of the Composition is not open to thepoint of a positive confirmation and is not closed to the point of a positive confirmation. It is in an intermediate position. /// - CLOSED + UNLATCHED } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateMotionDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateMotionDescriptions.g.cs index 9c4d9b488..a7812bb5b 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateMotionDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateMotionDescriptions.g.cs @@ -1,10 +1,18 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2024 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class CompositionStateMotionDescriptions { + /// + /// Position of the Composition is closed to the point of a positive confirmation. + /// + public const string CLOSED = "Position of the Composition is closed to the point of a positive confirmation."; + /// /// Position of the Composition is open to the point of a positive confirmation. /// @@ -14,20 +22,18 @@ public static class CompositionStateMotionDescriptions /// Position of the Composition is not open to thepoint of a positive confirmation and is not closed to the point of a positive confirmation. It is in an intermediate position. /// public const string UNLATCHED = "Position of the Composition is not open to thepoint of a positive confirmation and is not closed to the point of a positive confirmation. It is in an intermediate position."; - - /// - /// Position of the Composition is closed to the point of a positive confirmation. - /// - public const string CLOSED = "Position of the Composition is closed to the point of a positive confirmation."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(CompositionStateMotion value) { switch (value) { + case CompositionStateMotion.CLOSED: return "Position of the Composition is closed to the point of a positive confirmation."; case CompositionStateMotion.OPEN: return "Position of the Composition is open to the point of a positive confirmation."; case CompositionStateMotion.UNLATCHED: return "Position of the Composition is not open to thepoint of a positive confirmation and is not closed to the point of a positive confirmation. It is in an intermediate position."; - case CompositionStateMotion.CLOSED: return "Position of the Composition is closed to the point of a positive confirmation."; } return null; diff --git a/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateSwitched.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateSwitched.g.cs index 43e4c84c1..619a3a9ef 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateSwitched.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateSwitched.g.cs @@ -1,21 +1,21 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2024 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Observations.Events { /// - /// + /// CompositionStateSwitched controlled vocabulary as defined by the MTConnect Standard. /// public enum CompositionStateSwitched { /// - /// Activation state of the Composition is in an `ON` condition, it is operating, or it is powered. + /// Activation state of the Composition is in an `OFF` condition, it is not operating, or it is not powered. /// - ON, + OFF, /// - /// Activation state of the Composition is in an `OFF` condition, it is not operating, or it is not powered. + /// Activation state of the Composition is in an `ON` condition, it is operating, or it is powered. /// - OFF + ON } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateSwitchedDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateSwitchedDescriptions.g.cs index becc6eca1..ba2423a1b 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateSwitchedDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateSwitchedDescriptions.g.cs @@ -1,27 +1,33 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2024 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class CompositionStateSwitchedDescriptions { /// - /// Activation state of the Composition is in an `ON` condition, it is operating, or it is powered. + /// Activation state of the Composition is in an `OFF` condition, it is not operating, or it is not powered. /// - public const string ON = "Activation state of the Composition is in an `ON` condition, it is operating, or it is powered."; + public const string OFF = "Activation state of the Composition is in an `OFF` condition, it is not operating, or it is not powered."; /// - /// Activation state of the Composition is in an `OFF` condition, it is not operating, or it is not powered. + /// Activation state of the Composition is in an `ON` condition, it is operating, or it is powered. /// - public const string OFF = "Activation state of the Composition is in an `OFF` condition, it is not operating, or it is not powered."; + public const string ON = "Activation state of the Composition is in an `ON` condition, it is operating, or it is powered."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(CompositionStateSwitched value) { switch (value) { - case CompositionStateSwitched.ON: return "Activation state of the Composition is in an `ON` condition, it is operating, or it is powered."; case CompositionStateSwitched.OFF: return "Activation state of the Composition is in an `OFF` condition, it is not operating, or it is not powered."; + case CompositionStateSwitched.ON: return "Activation state of the Composition is in an `ON` condition, it is operating, or it is powered."; } return null; diff --git a/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateVertical.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateVertical.g.cs index 4d206f926..b3a00d8ee 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateVertical.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateVertical.g.cs @@ -1,18 +1,13 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2024 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Observations.Events { /// - /// + /// CompositionStateVertical controlled vocabulary as defined by the MTConnect Standard. /// public enum CompositionStateVertical { - /// - /// Position of the Composition element is oriented in an upward direction to the point of a positive confirmation. - /// - UP, - /// /// Position of the Composition element is oriented in a downward direction to the point of a positive confirmation. /// @@ -21,6 +16,11 @@ public enum CompositionStateVertical /// /// Position of the Composition element is not oriented in an upward direction to the point of a positive confirmation and is not oriented in a downward direction to the point of a positive confirmation. It is in an intermediate position. /// - TRANSITIONING + TRANSITIONING, + + /// + /// Position of the Composition element is oriented in an upward direction to the point of a positive confirmation. + /// + UP } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateVerticalDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateVerticalDescriptions.g.cs index 5bb51ad77..76fef21ac 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateVerticalDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/CompositionStateVerticalDescriptions.g.cs @@ -1,15 +1,13 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2024 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class CompositionStateVerticalDescriptions { - /// - /// Position of the Composition element is oriented in an upward direction to the point of a positive confirmation. - /// - public const string UP = "Position of the Composition element is oriented in an upward direction to the point of a positive confirmation."; - /// /// Position of the Composition element is oriented in a downward direction to the point of a positive confirmation. /// @@ -19,15 +17,23 @@ public static class CompositionStateVerticalDescriptions /// Position of the Composition element is not oriented in an upward direction to the point of a positive confirmation and is not oriented in a downward direction to the point of a positive confirmation. It is in an intermediate position. /// public const string TRANSITIONING = "Position of the Composition element is not oriented in an upward direction to the point of a positive confirmation and is not oriented in a downward direction to the point of a positive confirmation. It is in an intermediate position."; + + /// + /// Position of the Composition element is oriented in an upward direction to the point of a positive confirmation. + /// + public const string UP = "Position of the Composition element is oriented in an upward direction to the point of a positive confirmation."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(CompositionStateVertical value) { switch (value) { - case CompositionStateVertical.UP: return "Position of the Composition element is oriented in an upward direction to the point of a positive confirmation."; case CompositionStateVertical.DOWN: return "Position of the Composition element is oriented in a downward direction to the point of a positive confirmation."; case CompositionStateVertical.TRANSITIONING: return "Position of the Composition element is not oriented in an upward direction to the point of a positive confirmation and is not oriented in a downward direction to the point of a positive confirmation. It is in an intermediate position."; + case CompositionStateVertical.UP: return "Position of the Composition element is oriented in an upward direction to the point of a positive confirmation."; } return null; diff --git a/libraries/MTConnect.NET-Common/Observations/Events/ConnectionStatusDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/ConnectionStatusDescriptions.g.cs index 287524dce..368e7ff62 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/ConnectionStatusDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/ConnectionStatusDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class ConnectionStatusDescriptions { /// @@ -21,6 +24,9 @@ public static class ConnectionStatusDescriptions public const string ESTABLISHED = "Open connection.The normal state for the data transfer phase of the connection."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(ConnectionStatus value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/ControllerModeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/ControllerModeDescriptions.g.cs index f98ff9907..20315c845 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/ControllerModeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/ControllerModeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class ControllerModeDescriptions { /// @@ -36,6 +39,9 @@ public static class ControllerModeDescriptions public const string FEED_HOLD = "Axes of the device are commanded to stop, but the spindle continues to function."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(ControllerMode value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/ControllerModeOverrideDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/ControllerModeOverrideDescriptions.g.cs index 4eaceb42d..3040ea55e 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/ControllerModeOverrideDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/ControllerModeOverrideDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class ControllerModeOverrideDescriptions { /// @@ -16,6 +19,9 @@ public static class ControllerModeOverrideDescriptions public const string OFF = "ControllerModeOverride is in the `OFF` state and the mode override is inactive."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(ControllerModeOverride value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/DirectionDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/DirectionDescriptions.g.cs index 7a8b1cc62..65901edf9 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/DirectionDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/DirectionDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class DirectionDescriptions { /// @@ -26,6 +29,9 @@ public static class DirectionDescriptions public const string NEGATIVE = ""; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(Direction value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/DirectionLinear.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/DirectionLinear.g.cs index 1b0583ee4..93fb40476 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/DirectionLinear.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/DirectionLinear.g.cs @@ -1,18 +1,13 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2024 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Observations.Events { /// - /// + /// DirectionLinear controlled vocabulary as defined by the MTConnect Standard. /// public enum DirectionLinear { - /// - /// Linear position is increasing. - /// - POSITIVE, - /// /// Linear position is decreasing. /// @@ -21,6 +16,11 @@ public enum DirectionLinear /// /// No direction. /// - NONE + NONE, + + /// + /// Linear position is increasing. + /// + POSITIVE } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Observations/Events/DirectionLinearDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/DirectionLinearDescriptions.g.cs index d1bd1ebca..250b4e6aa 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/DirectionLinearDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/DirectionLinearDescriptions.g.cs @@ -1,15 +1,13 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2024 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class DirectionLinearDescriptions { - /// - /// Linear position is increasing. - /// - public const string POSITIVE = "Linear position is increasing."; - /// /// Linear position is decreasing. /// @@ -19,15 +17,23 @@ public static class DirectionLinearDescriptions /// No direction. /// public const string NONE = "No direction."; + + /// + /// Linear position is increasing. + /// + public const string POSITIVE = "Linear position is increasing."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(DirectionLinear value) { switch (value) { - case DirectionLinear.POSITIVE: return "Linear position is increasing."; case DirectionLinear.NEGATIVE: return "Linear position is decreasing."; case DirectionLinear.NONE: return "No direction."; + case DirectionLinear.POSITIVE: return "Linear position is increasing."; } return null; diff --git a/libraries/MTConnect.NET-Common/Observations/Events/DirectionRotary.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/DirectionRotary.g.cs index 940ed7f06..023fe98ce 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/DirectionRotary.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/DirectionRotary.g.cs @@ -1,10 +1,10 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2024 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Observations.Events { /// - /// + /// DirectionRotary controlled vocabulary as defined by the MTConnect Standard. /// public enum DirectionRotary { diff --git a/libraries/MTConnect.NET-Common/Observations/Events/DirectionRotaryDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/DirectionRotaryDescriptions.g.cs index 63a35118e..66deeaf25 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/DirectionRotaryDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/DirectionRotaryDescriptions.g.cs @@ -1,8 +1,11 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2024 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class DirectionRotaryDescriptions { /// @@ -21,6 +24,9 @@ public static class DirectionRotaryDescriptions public const string NONE = "No direction."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(DirectionRotary value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/DoorStateDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/DoorStateDescriptions.g.cs index b28b5e1f3..4b5ca3dee 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/DoorStateDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/DoorStateDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class DoorStateDescriptions { /// @@ -21,6 +24,9 @@ public static class DoorStateDescriptions public const string UNLATCHED = "Door is not closed to the point of a positive confirmation and not open to the point of a positive confirmation. It is in an intermediate position."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(DoorState value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/EmergencyStopDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/EmergencyStopDescriptions.g.cs index 492b06f88..17b68adec 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/EmergencyStopDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/EmergencyStopDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class EmergencyStopDescriptions { /// @@ -16,6 +19,9 @@ public static class EmergencyStopDescriptions public const string TRIGGERED = "Operation of the piece of equipment, component, or composition is inhibited."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(EmergencyStop value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/EndOfBarDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/EndOfBarDescriptions.g.cs index f5310a813..e86cba884 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/EndOfBarDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/EndOfBarDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class EndOfBarDescriptions { /// @@ -16,6 +19,9 @@ public static class EndOfBarDescriptions public const string NO = "EndOfBar has not been reached."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(EndOfBar value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/EquipmentModeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/EquipmentModeDescriptions.g.cs index 07d69949e..47731de70 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/EquipmentModeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/EquipmentModeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class EquipmentModeDescriptions { /// @@ -16,6 +19,9 @@ public static class EquipmentModeDescriptions public const string OFF = "Equipment is not functioning in the mode designated by the `subType`."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(EquipmentMode value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/EventValue.cs b/libraries/MTConnect.NET-Common/Observations/Events/EventValue.cs index 4849440f4..4c8ac04ac 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/EventValue.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/EventValue.cs @@ -6,24 +6,48 @@ namespace MTConnect.Observations.Events { + /// + /// A simple EVENT category Observation that carries a single reported value. + /// public class EventValue : EventValueObservation { + /// + /// The value reported by the Event. + /// public object Value { get; set; } + /// + /// Initializes a new Event value with no reported value. + /// protected EventValue() { } + /// + /// Initializes a new Event value with the specified reported value. + /// + /// The value reported by the Event. public EventValue(object value) { Value = value; } + /// + /// Returns the string representation of the reported value. + /// + /// The value's string form, or null when no value is set. public override string ToString() { return Value?.ToString(); } + /// + /// Resolves the human-readable description for a controlled-vocabulary Event value based on its DataItem type and subtype. + /// + /// The DataItem type identifier (for example, EXECUTION). + /// The DataItem subtype, used to disambiguate types such as DIRECTION and COMPOSITION_STATE. + /// The reported enumeration value to describe. + /// The matching description text, or null when the type or value has no controlled-vocabulary description. public static string GetDescriptionText(string type, string subType, string value) { switch (type.ToUnderscoreUpper()) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/ExecutionDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/ExecutionDescriptions.g.cs index 8199947b2..a074a15a2 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/ExecutionDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/ExecutionDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class ExecutionDescriptions { /// @@ -56,6 +59,9 @@ public static class ExecutionDescriptions public const string PROGRAM_OPTIONAL_STOP = "Program has been intentionally optionally stopped using an M01 or similar code.**DEPRECATED** in *version 1.4* and replaced with `OPTIONAL_STOP`."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(Execution value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/FunctionalModeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/FunctionalModeDescriptions.g.cs index 65f7c3957..c811ed692 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/FunctionalModeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/FunctionalModeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class FunctionalModeDescriptions { /// @@ -31,6 +34,9 @@ public static class FunctionalModeDescriptions public const string PROCESS_DEVELOPMENT = "Component is being used to prove-out a new process, testing of equipment or processes, or any other active use that does not result in the production of product."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(FunctionalMode value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/InterfaceStateDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/InterfaceStateDescriptions.g.cs index 8d7e33bb4..3df54f664 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/InterfaceStateDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/InterfaceStateDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class InterfaceStateDescriptions { /// @@ -16,6 +19,9 @@ public static class InterfaceStateDescriptions public const string DISABLED = "Interface is currently not operational."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(InterfaceState value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/LeakDetectDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/LeakDetectDescriptions.g.cs index 3a43bb3bd..d64af2800 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/LeakDetectDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/LeakDetectDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class LeakDetectDescriptions { /// @@ -16,6 +19,9 @@ public static class LeakDetectDescriptions public const string NOT_DETECTED = "Leak is currently not being detected."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(LeakDetect value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/LockStateDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/LockStateDescriptions.g.cs index ec92152fd..baab8d4ef 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/LockStateDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/LockStateDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class LockStateDescriptions { /// @@ -16,6 +19,9 @@ public static class LockStateDescriptions public const string UNLOCKED = "Mechanism is disengaged and the associated Component is able to be opened or operated."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(LockState value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/MaintenanceListDirection.cs b/libraries/MTConnect.NET-Common/Observations/Events/MaintenanceListDirection.cs index d2b48076f..089f3669f 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/MaintenanceListDirection.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/MaintenanceListDirection.cs @@ -3,10 +3,19 @@ namespace MTConnect.Observations.Events { + /// + /// The direction in which a MaintenanceList interval counts toward its limit. + /// public enum MaintenanceListDirection { + /// + /// The interval counts down toward zero from the configured limit. + /// DOWN, + /// + /// The interval counts up toward the configured limit. + /// UP } } diff --git a/libraries/MTConnect.NET-Common/Observations/Events/MaintenanceListInterval.cs b/libraries/MTConnect.NET-Common/Observations/Events/MaintenanceListInterval.cs index 875ab3c7c..1512889e2 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/MaintenanceListInterval.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/MaintenanceListInterval.cs @@ -3,10 +3,19 @@ namespace MTConnect.Observations.Events { + /// + /// How a MaintenanceList interval value is interpreted relative to the last maintenance action. + /// public enum MaintenanceListInterval { + /// + /// The interval is measured against an absolute reference point. + /// ABSOLUTE, + /// + /// The interval is measured incrementally from the last maintenance action. + /// INCREMENTAL } } diff --git a/libraries/MTConnect.NET-Common/Observations/Events/NetworkWirelessDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/NetworkWirelessDescriptions.g.cs deleted file mode 100644 index 5b91e2a6a..000000000 --- a/libraries/MTConnect.NET-Common/Observations/Events/NetworkWirelessDescriptions.g.cs +++ /dev/null @@ -1,30 +0,0 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. -// TrakHound Inc. licenses this file to you under the MIT license. - -namespace MTConnect.Observations.Events -{ - public static class NetworkWirelessDescriptions - { - /// - /// - /// - public const string YES = ""; - - /// - /// - /// - public const string NO = ""; - - - public static string Get(NetworkWireless value) - { - switch (value) - { - case NetworkWireless.YES: return ""; - case NetworkWireless.NO: return ""; - } - - return null; - } - } -} \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Observations/Events/OperatingModeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/OperatingModeDescriptions.g.cs index d9e095fd9..e718e2ee4 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/OperatingModeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/OperatingModeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class OperatingModeDescriptions { /// @@ -21,6 +24,9 @@ public static class OperatingModeDescriptions public const string SEMI_AUTOMATIC = "Executes a single instruction from a recipe or program.> Note 1 to entry: Setpoint is entered and fixed, but the PID is controlling.> Note 2 to entry: Still goes through the PID control system.> Note 3 to entry: Manual fixed entry from a recipe."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(OperatingMode value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/PartCountTypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/PartCountTypeDescriptions.g.cs index 7a381fbf9..4bf96abeb 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/PartCountTypeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/PartCountTypeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class PartCountTypeDescriptions { /// @@ -16,6 +19,9 @@ public static class PartCountTypeDescriptions public const string BATCH = "Pre-specified group of items."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(PartCountType value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/PartDetectDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/PartDetectDescriptions.g.cs index e16bd8d2b..7947ac5af 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/PartDetectDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/PartDetectDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class PartDetectDescriptions { /// @@ -16,6 +19,9 @@ public static class PartDetectDescriptions public const string NOT_PRESENT = "Part or work piece is not detected or is not present."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(PartDetect value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/PartProcessingStateDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/PartProcessingStateDescriptions.g.cs index 48ebbb4c7..97845344f 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/PartProcessingStateDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/PartProcessingStateDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class PartProcessingStateDescriptions { /// @@ -66,6 +69,9 @@ public static class PartProcessingStateDescriptions public const string TRANSIT_COMPLETE = "Part occurrence has been placed at its designated destination."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(PartProcessingState value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/PartStatusDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/PartStatusDescriptions.g.cs index 86a5fb7dd..1906a964b 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/PartStatusDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/PartStatusDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class PartStatusDescriptions { /// @@ -16,6 +19,9 @@ public static class PartStatusDescriptions public const string FAIL = "Part does not conform to some given requirements."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(PartStatus value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/PathModeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/PathModeDescriptions.g.cs index ea1a5d57e..f798cbf27 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/PathModeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/PathModeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class PathModeDescriptions { /// @@ -26,6 +29,9 @@ public static class PathModeDescriptions public const string MIRROR = "Axes associated with the path are mirroring the motion of the `MASTER` path."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(PathMode value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/PowerStateDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/PowerStateDescriptions.g.cs index cf8ad3c8b..c029ab929 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/PowerStateDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/PowerStateDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class PowerStateDescriptions { /// @@ -16,6 +19,9 @@ public static class PowerStateDescriptions public const string OFF = "Source of energy for an entity or the enabling signal providing permission for the entity to perform its function(s) is not present or is disconnected."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(PowerState value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/PowerStatusDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/PowerStatusDescriptions.g.cs index 9bdb4e1ea..957f986d6 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/PowerStatusDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/PowerStatusDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class PowerStatusDescriptions { /// @@ -16,6 +19,9 @@ public static class PowerStatusDescriptions public const string OFF = ""; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(PowerStatus value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/ProcessStateDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/ProcessStateDescriptions.g.cs index 18db2b6d2..622249f49 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/ProcessStateDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/ProcessStateDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class ProcessStateDescriptions { /// @@ -36,6 +39,9 @@ public static class ProcessStateDescriptions public const string ABORTED = "Process occurrence has come to a premature end and cannot be resumed."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(ProcessState value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/ProgramEditDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/ProgramEditDescriptions.g.cs index 5e2c8e459..71aa4894f 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/ProgramEditDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/ProgramEditDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class ProgramEditDescriptions { /// @@ -21,6 +24,9 @@ public static class ProgramEditDescriptions public const string NOT_READY = "Controller is being inhibited by a function from entering the program edit mode."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(ProgramEdit value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/ProgramLocationTypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/ProgramLocationTypeDescriptions.g.cs index 11f176c18..cd6b6b59c 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/ProgramLocationTypeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/ProgramLocationTypeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class ProgramLocationTypeDescriptions { /// @@ -16,6 +19,9 @@ public static class ProgramLocationTypeDescriptions public const string EXTERNAL = "Not managed by the controller."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(ProgramLocationType value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/RotaryModeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/RotaryModeDescriptions.g.cs index c19ee7c32..87299175e 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/RotaryModeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/RotaryModeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class RotaryModeDescriptions { /// @@ -21,6 +24,9 @@ public static class RotaryModeDescriptions public const string CONTOUR = "Position of the axis is being interpolated."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(RotaryMode value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/SensorStateDetectDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/SensorStateDetectDescriptions.g.cs deleted file mode 100644 index f85087f3a..000000000 --- a/libraries/MTConnect.NET-Common/Observations/Events/SensorStateDetectDescriptions.g.cs +++ /dev/null @@ -1,30 +0,0 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. -// TrakHound Inc. licenses this file to you under the MIT license. - -namespace MTConnect.Observations.Events -{ - public static class SensorStateDetectDescriptions - { - /// - /// Activation state of the Composition is in an `ON` condition, it is operating, or it is powered. - /// - public const string ON = "Activation state of the Composition is in an `ON` condition, it is operating, or it is powered."; - - /// - /// Activation state of the Composition is in an `OFF` condition, it is not operating, or it is not powered. - /// - public const string OFF = "Activation state of the Composition is in an `OFF` condition, it is not operating, or it is not powered."; - - - public static string Get(SensorStateDetect value) - { - switch (value) - { - case SensorStateDetect.ON: return "Activation state of the Composition is in an `ON` condition, it is operating, or it is powered."; - case SensorStateDetect.OFF: return "Activation state of the Composition is in an `OFF` condition, it is not operating, or it is not powered."; - } - - return null; - } - } -} \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Observations/Events/SpindleInterlockDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/SpindleInterlockDescriptions.g.cs index 35342c6d7..bde466680 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/SpindleInterlockDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/SpindleInterlockDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class SpindleInterlockDescriptions { /// @@ -16,6 +19,9 @@ public static class SpindleInterlockDescriptions public const string INACTIVE = "Spindle has not been deactivated."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(SpindleInterlock value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/UncertaintyTypeDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/UncertaintyTypeDescriptions.g.cs index 8ee6897e3..f8aa0e6d2 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/UncertaintyTypeDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/UncertaintyTypeDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class UncertaintyTypeDescriptions { /// @@ -16,6 +19,9 @@ public static class UncertaintyTypeDescriptions public const string MEAN = "Standard uncertainty using arithmetic mean or average the observations. JCGM 100:2008 4.2"; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(UncertaintyType value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/ValveStateDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/ValveStateDescriptions.g.cs index 001b5d570..176c4e97a 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/ValveStateDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/ValveStateDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class ValveStateDescriptions { /// @@ -26,6 +29,9 @@ public static class ValveStateDescriptions public const string CLOSING = "Valve is transitioning from an `OPEN` state to a `CLOSED` state."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(ValveState value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/Events/WaitStateDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/Events/WaitStateDescriptions.g.cs index 299817d17..a8d9346a1 100644 --- a/libraries/MTConnect.NET-Common/Observations/Events/WaitStateDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Events/WaitStateDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations.Events { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class WaitStateDescriptions { /// @@ -61,6 +64,9 @@ public static class WaitStateDescriptions public const string RESUMING = "Execution is waiting while the equipment is resuming the production cycle but has not yet resumed execution."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(WaitState value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/IDataSetEntry.cs b/libraries/MTConnect.NET-Common/Observations/IDataSetEntry.cs index 4521452fd..d56f82a05 100644 --- a/libraries/MTConnect.NET-Common/Observations/IDataSetEntry.cs +++ b/libraries/MTConnect.NET-Common/Observations/IDataSetEntry.cs @@ -13,6 +13,9 @@ public interface IDataSetEntry /// string Key { get; } + /// + /// An optional human-readable description of the entry's . + /// string KeyDescription { get; } /// diff --git a/libraries/MTConnect.NET-Common/Observations/IObservation.cs b/libraries/MTConnect.NET-Common/Observations/IObservation.cs index b918ae605..0889151a3 100644 --- a/libraries/MTConnect.NET-Common/Observations/IObservation.cs +++ b/libraries/MTConnect.NET-Common/Observations/IObservation.cs @@ -113,6 +113,10 @@ public interface IObservation : IMTConnectEntity string GetValue(string valueKey); + /// + /// Validate this observation against the constraints of its DataItem. + /// + /// The validation result describing whether the observation is valid and, if not, why. ValidationResult Validate(); } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Observations/ITableCell.cs b/libraries/MTConnect.NET-Common/Observations/ITableCell.cs index 537ffe913..aadbb4f64 100644 --- a/libraries/MTConnect.NET-Common/Observations/ITableCell.cs +++ b/libraries/MTConnect.NET-Common/Observations/ITableCell.cs @@ -13,6 +13,9 @@ public interface ITableCell /// string Key { get; } + /// + /// An optional human-readable description of the cell's (column). + /// string KeyDescription { get; set; } /// diff --git a/libraries/MTConnect.NET-Common/Observations/ITableEntry.cs b/libraries/MTConnect.NET-Common/Observations/ITableEntry.cs index 307fcfb0a..5d476e19a 100644 --- a/libraries/MTConnect.NET-Common/Observations/ITableEntry.cs +++ b/libraries/MTConnect.NET-Common/Observations/ITableEntry.cs @@ -15,6 +15,9 @@ public interface ITableEntry /// string Key { get; } + /// + /// An optional human-readable description of the entry's (row). + /// string KeyDescription { get; } /// diff --git a/libraries/MTConnect.NET-Common/Observations/Observation.cs b/libraries/MTConnect.NET-Common/Observations/Observation.cs index 55dbf5da5..6215341de 100644 --- a/libraries/MTConnect.NET-Common/Observations/Observation.cs +++ b/libraries/MTConnect.NET-Common/Observations/Observation.cs @@ -20,16 +20,38 @@ public class Observation : IObservation /// If an Agent cannot determine a Valid Data Value for a DataItem, the value returned for the Result for the Data Entity MUST be reported as UNAVAILABLE. /// public const string Unavailable = "UNAVAILABLE"; + + /// + /// The explanatory description of when an Observation result is reported as UNAVAILABLE. + /// public const string UnavailableDescription = "If an Agent cannot determine a Valid Data Value for a DataItem, the value returned for the Result for the Data Entity MUST be reported as UNAVAILABLE."; private const string UppercaseValuePattern = "^[a-zA-Z_]*$"; private static readonly Regex _uppercaseValueRegex = new Regex(UppercaseValuePattern); + /// + /// Cache mapping each Observation type identifier to its concrete implementing type's full name. + /// protected static readonly Dictionary _typeIds = new Dictionary(); + + /// + /// Lazily populated cache mapping each Observation type identifier to its concrete CLR type. + /// protected static Dictionary _types; + + /// + /// Synchronization object guarding lazy initialization of the shared type caches. + /// protected static readonly object _typeLock = new object(); + /// + /// Synchronization object guarding mutation of this Observation's value collection. + /// protected readonly object _valueLock = new object(); + + /// + /// The Observation's values, keyed by value key. + /// protected readonly Dictionary _values = new Dictionary(); @@ -67,6 +89,9 @@ public string Uuid set => _uuid = value; } + /// + /// The MTConnect entity classification for this object, which is always . + /// public MTConnectEntityType EntityType => MTConnectEntityType.Observation; internal string _dataItemId; @@ -219,6 +244,10 @@ public bool Extended public IEnumerable Values => _values.Values; + /// + /// Validates this Observation against its DataItem's constraints for the Device's MTConnect version. + /// + /// The validation result; an invalid result when the Observation has no associated DataItem or Device. public ValidationResult Validate() { var result = new ValidationResult(false); @@ -232,6 +261,11 @@ public ValidationResult Validate() } + /// + /// Creates the Observation subclass that matches the given DataItem's category (Sample, Event, or Condition). + /// + /// The DataItem the Observation is created for. + /// A category-specific Observation, or a base Observation when is null. public static Observation Create(IDataItem dataItem) { if (dataItem != null) @@ -248,6 +282,11 @@ public static Observation Create(IDataItem dataItem) } + /// + /// Returns the raw string value stored under the specified value key. + /// + /// The value key to look up. + /// The stored value, or null when the key is absent. public string GetValue(string valueKey) { if (!string.IsNullOrEmpty(valueKey) && !_values.IsNullOrEmpty()) @@ -264,6 +303,12 @@ public string GetValue(string valueKey) return null; } + /// + /// Returns the value stored under the specified value key converted to the requested type. + /// + /// The type to convert the stored value to. + /// The value key to look up. + /// The converted value, or the default of when the key is absent. public TValue GetValue(string valueKey) { var value = GetValue(valueKey); @@ -275,6 +320,11 @@ public TValue GetValue(string valueKey) return default; } + /// + /// Adds or replaces the value stored under the specified value key. + /// + /// The value key to set. + /// The value to store; ignored when null. public void AddValue(string valueKey, object value) { if (!string.IsNullOrEmpty(valueKey) && value != null) @@ -283,6 +333,10 @@ public void AddValue(string valueKey, object value) } } + /// + /// Adds or replaces the given value, raising the value-added notification afterward. + /// + /// The value to store, identified by its key. public void AddValue(ObservationValue observationValue) { if (!string.IsNullOrEmpty(observationValue.Key)) @@ -301,6 +355,10 @@ public void AddValue(ObservationValue observationValue) } } + /// + /// Adds or replaces each value in the given collection. + /// + /// The values to store. public void AddValues(IEnumerable observationValues) { if (!observationValues.IsNullOrEmpty()) @@ -313,9 +371,22 @@ public void AddValues(IEnumerable observationValues) } + /// + /// Hook invoked after a value is added, letting derived Observation types react to the change. + /// The base implementation does nothing. + /// + /// The value that was added. protected virtual void OnValueAdded(ObservationValue observationValue) { } + /// + /// Returns the human-readable description for an observed value of the given category, type, and subtype. + /// + /// The DataItem category. + /// The DataItem Type. + /// The DataItem SubType. + /// The observed value to describe. + /// The description text, or null when no description applies to the category. public static string GetDescriptionText(DataItemCategory category, string type, string subType, string value) { switch (category) @@ -327,6 +398,11 @@ public static string GetDescriptionText(DataItemCategory category, string type, } + /// + /// Returns a materialized copy of the supplied Observation values. + /// + /// The values to copy. + /// A new list containing the supplied values, empty when none are supplied. public static IEnumerable ProcessValues(IEnumerable values) { var valuesList = new List(); @@ -342,6 +418,11 @@ public static IEnumerable ProcessValues(IEnumerable + /// Returns a copy of the supplied values with non-numeric, identifier-shaped string values upper-cased. + /// + /// The values to normalize. + /// The values with eligible string values upper-cased. public static IEnumerable UppercaseValues(IEnumerable values) { if (!values.IsNullOrEmpty()) @@ -396,6 +477,10 @@ private static object ChangeType(object obj, Type type) } + /// + /// Discovers every concrete Observation type across the loaded assemblies, keyed by Observation type identifier. + /// + /// The discovered Observation types keyed by their type identifier. protected static Dictionary GetAllTypes() { var assemblies = Assemblies.Get(); diff --git a/libraries/MTConnect.NET-Common/Observations/ObservationValidationResult.cs b/libraries/MTConnect.NET-Common/Observations/ObservationValidationResult.cs index bf1c5cb64..15c7bbbac 100644 --- a/libraries/MTConnect.NET-Common/Observations/ObservationValidationResult.cs +++ b/libraries/MTConnect.NET-Common/Observations/ObservationValidationResult.cs @@ -8,11 +8,22 @@ namespace MTConnect.Observations /// public struct ObservationValidationResult { + /// + /// Indicates whether the Observation passed validation. + /// public bool IsValid { get; set; } + /// + /// An optional message explaining the validation outcome, typically the reason for a failure. + /// public string Message { get; set; } + /// + /// Initializes a new Observation validation result with the given outcome and optional message. + /// + /// Whether the Observation passed validation. + /// An optional explanatory message. public ObservationValidationResult(bool isValid, string message = null) { IsValid = isValid; diff --git a/libraries/MTConnect.NET-Common/Observations/ObservationValue.cs b/libraries/MTConnect.NET-Common/Observations/ObservationValue.cs index 2f57b27db..978d9e79f 100644 --- a/libraries/MTConnect.NET-Common/Observations/ObservationValue.cs +++ b/libraries/MTConnect.NET-Common/Observations/ObservationValue.cs @@ -23,6 +23,11 @@ public struct ObservationValue public string Value => _value; + /// + /// Initializes a new Observation value pairing a key with a value, stringifying the value. + /// + /// The unique key identifying the value. + /// The value to record; stored as an empty string when null. public ObservationValue(string key, object value) { _key = key; @@ -30,6 +35,10 @@ public ObservationValue(string key, object value) } + /// + /// Determines whether this entry carries both a non-empty key and a value. + /// + /// True when the entry has a usable key and value; otherwise false. public bool HasValue() { return !string.IsNullOrEmpty(Key) && Value != null; diff --git a/libraries/MTConnect.NET-Common/Observations/Output/IObservationOutput.cs b/libraries/MTConnect.NET-Common/Observations/Output/IObservationOutput.cs index ab3970760..bafb9a22f 100644 --- a/libraries/MTConnect.NET-Common/Observations/Output/IObservationOutput.cs +++ b/libraries/MTConnect.NET-Common/Observations/Output/IObservationOutput.cs @@ -6,43 +6,102 @@ namespace MTConnect.Observations.Output { + /// + /// A read-only projection of an Observation prepared for serialization into an MTConnectStreams response. + /// public interface IObservationOutput { + /// + /// The UUID of the Device the Observation belongs to. + /// string DeviceUuid { get; } + /// + /// The DataItem definition the Observation was produced for. + /// IDataItem DataItem { get; } + /// + /// The Id of the DataItem the Observation was produced for. + /// string DataItemId { get; } + /// + /// The category (SAMPLE, EVENT, or CONDITION) of the DataItem. + /// DataItemCategory Category { get; } + /// + /// The type of the DataItem. + /// string Type { get; } + /// + /// The subtype of the DataItem, when present. + /// string SubType { get; } + /// + /// The name of the DataItem, when present. + /// string Name { get; } + /// + /// The instance identifier of the Agent that produced the Observation. + /// ulong InstanceId { get; } + /// + /// The sequence number assigned to the Observation in the Agent's buffer. + /// ulong Sequence { get; } + /// + /// The UTC timestamp at which the Observation was recorded. + /// DateTime Timestamp { get; } + /// + /// The Observation timestamp expressed with the configured output time-zone offset. + /// DateTimeOffset TimeZoneTimestamp { get; } + /// + /// The Id of the Composition the Observation is associated with, when present. + /// string CompositionId { get; } + /// + /// The representation (VALUE, DATA_SET, TABLE, or TIME_SERIES) of the DataItem. + /// DataItemRepresentation Representation { get; } + /// + /// The quality of the reported data. + /// Quality Quality { get; } + /// + /// Whether the DataItem is deprecated in the active MTConnect version. + /// bool Deprecated { get; } + /// + /// Whether the Observation carries values beyond the standard MTConnect schema. + /// bool Extended { get; } + /// + /// The ValueKey and value pairs that make up the Observation. + /// ObservationValue[] Values { get; } + /// + /// Gets the value recorded for the specified ValueKey. + /// + /// The ValueKey identifying the Representation component to retrieve. + /// The recorded value, or null when no matching value exists. string GetValue(string valueKey); } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Observations/Output/ObservationOutput.cs b/libraries/MTConnect.NET-Common/Observations/Output/ObservationOutput.cs index ea35ea201..6eb7a5699 100644 --- a/libraries/MTConnect.NET-Common/Observations/Output/ObservationOutput.cs +++ b/libraries/MTConnect.NET-Common/Observations/Output/ObservationOutput.cs @@ -13,6 +13,9 @@ namespace MTConnect.Observations.Output public struct ObservationOutput : IObservationOutput { internal string _deviceUuid; + /// + /// The UUID of the Device the Observation belongs to. + /// public string DeviceUuid { get => _deviceUuid; @@ -20,6 +23,9 @@ public string DeviceUuid } internal IDataItem _dataItem; + /// + /// The DataItem definition the Observation was produced for. + /// public IDataItem DataItem { get => _dataItem; @@ -31,6 +37,9 @@ public IDataItem DataItem /// The DataItemID MUST match the id attribute of the data item defined in the Device Information Model that this DataItem element represents. /// internal string _dataItemId; + /// + /// The unique identifier for the DataItem, matching the id of the DataItem in the Device Information Model. + /// public string DataItemId { get => _dataItemId; @@ -43,6 +52,9 @@ public string DataItemId /// The most accurate time available to the device MUST be used for the timestamp. /// internal DateTime _timestamp; + /// + /// The time the DataItem data was reported or its statistics computed; the end of the collection interval for durations and TIME_SERIES. + /// public DateTime Timestamp { get => _timestamp; @@ -50,6 +62,9 @@ public DateTime Timestamp } internal DateTimeOffset _timeZoneTimestamp; + /// + /// The Observation timestamp expressed with the configured output time-zone offset. + /// public DateTimeOffset TimeZoneTimestamp { get => _timeZoneTimestamp; @@ -61,6 +76,9 @@ public DateTimeOffset TimeZoneTimestamp /// The name MUST match the name of the data item defined in the Device Information Model that this DataItem represents. /// internal string _name; + /// + /// The name of the DataItem, matching the name of the DataItem in the Device Information Model. + /// public string Name { get => _name; @@ -71,6 +89,9 @@ public string Name /// The Agent Instance ID that produced the Observation /// internal ulong _instanceId; + /// + /// The instance identifier of the Agent that produced the Observation. + /// public ulong InstanceId { get => _instanceId; @@ -82,6 +103,9 @@ public ulong InstanceId /// The value MUST be represented as an unsigned 64 bit with valid values from 1 to 2^64-1. /// internal ulong _sequence; + /// + /// The sequential position of the Observation in the Agent's data buffer (1 to 2^64-1). + /// public ulong Sequence { get => _sequence; @@ -92,6 +116,9 @@ public ulong Sequence /// Category of DataItem (Condition, Event, or Sample) /// internal DataItemCategory _category; + /// + /// The category (SAMPLE, EVENT, or CONDITION) of the DataItem. + /// public DataItemCategory Category { get => _category; @@ -102,6 +129,9 @@ public DataItemCategory Category /// Type associated with the DataItem /// internal string _type; + /// + /// The type associated with the DataItem. + /// public string Type { get => _type; @@ -112,6 +142,9 @@ public string Type /// The subtype of the DataItem defined in the Device Information Model that this DataItem element represents /// internal string _subType; + /// + /// The subtype of the DataItem defined in the Device Information Model. + /// public string SubType { get => _subType; @@ -122,6 +155,9 @@ public string SubType /// The identifier of the Composition element defined in the MTConnectDevices document associated with the data reported for the DataItem. /// internal string _compositionId; + /// + /// The identifier of the Composition element associated with the data reported for the DataItem. + /// public string CompositionId { get => _compositionId; @@ -136,6 +172,9 @@ public string CompositionId /// If a representation is not specified, it MUST be determined to be a VALUE. /// internal DataItemRepresentation _representation; + /// + /// The representation of the reported data (VALUE, DATA_SET, TABLE, or TIME_SERIES); VALUE when unspecified. + /// public DataItemRepresentation Representation { get => _representation; @@ -146,6 +185,9 @@ public DataItemRepresentation Representation /// Indicates if the Observation is verifiable and is in accordance with the normative definitions within the MTConnect Standard. /// internal Quality _quality; + /// + /// Indicates whether the Observation is verifiable against the normative definitions in the MTConnect Standard. + /// public Quality Quality { get => _quality; @@ -156,6 +198,9 @@ public Quality Quality /// Indicates if the Observation has any property or controlled vocabulary that has been deprecated in the MTConnect Standard. /// internal bool _deprecated; + /// + /// Indicates whether the Observation uses any property or controlled vocabulary deprecated in the MTConnect Standard. + /// public bool Deprecated { get => _deprecated; @@ -166,6 +211,9 @@ public bool Deprecated /// Indicates if the Observation has any property or controlled vocabulary that has been extended and cannot be validated. /// internal bool _extended; + /// + /// Indicates whether the Observation uses any extended property or controlled vocabulary that cannot be validated. + /// public bool Extended { get => _extended; @@ -176,6 +224,9 @@ public bool Extended /// Gets the Values associated with this Observation. These values represent data recorded during an Observation. /// internal ObservationValue[] _values; + /// + /// The ValueKey and value pairs recorded during the Observation. + /// public ObservationValue[] Values { get => _values; @@ -183,6 +234,10 @@ public ObservationValue[] Values } + /// + /// Initializes a new output projection from a reported Observation, copying its identity, metadata, and values. + /// + /// The source Observation; a null argument yields default field values. public ObservationOutput(IObservation observation) { _deviceUuid = null; @@ -230,6 +285,11 @@ public ObservationOutput(IObservation observation) } + /// + /// Gets the value recorded for the specified ValueKey. + /// + /// The ValueKey identifying the Representation component to retrieve. + /// The recorded value, or null when no matching value exists. public string GetValue(string valueKey) { if (valueKey != null && _values != null && _values.Length > 0) diff --git a/libraries/MTConnect.NET-Common/Observations/Quality.g.cs b/libraries/MTConnect.NET-Common/Observations/Quality.g.cs index f524974a3..fdfca08b5 100644 --- a/libraries/MTConnect.NET-Common/Observations/Quality.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/Quality.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations { + /// + /// Quality controlled vocabulary as defined by the MTConnect Standard. + /// public enum Quality { /// diff --git a/libraries/MTConnect.NET-Common/Observations/QualityDescriptions.g.cs b/libraries/MTConnect.NET-Common/Observations/QualityDescriptions.g.cs index f86f5c436..38c60c359 100644 --- a/libraries/MTConnect.NET-Common/Observations/QualityDescriptions.g.cs +++ b/libraries/MTConnect.NET-Common/Observations/QualityDescriptions.g.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations { + /// + /// Description text for each value as defined by the MTConnect Standard. + /// public static class QualityDescriptions { /// @@ -21,6 +24,9 @@ public static class QualityDescriptions public const string VALID = "Observation is valid against the MTConnect Standard."; + /// + /// Returns the MTConnect Standard description text for the specified value, or null when none is defined. + /// public static string Get(Quality value) { switch (value) diff --git a/libraries/MTConnect.NET-Common/Observations/SampleDataSetObservation.cs b/libraries/MTConnect.NET-Common/Observations/SampleDataSetObservation.cs index f963d6f99..99f3b1915 100644 --- a/libraries/MTConnect.NET-Common/Observations/SampleDataSetObservation.cs +++ b/libraries/MTConnect.NET-Common/Observations/SampleDataSetObservation.cs @@ -32,12 +32,19 @@ public IEnumerable Entries } + /// + /// Initializes a new Sample Observation that reports a DATA_SET representation. + /// public SampleDataSetObservation() : base() { _representation = Devices.DataItemRepresentation.DATA_SET; } + /// + /// Invalidates the cached Data Set entries so they are rebuilt the next time they are read. + /// + /// The value that was added. protected override void OnValueAdded(ObservationValue observationValue) { _entries = null; diff --git a/libraries/MTConnect.NET-Common/Observations/SampleObservation.cs b/libraries/MTConnect.NET-Common/Observations/SampleObservation.cs index 132cb1c7f..e21f1eeab 100644 --- a/libraries/MTConnect.NET-Common/Observations/SampleObservation.cs +++ b/libraries/MTConnect.NET-Common/Observations/SampleObservation.cs @@ -78,12 +78,20 @@ public double Duration } + /// + /// Initializes a new Sample Observation with the Sample category. + /// public SampleObservation() { _category = DataItemCategory.SAMPLE; } + /// + /// Creates a Sample Observation for the given DataItem, copying its identifying metadata. + /// + /// The DataItem the Observation is created for. + /// The Sample Observation, or null when is null. public new static SampleObservation Create(IDataItem dataItem) { if (dataItem != null) @@ -102,6 +110,11 @@ public SampleObservation() return null; } + /// + /// Creates a Sample Observation from an existing Observation, copying its metadata and values. + /// + /// The source Observation to copy. + /// The Sample Observation, or null when is null. public static SampleObservation Create(IObservation observation) { if (observation != null) @@ -125,6 +138,12 @@ public static SampleObservation Create(IObservation observation) } + /// + /// Creates the Sample Observation subclass matching the given type and representation. + /// + /// The DataItem Type identifier. + /// The DataItem representation. + /// A type-specific Sample Observation, or a base SampleObservation when the type is not recognized. public static SampleObservation Create(string type, DataItemRepresentation representation) { Type dataItemType = null; diff --git a/libraries/MTConnect.NET-Common/Observations/SampleTableObservation.cs b/libraries/MTConnect.NET-Common/Observations/SampleTableObservation.cs index d4e113f59..5a7670e97 100644 --- a/libraries/MTConnect.NET-Common/Observations/SampleTableObservation.cs +++ b/libraries/MTConnect.NET-Common/Observations/SampleTableObservation.cs @@ -32,12 +32,19 @@ public IEnumerable Entries } + /// + /// Initializes a new Sample Observation that reports a TABLE representation. + /// public SampleTableObservation() : base() { _representation = Devices.DataItemRepresentation.TABLE; } + /// + /// Invalidates the cached Table entries so they are rebuilt the next time they are read. + /// + /// The value that was added. protected override void OnValueAdded(ObservationValue observationValue) { _entries = null; diff --git a/libraries/MTConnect.NET-Common/Observations/SampleTimeSeriesObservation.cs b/libraries/MTConnect.NET-Common/Observations/SampleTimeSeriesObservation.cs index 560d0a61f..6176f6e19 100644 --- a/libraries/MTConnect.NET-Common/Observations/SampleTimeSeriesObservation.cs +++ b/libraries/MTConnect.NET-Common/Observations/SampleTimeSeriesObservation.cs @@ -35,12 +35,19 @@ public IEnumerable Samples } + /// + /// Initializes a new Sample Observation that reports a TIME_SERIES representation. + /// public SampleTimeSeriesObservation() : base() { _representation = Devices.DataItemRepresentation.TIME_SERIES; } + /// + /// Invalidates the cached Time Series samples so they are rebuilt the next time they are read. + /// + /// The value that was added. protected override void OnValueAdded(ObservationValue observationValue) { _entries = null; diff --git a/libraries/MTConnect.NET-Common/Observations/SampleValueObservation.cs b/libraries/MTConnect.NET-Common/Observations/SampleValueObservation.cs index b866b9f60..fcfcb6f3b 100644 --- a/libraries/MTConnect.NET-Common/Observations/SampleValueObservation.cs +++ b/libraries/MTConnect.NET-Common/Observations/SampleValueObservation.cs @@ -18,6 +18,9 @@ public string Result } + /// + /// Initializes a new Sample Observation that reports a single VALUE representation. + /// public SampleValueObservation() : base() { _representation = Devices.DataItemRepresentation.VALUE; diff --git a/libraries/MTConnect.NET-Common/Observations/TableCell.cs b/libraries/MTConnect.NET-Common/Observations/TableCell.cs index 5e4a85703..976c14616 100644 --- a/libraries/MTConnect.NET-Common/Observations/TableCell.cs +++ b/libraries/MTConnect.NET-Common/Observations/TableCell.cs @@ -13,6 +13,9 @@ public class TableCell : ITableCell /// public string Key { get; set; } + /// + /// An optional human-readable description of the cell's (column). + /// public string KeyDescription { get; set; } /// @@ -21,14 +24,26 @@ public class TableCell : ITableCell public string Value { get; set; } + /// + /// Initializes a new, empty Table cell. + /// public TableCell() { } + /// + /// Initializes a new Table cell with the given column key and value. + /// + /// The cell's column key. + /// The cell's value; stringified when stored. public TableCell(string key, object value) { Key = key; Value = value?.ToString(); } + /// + /// Returns the cell formatted as "key=value", or an empty string when the cell has no key. + /// + /// The string representation of the cell. public override string ToString() { if (!string.IsNullOrEmpty(Key)) diff --git a/libraries/MTConnect.NET-Common/Observations/TableEntry.cs b/libraries/MTConnect.NET-Common/Observations/TableEntry.cs index bb6ffa48e..12a216561 100644 --- a/libraries/MTConnect.NET-Common/Observations/TableEntry.cs +++ b/libraries/MTConnect.NET-Common/Observations/TableEntry.cs @@ -15,6 +15,9 @@ public class TableEntry : ITableEntry /// public string Key { get; set; } + /// + /// An optional human-readable description of the entry's (row). + /// public string KeyDescription { get; set; } /// @@ -28,14 +31,27 @@ public class TableEntry : ITableEntry public IEnumerable Cells { get; set; } + /// + /// Initializes a new, empty Table entry. + /// public TableEntry() { } + /// + /// Initializes a new Table entry with the given row key and its cells. + /// + /// The entry's row key. + /// The cells (columns) that make up the row. public TableEntry(string key, IEnumerable cells) { Key = key; Cells = cells; } + /// + /// Initializes a new Table entry that marks a row key as added or removed. + /// + /// The entry's row key. + /// Whether the row was removed from the table. public TableEntry(string key, bool removed) { Key = key; diff --git a/libraries/MTConnect.NET-Common/Observations/TableObservation.cs b/libraries/MTConnect.NET-Common/Observations/TableObservation.cs index fe6e2ab70..fe03d9a69 100644 --- a/libraries/MTConnect.NET-Common/Observations/TableObservation.cs +++ b/libraries/MTConnect.NET-Common/Observations/TableObservation.cs @@ -11,9 +11,17 @@ namespace MTConnect.Observations /// public static class TableObservation { + /// + /// The sentinel value stored for a Table row key to mark that the row was removed from the table. + /// public const string EntryRemovedValue = "[!ENTRY_REMOVED!]"; + /// + /// Extracts the Table entries (rows and their cells) from a flat collection of Observation values. + /// + /// The Observation values to decode. + /// The decoded Table entries. public static IEnumerable GetEntries(IEnumerable values) { var entries = new List(); @@ -78,6 +86,11 @@ public static IEnumerable GetEntries(IEnumerable return entries; } + /// + /// Encodes a set of Table entries into the flat Observation values that represent them. + /// + /// The Table entries to encode. + /// The Observation values, with removed rows encoded using the removal sentinel. public static IEnumerable SetEntries(IEnumerable entries) { if (!entries.IsNullOrEmpty()) diff --git a/libraries/MTConnect.NET-Common/Observations/TimeSeriesObservation.cs b/libraries/MTConnect.NET-Common/Observations/TimeSeriesObservation.cs index d3a899d2f..9916d5b88 100644 --- a/libraries/MTConnect.NET-Common/Observations/TimeSeriesObservation.cs +++ b/libraries/MTConnect.NET-Common/Observations/TimeSeriesObservation.cs @@ -6,8 +6,16 @@ namespace MTConnect.Observations { + /// + /// A Time Series observation reports an ordered sequence of sampled values captured over a time interval. + /// public static class TimeSeriesObservation { + /// + /// Extracts the ordered numeric samples from a flat collection of Observation values. + /// + /// The Observation values to decode. + /// The samples in index order. public static IEnumerable GetSamples(IEnumerable values) { var samples = new List(); diff --git a/libraries/MTConnect.NET-Common/Observations/UnitSystem.cs b/libraries/MTConnect.NET-Common/Observations/UnitSystem.cs index abadb18d9..bbaea03f7 100644 --- a/libraries/MTConnect.NET-Common/Observations/UnitSystem.cs +++ b/libraries/MTConnect.NET-Common/Observations/UnitSystem.cs @@ -3,10 +3,15 @@ namespace MTConnect.Observations { + /// + /// The system of measurement an Observation's values are expressed in. + /// public enum UnitSystem { + /// SI metric units. METRIC, + /// US customary inch-based units. INCH } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Observations/ValueKeys.cs b/libraries/MTConnect.NET-Common/Observations/ValueKeys.cs index 32fd4817e..116c9ec13 100644 --- a/libraries/MTConnect.NET-Common/Observations/ValueKeys.cs +++ b/libraries/MTConnect.NET-Common/Observations/ValueKeys.cs @@ -11,24 +11,61 @@ namespace MTConnect.Observations /// public class ValueKeys { + /// The value key holding an Observation's primary result value. public const string Result = "Result"; + + /// The value key holding a Condition Observation's level (Normal, Warning, Fault, Unavailable). public const string Level = "Level"; + + /// The value key holding the identifier that correlates related Condition Observations. public const string ConditionId = "ConditionId"; + + /// The value key holding a device-native code reported alongside a Condition. public const string NativeCode = "NativeCode"; + + /// The value key holding a device-native severity reported alongside a Condition. public const string NativeSeverity = "NativeSeverity"; + + /// The value key holding a Condition's qualifier (for example High or Low). public const string Qualifier = "Qualifier"; + + /// The value key holding the human-readable message text of an Observation. public const string Message = "Message"; + + /// The value key holding the statistical operation applied to a Sample value. public const string Statistic = "Statistic"; + + /// The value key holding the reporting rate of a Sample Observation. public const string SampleRate = "SampleRate"; + + /// The value key holding the number of samples carried by a Time Series Observation. public const string SampleCount = "SampleCount"; + + /// The value key holding the entry count of a Data Set or Table Observation. public const string Count = "Count"; + + /// The value key holding the time span an Observation covers. public const string Duration = "Duration"; + + /// The value key holding the asset type associated with an asset-related Observation. public const string AssetType = "AssetType"; + + /// The value key holding the device type associated with the Observation. public const string DeviceType = "DeviceType"; + + /// The value key holding the content hash used to detect Observation changes. public const string Hash = "Hash"; + + /// The value key flagging that a Data Set or Table Observation reset its accumulated entries. public const string ResetTriggered = "ResetTriggered"; + + /// The key prefix used to compose indexed Time Series value keys. public const string TimeSeriesPrefix = "TimeSeries"; + + /// The key prefix used to compose keyed Data Set value keys. public const string DataSetPrefix = "DataSet"; + + /// The key prefix used to compose keyed Table value keys. public const string TablePrefix = "Table"; private static readonly ConcurrentDictionary _pascalKeys = new ConcurrentDictionary(); @@ -39,8 +76,18 @@ public class ValueKeys #region "TimeSeries" + /// + /// Builds the value key for the sample at the given position within a Time Series Observation. + /// + /// The zero-based sample position. + /// The composed Time Series value key. public static string CreateTimeSeriesValueKey(int index) => $"{TimeSeriesPrefix}[{index.ToString("00000")}]"; + /// + /// Extracts the sample position encoded in a Time Series value key. + /// + /// The Time Series value key to parse. + /// The zero-based sample position, or -1 when the key is not a Time Series key. public static int GetTimeSeriesIndex(string valueKey) { if (!string.IsNullOrEmpty(valueKey)) @@ -55,6 +102,11 @@ public static int GetTimeSeriesIndex(string valueKey) return -1; } + /// + /// Determines whether the given value key identifies a Time Series sample. + /// + /// The value key to test. + /// True when the key uses the Time Series prefix; otherwise false. public static bool IsTimeSeriesKey(string valueKey) { if (!string.IsNullOrEmpty(valueKey)) @@ -69,8 +121,18 @@ public static bool IsTimeSeriesKey(string valueKey) #region "DataSet" + /// + /// Builds the value key for the entry stored under the given key in a Data Set Observation. + /// + /// The Data Set entry key. + /// The composed Data Set value key. public static string CreateDataSetValueKey(string key) => $"{DataSetPrefix}[{key}]"; + /// + /// Extracts the entry key encoded in a Data Set value key. + /// + /// The Data Set value key to parse. + /// The entry key, or null when the value key is not a Data Set key. public static string GetDataSetKey(string valueKey) { if (!string.IsNullOrEmpty(valueKey) && valueKey.Length > DataSetPrefix.Length) @@ -97,6 +159,11 @@ public static string GetDataSetKey(string valueKey) return null; } + /// + /// Determines whether the given value key identifies a Data Set entry. + /// + /// The value key to test. + /// True when the key uses the Data Set prefix; otherwise false. public static bool IsDataSetKey(string valueKey) { if (!string.IsNullOrEmpty(valueKey)) @@ -111,6 +178,12 @@ public static bool IsDataSetKey(string valueKey) #region "Table" + /// + /// Builds the value key for a Table Observation entry, optionally addressing an individual cell. + /// + /// The Table entry (row) key. + /// The optional cell (column) key within the entry. + /// The composed Table value key. public static string CreateTableValueKey(string key, string cellKey = null) { if (!string.IsNullOrEmpty(cellKey)) @@ -123,6 +196,11 @@ public static string CreateTableValueKey(string key, string cellKey = null) } } + /// + /// Determines whether the given value key identifies a Table entry. + /// + /// The value key to test. + /// True when the key uses the Table prefix; otherwise false. public static bool IsTableKey(string valueKey) { if (!string.IsNullOrEmpty(valueKey)) @@ -133,6 +211,11 @@ public static bool IsTableKey(string valueKey) return false; } + /// + /// Extracts the entry (row) key encoded in a Table value key. + /// + /// The Table value key to parse. + /// The entry key, or null when the value key is not a Table key. public static string GetTableKey(string valueKey) { if (!string.IsNullOrEmpty(valueKey) && valueKey.Length > TablePrefix.Length) @@ -159,6 +242,11 @@ public static string GetTableKey(string valueKey) return null; } + /// + /// Extracts the cell (column) key encoded in a Table value key. + /// + /// The Table value key to parse. + /// The cell key, or null when the value key does not address a cell. public static string GetTableCellKey(string valueKey) { if (!string.IsNullOrEmpty(valueKey) && valueKey.Length > TablePrefix.Length) @@ -190,6 +278,11 @@ public static string GetTableCellKey(string valueKey) #endregion + /// + /// Returns the PascalCase form of a value key, caching the conversion for reuse. + /// + /// The value key to convert. + /// The PascalCase key, or null when is null or empty. public static string GetPascalCaseKey(string key) { if (!string.IsNullOrEmpty(key)) @@ -207,6 +300,11 @@ public static string GetPascalCaseKey(string key) return null; } + /// + /// Returns the camelCase form of a value key, caching the conversion for reuse. + /// + /// The value key to convert. + /// The camelCase key, or null when is null or empty. public static string GetCamelCaseKey(string key) { if (!string.IsNullOrEmpty(key)) diff --git a/libraries/MTConnect.NET-Common/Observations/ValueKeysDescriptions.cs b/libraries/MTConnect.NET-Common/Observations/ValueKeysDescriptions.cs index 91828b83c..8f1fc54d1 100644 --- a/libraries/MTConnect.NET-Common/Observations/ValueKeysDescriptions.cs +++ b/libraries/MTConnect.NET-Common/Observations/ValueKeysDescriptions.cs @@ -3,6 +3,9 @@ namespace MTConnect.Observations { + /// + /// Provides the human-readable description for each well-known Observation value key. + /// public static class ValueKeysDescriptions { /// @@ -31,6 +34,11 @@ public static class ValueKeysDescriptions public const string Qualifier = "Qualifies the Condition and adds context or additional clarification."; + /// + /// Returns the human-readable description for the given Observation value key. + /// + /// The value key to describe. + /// The description text, or an empty string for an unrecognized key. public static string Get(string valueKey) { switch (valueKey) diff --git a/libraries/MTConnect.NET-Common/Position3D.cs b/libraries/MTConnect.NET-Common/Position3D.cs index de120c3b5..a28a77b92 100644 --- a/libraries/MTConnect.NET-Common/Position3D.cs +++ b/libraries/MTConnect.NET-Common/Position3D.cs @@ -5,18 +5,36 @@ namespace MTConnect { + /// + /// A Cartesian position in three dimensions, serialized as the MTConnect space-separated "X Y Z" string form. + /// public class Position3D { private static readonly Regex _regex = new Regex(@"([0-9\.]*) ([0-9\.]*) ([0-9\.]*)"); + /// + /// The X coordinate. + /// public double X { get; set; } + /// + /// The Y coordinate. + /// public double Y { get; set; } + /// + /// The Z coordinate. + /// public double Z { get; set; } + /// + /// Initializes a position from its three coordinates. + /// + /// The X coordinate. + /// The Y coordinate. + /// The Z coordinate. public Position3D(double x, double y, double z) { X = x; @@ -24,11 +42,18 @@ public Position3D(double x, double y, double z) Z = z; } + /// + /// Renders the position in the MTConnect space-separated "X Y Z" form. + /// public override string ToString() { return $"{X} {Y} {Z}"; } + /// + /// Parses a space-separated "X Y Z" string into a position; returns null when the input is empty or does not match the expected form. + /// + /// The space-separated coordinate triple. public static Position3D FromString(string input) { if (!string.IsNullOrEmpty(input)) diff --git a/libraries/MTConnect.NET-Common/README.md b/libraries/MTConnect.NET-Common/README.md index 28d421395..3317b1b9c 100644 --- a/libraries/MTConnect.NET-Common/README.md +++ b/libraries/MTConnect.NET-Common/README.md @@ -1,7 +1,9 @@ ![MTConnect.NET Logo](https://raw.githubusercontent.com/TrakHound/MTConnect.NET/master/img/mtconnect-net-03-md.png) # MTConnect.NET-Common -This libary project contains the basic classes for implementing MTConnect +This libary project contains the basic classes for implementing MTConnect. + +For end-to-end narrative documentation, concept pages, and the generated API reference, see [docs/](../../docs/). ## Nuget
diff --git a/libraries/MTConnect.NET-Common/Streams/Output/ComponentStreamOutput.cs b/libraries/MTConnect.NET-Common/Streams/Output/ComponentStreamOutput.cs index 74715ae60..c179331c3 100644 --- a/libraries/MTConnect.NET-Common/Streams/Output/ComponentStreamOutput.cs +++ b/libraries/MTConnect.NET-Common/Streams/Output/ComponentStreamOutput.cs @@ -55,8 +55,15 @@ public IObservationOutput[] Observations } + /// + /// Initializes an empty component stream output. + /// public ComponentStreamOutput() { } + /// + /// Builds a component stream output from a deserialized component stream, copying its component identity and observations; a null source leaves the output empty. + /// + /// The source component stream. public ComponentStreamOutput(IComponentStream componentStream) { if (componentStream != null) diff --git a/libraries/MTConnect.NET-Common/Streams/Output/DeviceStreamOutput.cs b/libraries/MTConnect.NET-Common/Streams/Output/DeviceStreamOutput.cs index 544193855..06898a31b 100644 --- a/libraries/MTConnect.NET-Common/Streams/Output/DeviceStreamOutput.cs +++ b/libraries/MTConnect.NET-Common/Streams/Output/DeviceStreamOutput.cs @@ -51,8 +51,15 @@ public IEnumerable Observations } + /// + /// Initializes an empty device stream output. + /// public DeviceStreamOutput() { } + /// + /// Builds a device stream output from a deserialized device stream, copying its device identity and projecting its component streams; a null source leaves the output empty. + /// + /// The source device stream. public DeviceStreamOutput(IDeviceStream deviceStream) { if (deviceStream != null) diff --git a/libraries/MTConnect.NET-Common/Streams/Output/IStreamsResponseOutputDocument.cs b/libraries/MTConnect.NET-Common/Streams/Output/IStreamsResponseOutputDocument.cs index 050d8a864..d589debf3 100644 --- a/libraries/MTConnect.NET-Common/Streams/Output/IStreamsResponseOutputDocument.cs +++ b/libraries/MTConnect.NET-Common/Streams/Output/IStreamsResponseOutputDocument.cs @@ -33,10 +33,19 @@ public interface IStreamsResponseOutputDocument /// IEnumerable GetObservations(); + /// + /// The sequence number of the earliest observation included in this document. + /// ulong FirstObservationSequence { get; } + /// + /// The sequence number of the latest observation included in this document. + /// ulong LastObservationSequence { get; } + /// + /// The total number of observations included in this document. + /// uint ObservationCount { get; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-Common/Streams/Output/StreamsResponseOutputDocument.cs b/libraries/MTConnect.NET-Common/Streams/Output/StreamsResponseOutputDocument.cs index fdad612ea..4b04670f7 100644 --- a/libraries/MTConnect.NET-Common/Streams/Output/StreamsResponseOutputDocument.cs +++ b/libraries/MTConnect.NET-Common/Streams/Output/StreamsResponseOutputDocument.cs @@ -28,16 +28,32 @@ public class StreamsResponseOutputDocument : IStreamsResponseOutputDocument /// public Version Version { get; set; } + /// + /// The sequence number of the earliest observation included in this document. + /// public ulong FirstObservationSequence { get; set; } + /// + /// The sequence number of the latest observation included in this document. + /// public ulong LastObservationSequence { get; set; } + /// + /// The total number of observations included in this document. + /// public uint ObservationCount { get; set; } + /// + /// Initializes an empty streams output document. + /// public StreamsResponseOutputDocument() { } - public StreamsResponseOutputDocument(IStreamsResponseDocument document) + /// + /// Builds an output document from a deserialized streams response, copying its header and version and projecting each device stream into its output representation; a null source yields an empty document. + /// + /// The source streams response document. + public StreamsResponseOutputDocument(IStreamsResponseDocument document) { if (document != null) { @@ -57,6 +73,9 @@ public StreamsResponseOutputDocument(IStreamsResponseDocument document) } + /// + /// Flattens the document's device streams into a single sequence of all contained observation outputs. + /// public IEnumerable GetObservations() { if (!Streams.IsNullOrEmpty()) diff --git a/libraries/MTConnect.NET-Common/Streams/StreamsResponseDocument.cs b/libraries/MTConnect.NET-Common/Streams/StreamsResponseDocument.cs index c4b5aad39..7044edb9d 100644 --- a/libraries/MTConnect.NET-Common/Streams/StreamsResponseDocument.cs +++ b/libraries/MTConnect.NET-Common/Streams/StreamsResponseDocument.cs @@ -29,6 +29,9 @@ public class StreamsResponseDocument : IStreamsResponseDocument public Version Version { get; set; } + /// + /// Flattens the document's per-device and per-component streams into a single sequence of all contained observations. + /// public IEnumerable GetObservations() { if (!Streams.IsNullOrEmpty()) diff --git a/libraries/MTConnect.NET-Common/UnitVector3D.cs b/libraries/MTConnect.NET-Common/UnitVector3D.cs index b11389306..9a521f2c3 100644 --- a/libraries/MTConnect.NET-Common/UnitVector3D.cs +++ b/libraries/MTConnect.NET-Common/UnitVector3D.cs @@ -10,13 +10,28 @@ namespace MTConnect /// public class UnitVector3D { + /// + /// The X component of the unit vector. + /// public double X { get; set; } + /// + /// The Y component of the unit vector. + /// public double Y { get; set; } + /// + /// The Z component of the unit vector. + /// public double Z { get; set; } + /// + /// Initializes a unit vector from its three components (the caller is responsible for supplying a normalized vector). + /// + /// The X component. + /// The Y component. + /// The Z component. public UnitVector3D(double x, double y, double z) { X = x; @@ -24,11 +39,18 @@ public UnitVector3D(double x, double y, double z) Z = z; } + /// + /// Renders the vector in the MTConnect space-separated "X Y Z" form. + /// public override string ToString() { return $"{X} {Y} {Z}"; } + /// + /// Parses a space-separated "X Y Z" string into a unit vector; returns null when the input is empty or does not match the expected form. + /// + /// The space-separated component triple. public static UnitVector3D FromString(string input) { if (!string.IsNullOrEmpty(input)) diff --git a/libraries/MTConnect.NET-Common/UnixTime.cs b/libraries/MTConnect.NET-Common/UnixTime.cs index b24341737..f771a8daf 100644 --- a/libraries/MTConnect.NET-Common/UnixTime.cs +++ b/libraries/MTConnect.NET-Common/UnixTime.cs @@ -10,6 +10,9 @@ namespace MTConnect /// public static class UnixDateTime { + /// + /// The current UTC instant expressed in Unix ticks (tenths of a microsecond since the Unix epoch). + /// public static long Now { get @@ -20,12 +23,26 @@ public static long Now } + /// + /// Conversions between and the Unix-tick representation MTConnect uses for observation timestamps. + /// public static class UnixTimeExtensions { + /// + /// The Unix epoch (1970-01-01T00:00:00Z) used as the reference point for tick conversions. + /// public static readonly DateTime EpochTime = new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Utc); + + /// + /// The number of .NET ticks between DateTime.MinValue and the Unix epoch. + /// public const long EpochTicks = 621355968000000000; + /// + /// Converts a DateTime to Unix ticks since the epoch, converting a Local value to UTC first; an Unspecified value is treated as UTC. + /// + /// The DateTime to convert. public static long ToUnixTime(this DateTime d) { var x = d; @@ -68,16 +85,28 @@ public static long ToUnixUTCTime(this DateTime d, DateTimeKind unspecifiedAssume => ToUnixUtcTime(d, unspecifiedAssume); + /// + /// Converts Unix ticks since the epoch to a UTC . + /// + /// The Unix ticks to convert. public static DateTime ToDateTime(this long unixTicks) { return FromUnixTime(unixTicks); } + /// + /// Converts Unix ticks since the epoch to a in the local time zone. + /// + /// The Unix ticks to convert. public static DateTime ToLocalDateTime(this long unixTicks) { return FromUnixTime(unixTicks).ToLocalTime(); } + /// + /// Converts Unix ticks since the epoch to a UTC by adding them to . + /// + /// The Unix ticks to convert. public static DateTime FromUnixTime(long unixTicks) { return EpochTime.AddTicks(unixTicks); diff --git a/libraries/MTConnect.NET-DeviceFinder/AddressRange.cs b/libraries/MTConnect.NET-DeviceFinder/AddressRange.cs index 76caf5184..cad15f4a3 100644 --- a/libraries/MTConnect.NET-DeviceFinder/AddressRange.cs +++ b/libraries/MTConnect.NET-DeviceFinder/AddressRange.cs @@ -8,17 +8,25 @@ namespace MTConnect.DeviceFinder /// public class AddressRange { + /// The lowest IPv4 address (inclusive) in dotted-quad form that the finder is allowed to probe. public string Minimum { get; set; } + /// The highest IPv4 address (inclusive) in dotted-quad form that the finder is allowed to probe. public string Maximum { get; set; } + /// Optional explicit allow-list; if set, only these addresses inside the [, ] range are probed. public string[] AllowedAddresses { get; set; } + /// Optional explicit deny-list; addresses inside the range that match an entry here are skipped during probing. public string[] DeniedAddresses { get; set; } + /// Creates an empty range; / must be set before the finder uses the range. public AddressRange() { } + /// Creates a range bounded by the supplied minimum and maximum addresses. + /// The lowest IPv4 address (inclusive) in dotted-quad form. + /// The highest IPv4 address (inclusive) in dotted-quad form. public AddressRange(string minimum, string maximum) { Minimum = minimum; diff --git a/libraries/MTConnect.NET-DeviceFinder/IPNetwork/IPNetwork.cs b/libraries/MTConnect.NET-DeviceFinder/IPNetwork/IPNetwork.cs index 72a0e8160..997598732 100644 --- a/libraries/MTConnect.NET-DeviceFinder/IPNetwork/IPNetwork.cs +++ b/libraries/MTConnect.NET-DeviceFinder/IPNetwork/IPNetwork.cs @@ -1767,7 +1767,8 @@ private static void InternalWideSubnet(bool tryWide, IPNetwork[] ipnetworks, out IPNetwork[] nnin = Array.FindAll(ipnetworks, new Predicate( - delegate (IPNetwork ipnet) { + delegate (IPNetwork ipnet) + { return ipnet != null; } )); diff --git a/libraries/MTConnect.NET-DeviceFinder/MTConnectDevice.cs b/libraries/MTConnect.NET-DeviceFinder/MTConnectDevice.cs index d785f14bc..bf55281ed 100644 --- a/libraries/MTConnect.NET-DeviceFinder/MTConnectDevice.cs +++ b/libraries/MTConnect.NET-DeviceFinder/MTConnectDevice.cs @@ -62,6 +62,12 @@ public struct MTConnectDevice public string Station { get; set; } + /// Constructs a discovered device record from the network-layer details and the UUID/name probed from the agent. + /// The IP address that responded to the probe. + /// The TCP port the MTConnect agent is listening on. + /// The MAC address resolved for on the local segment. + /// The UUID returned in the probe response. + /// The device name returned in the probe response. public MTConnectDevice( IPAddress ipAddress, int port, diff --git a/libraries/MTConnect.NET-DeviceFinder/MTConnectDeviceFinder.cs b/libraries/MTConnect.NET-DeviceFinder/MTConnectDeviceFinder.cs index c1f0710e9..fc0027ff5 100644 --- a/libraries/MTConnect.NET-DeviceFinder/MTConnectDeviceFinder.cs +++ b/libraries/MTConnect.NET-DeviceFinder/MTConnectDeviceFinder.cs @@ -27,19 +27,43 @@ public class MTConnectDeviceFinder private int sentPortRequests = 0; private int receivedPortRequests = 0; + /// Delegate fired by when an MTConnect agent has been positively identified at an address/port pair. public delegate void DeviceHandler(MTConnectDeviceFinder sender, MTConnectDevice device); + + /// Delegate fired by ; carries the elapsed milliseconds of the search. public delegate void RequestStatusHandler(MTConnectDeviceFinder sender, long milliseconds); + + /// Delegate fired by once a ping has been dispatched to . public delegate void PingSentHandler(MTConnectDeviceFinder sender, IPAddress address); + + /// Delegate fired by when a ping reply (success or timeout) returns from . public delegate void PingReceivedHandler(MTConnectDeviceFinder sender, IPAddress address, PingReply reply); + + /// Delegate fired by / to report the state of a TCP port at . public delegate void PortRequestHandler(MTConnectDeviceFinder sender, IPAddress address, int port); + + /// Delegate fired by // for each MTConnect probe attempt. public delegate void ProbeRequestHandler(MTConnectDeviceFinder sender, IPAddress address, int port); + /// Raised after a ping has been dispatched to a candidate address. public event PingSentHandler PingSent; + + /// Raised when the ping reply (success or timeout) returns; reachable addresses move on to the port-scan phase. public event PingReceivedHandler PingReceived; + + /// Raised when a TCP connect to a candidate port succeeds; the address/port becomes a probe target. public event PortRequestHandler PortOpened; + + /// Raised when a TCP connect to a candidate port fails or times out; the port is dropped. public event PortRequestHandler PortClosed; + + /// Raised before each MTConnect probe request is sent to an open port. public event ProbeRequestHandler ProbeSent; + + /// Raised when a probe response is parsed successfully; immediately followed by . public event ProbeRequestHandler ProbeSuccessful; + + /// Raised when a probe attempt fails (HTTP error, parse failure, non-MTConnect response). public event ProbeRequestHandler ProbeError; @@ -99,11 +123,15 @@ public class MTConnectDeviceFinder public event RequestStatusHandler SearchCompleted; + /// Constructs the finder bound to the first reachable network interface; call after configuring and . public MTConnectDeviceFinder() { Init(); } + /// Constructs the finder bound to a specific network interface. + /// The .NET of the interface to use for outbound probes. + /// The human-readable description of the same interface (used in logging events). public MTConnectDeviceFinder(string interfaceId, string interfaceDescription) { InterfaceId = interfaceId; @@ -329,7 +357,7 @@ private void SendProbe(IPAddress address, int port) foundDevice.MacAddress = macAddress; foundDevice.Name = device.Name; foundDevice.Uuid = device.Uuid; - + if (device.Description != null) { foundDevice.Manufacturer = device.Description.Manufacturer; diff --git a/libraries/MTConnect.NET-DeviceFinder/PortRange.cs b/libraries/MTConnect.NET-DeviceFinder/PortRange.cs index 154e63032..c97b0ab08 100644 --- a/libraries/MTConnect.NET-DeviceFinder/PortRange.cs +++ b/libraries/MTConnect.NET-DeviceFinder/PortRange.cs @@ -8,17 +8,25 @@ namespace MTConnect.DeviceFinder /// public class PortRange { + /// The lowest TCP port (inclusive) the finder is allowed to probe. public int Minimum { get; set; } + /// The highest TCP port (inclusive) the finder is allowed to probe. public int Maximum { get; set; } + /// Optional explicit allow-list; if set, only these ports inside the [, ] range are probed. public int[] AllowedPorts { get; set; } + /// Optional explicit deny-list; ports inside the range that appear here are skipped during probing. public int[] DeniedPorts { get; set; } + /// Creates an empty range; / must be set before the finder uses the range. public PortRange() { } + /// Creates a range bounded by the supplied minimum and maximum port numbers. + /// The lowest TCP port (inclusive). + /// The highest TCP port (inclusive). public PortRange(int minimum, int maximum) { Minimum = minimum; diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Common/AppDomainTask.cs b/libraries/MTConnect.NET-HTTP/Ceen/Common/AppDomainTask.cs index 78b1a2e25..289ce4f7f 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Common/AppDomainTask.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Common/AppDomainTask.cs @@ -3,75 +3,75 @@ namespace Ceen { - /// - /// Implementation of a Task that works across app domains - /// - internal class AppDomainTask : MarshalByRefObject - { - /// - /// A task completion source - /// - private TaskCompletionSource m_tcs = new TaskCompletionSource(TaskCreationOptions.RunContinuationsAsynchronously); + /// + /// Implementation of a Task that works across app domains + /// + internal class AppDomainTask : MarshalByRefObject + { + /// + /// A task completion source + /// + private TaskCompletionSource m_tcs = new TaskCompletionSource(TaskCreationOptions.RunContinuationsAsynchronously); - /// - /// Marks the operation complete - /// - /// The object to return. - public void SetComplete(object data) - { - m_tcs.TrySetResult(data); - } + /// + /// Marks the operation complete + /// + /// The object to return. + public void SetComplete(object data) + { + m_tcs.TrySetResult(data); + } - /// - /// Marks the operation cancelled - /// - public void SetCancelled() - { - m_tcs.TrySetCanceled(); - } + /// + /// Marks the operation cancelled + /// + public void SetCancelled() + { + m_tcs.TrySetCanceled(); + } - /// - /// Sets the operation failed. - /// - /// The exception, must be serializable or marshalbyref. - public void SetFailed(Exception ex) - { - m_tcs.TrySetException(ex); - } + /// + /// Sets the operation failed. + /// + /// The exception, must be serializable or marshalbyref. + public void SetFailed(Exception ex) + { + m_tcs.TrySetException(ex); + } - /// - /// Gets the result async - /// - /// The awaitable result. - public Task ResultAsync() - { - return m_tcs.Task; - } + /// + /// Gets the result async + /// + /// The awaitable result. + public Task ResultAsync() + { + return m_tcs.Task; + } - /// - /// Handles a task by invoking the AppDomainTask after completion - /// - /// The running task. - /// The handler for the result. - /// The data type parameter. - public static void HandleTask(Task sourcetask, AppDomainTask handler) - { - sourcetask.ContinueWith(task => - { - if (task.IsCanceled) - handler.SetCancelled(); - else if (task.IsFaulted) - { - if (task.Exception == null) - handler.SetFailed(new Exception()); - else if (task.Exception.GetType().IsSerializable) - handler.SetFailed(task.Exception); - else - handler.SetFailed(new Exception(task.Exception.Message)); - } - else - handler.SetComplete(task.Result); - }); - } - } + /// + /// Handles a task by invoking the AppDomainTask after completion + /// + /// The running task. + /// The handler for the result. + /// The data type parameter. + public static void HandleTask(Task sourcetask, AppDomainTask handler) + { + sourcetask.ContinueWith(task => + { + if (task.IsCanceled) + handler.SetCancelled(); + else if (task.IsFaulted) + { + if (task.Exception == null) + handler.SetFailed(new Exception()); + else if (task.Exception.GetType().IsSerializable) + handler.SetFailed(task.Exception); + else + handler.SetFailed(new Exception(task.Exception.Message)); + } + else + handler.SetComplete(task.Result); + }); + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Common/AsyncLock.cs b/libraries/MTConnect.NET-HTTP/Ceen/Common/AsyncLock.cs index fbe236504..99e54af96 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Common/AsyncLock.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Common/AsyncLock.cs @@ -13,123 +13,123 @@ namespace Ceen /// Implementation of a Semaphore that is usable with await statements /// internal class AsyncSemaphore - { - /// - /// A task signaling completion - /// - private readonly static Task m_completed = Task.FromResult(true); - /// - /// The list of waiters - /// - private readonly Queue, IDisposable>> m_waiters = new Queue, IDisposable>>(); - /// - /// The additional number of release calls - /// - private int m_currentCount; - - /// - /// Initializes a new instance of the class. - /// - /// The number of callers to allow before blocking. - public AsyncSemaphore(int initialCount) - { - if (initialCount < 0) - throw new ArgumentOutOfRangeException(nameof(initialCount)); - - m_currentCount = initialCount; - } - - /// - /// Waits for the semaphire to be released - /// - /// The cancellation token - /// The awaitable task. - public Task WaitAsync(CancellationToken token = default(CancellationToken)) - { - if (token.IsCancellationRequested) - { - return Task.FromCanceled(token); - } - - lock (m_waiters) - { - if (m_currentCount > 0) - { - --m_currentCount; - return m_completed; - } - else - { - var waiter = new TaskCompletionSource(TaskCreationOptions.RunContinuationsAsynchronously); - - // Make sure the waiter returns asap on cancellation - var registrar = - token.CanBeCanceled - ? token.Register(() => waiter.TrySetCanceled()) - : (IDisposable)null; - - m_waiters.Enqueue(new KeyValuePair, IDisposable>(waiter, registrar)); - return waiter.Task; - } - } - } - - /// - /// Releases the semaphore to a new - /// - public void Release() - { - TaskCompletionSource result = null; - lock (m_waiters) - { - while (m_waiters.Count > 0) - { - var res = m_waiters.Dequeue(); - - // Clear the cancellation event to avoid races - if (res.Value != null) - res.Value.Dispose(); - - if (!res.Key.Task.IsCanceled && !res.Key.Task.IsFaulted) - { - result = res.Key; - break; - } - } - - if (result == null) - ++m_currentCount; - } - if (result != null) - Task.Run(() => result.SetResult(true)); - } - } - - /// - /// Implementation of a lock construct that can be used with await statements, - /// note that this lock is not re-entrant like the regular monitors used - /// with the lock statement. - /// - public class AsyncLock - { - /// - /// The semaphore that provides the general functionality of this lock - /// - private readonly AsyncSemaphore m_semaphore; - - /// - /// The task used to encapsulate the lock - /// - private readonly Task m_releaser; - - /// - /// Initializes a new instance of the class. - /// - public AsyncLock() - { - m_semaphore = new AsyncSemaphore(1); - m_releaser = Task.FromResult(new Releaser(this)); - } + { + /// + /// A task signaling completion + /// + private readonly static Task m_completed = Task.FromResult(true); + /// + /// The list of waiters + /// + private readonly Queue, IDisposable>> m_waiters = new Queue, IDisposable>>(); + /// + /// The additional number of release calls + /// + private int m_currentCount; + + /// + /// Initializes a new instance of the class. + /// + /// The number of callers to allow before blocking. + public AsyncSemaphore(int initialCount) + { + if (initialCount < 0) + throw new ArgumentOutOfRangeException(nameof(initialCount)); + + m_currentCount = initialCount; + } + + /// + /// Waits for the semaphire to be released + /// + /// The cancellation token + /// The awaitable task. + public Task WaitAsync(CancellationToken token = default(CancellationToken)) + { + if (token.IsCancellationRequested) + { + return Task.FromCanceled(token); + } + + lock (m_waiters) + { + if (m_currentCount > 0) + { + --m_currentCount; + return m_completed; + } + else + { + var waiter = new TaskCompletionSource(TaskCreationOptions.RunContinuationsAsynchronously); + + // Make sure the waiter returns asap on cancellation + var registrar = + token.CanBeCanceled + ? token.Register(() => waiter.TrySetCanceled()) + : (IDisposable)null; + + m_waiters.Enqueue(new KeyValuePair, IDisposable>(waiter, registrar)); + return waiter.Task; + } + } + } + + /// + /// Releases the semaphore to a new + /// + public void Release() + { + TaskCompletionSource result = null; + lock (m_waiters) + { + while (m_waiters.Count > 0) + { + var res = m_waiters.Dequeue(); + + // Clear the cancellation event to avoid races + if (res.Value != null) + res.Value.Dispose(); + + if (!res.Key.Task.IsCanceled && !res.Key.Task.IsFaulted) + { + result = res.Key; + break; + } + } + + if (result == null) + ++m_currentCount; + } + if (result != null) + Task.Run(() => result.SetResult(true)); + } + } + + /// + /// Implementation of a lock construct that can be used with await statements, + /// note that this lock is not re-entrant like the regular monitors used + /// with the lock statement. + /// + public class AsyncLock + { + /// + /// The semaphore that provides the general functionality of this lock + /// + private readonly AsyncSemaphore m_semaphore; + + /// + /// The task used to encapsulate the lock + /// + private readonly Task m_releaser; + + /// + /// Initializes a new instance of the class. + /// + public AsyncLock() + { + m_semaphore = new AsyncSemaphore(1); + m_releaser = Task.FromResult(new Releaser(this)); + } /// /// Runs an action with the lock active @@ -143,30 +143,30 @@ public AsyncLock() action(); } - /// - /// Runs an action with the lock active - /// - /// The lock async. - /// The action to execute. - /// The cancellation token. - public async Task LockedAsync(Func action, CancellationToken token = default(CancellationToken)) - { - using (await LockAsync(token)) - await action(); - } - - /// - /// Runs an action with the lock active - /// - /// The lock async. - /// The action to execute. - /// The cancellation token. + /// + /// Runs an action with the lock active + /// + /// The lock async. + /// The action to execute. + /// The cancellation token. + public async Task LockedAsync(Func action, CancellationToken token = default(CancellationToken)) + { + using (await LockAsync(token)) + await action(); + } + + /// + /// Runs an action with the lock active + /// + /// The lock async. + /// The action to execute. + /// The cancellation token. /// The type of the return data - public async Task LockedAsync(Func> action, CancellationToken token = default(CancellationToken)) - { - using (await LockAsync(token)) - return await action(); - } + public async Task LockedAsync(Func> action, CancellationToken token = default(CancellationToken)) + { + using (await LockAsync(token)) + return await action(); + } /// /// Runs an action with the lock active @@ -187,65 +187,65 @@ public AsyncLock() /// The cancellation token /// The async. public Task LockAsync(CancellationToken token = default(CancellationToken)) - { - var wait = m_semaphore.WaitAsync(token); - - return wait.IsCompleted ? - m_releaser : - wait.ContinueWith( - (_, state) => new Releaser((AsyncLock)state), - this, - - // The token is signalling the wait task, so we do not cancel here - CancellationToken.None, - - // Only if we actually have the lock, should we return the releaser - TaskContinuationOptions.ExecuteSynchronously | TaskContinuationOptions.OnlyOnRanToCompletion, - TaskScheduler.Default); - } - - /// - /// Internal releaser construct which needs to be disposed to unlock - /// - public struct Releaser : IDisposable - { - /// - /// The parent instance - /// - private readonly AsyncLock m_parent; - - /// - /// A value indicating if the lock can be disposed - /// - private bool m_canDispose; - - /// - /// Initializes a new instance of the struct. - /// - /// The parent lock. - internal Releaser(AsyncLock parent) - { - m_parent = parent; - m_canDispose = true; - } - - /// - /// Releases all resource used by the object. - /// - /// Call when you are finished using the . The - /// method leaves the in an unusable state. After - /// calling , you must release all references to the so - /// the garbage collector can reclaim the memory that the was occupying. - public void Dispose() - { - if (m_parent != null) - lock (m_parent) - if (m_canDispose) - { - m_parent.m_semaphore.Release(); - m_canDispose = false; - } - } - } - } + { + var wait = m_semaphore.WaitAsync(token); + + return wait.IsCompleted ? + m_releaser : + wait.ContinueWith( + (_, state) => new Releaser((AsyncLock)state), + this, + + // The token is signalling the wait task, so we do not cancel here + CancellationToken.None, + + // Only if we actually have the lock, should we return the releaser + TaskContinuationOptions.ExecuteSynchronously | TaskContinuationOptions.OnlyOnRanToCompletion, + TaskScheduler.Default); + } + + /// + /// Internal releaser construct which needs to be disposed to unlock + /// + public struct Releaser : IDisposable + { + /// + /// The parent instance + /// + private readonly AsyncLock m_parent; + + /// + /// A value indicating if the lock can be disposed + /// + private bool m_canDispose; + + /// + /// Initializes a new instance of the struct. + /// + /// The parent lock. + internal Releaser(AsyncLock parent) + { + m_parent = parent; + m_canDispose = true; + } + + /// + /// Releases all resource used by the object. + /// + /// Call when you are finished using the . The + /// method leaves the in an unusable state. After + /// calling , you must release all references to the so + /// the garbage collector can reclaim the memory that the was occupying. + public void Dispose() + { + if (m_parent != null) + lock (m_parent) + if (m_canDispose) + { + m_parent.m_semaphore.Release(); + m_canDispose = false; + } + } + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Common/Attributes.cs b/libraries/MTConnect.NET-HTTP/Ceen/Common/Attributes.cs index ee27d0f9b..13f0ad282 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Common/Attributes.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Common/Attributes.cs @@ -7,23 +7,23 @@ namespace Ceen /// be loaded before a method can be called /// internal class RequireHandlerAttribute : Attribute - { - /// - /// Gets or sets a value indicating whether derived handlers are allowed. - /// - public bool AllowDerived { get; set; } = true; - /// - /// Gets or sets the type of the required module. - /// - public Type RequiredType { get; set; } + { + /// + /// Gets or sets a value indicating whether derived handlers are allowed. + /// + public bool AllowDerived { get; set; } = true; + /// + /// Gets or sets the type of the required module. + /// + public Type RequiredType { get; set; } - /// - /// Creates a new handler attribute - /// - /// The type of the required module. - public RequireHandlerAttribute(Type requiredtype) - { - RequiredType = requiredtype; - } - } + /// + /// Creates a new handler attribute + /// + /// The type of the required module. + public RequireHandlerAttribute(Type requiredtype) + { + RequiredType = requiredtype; + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Common/ContextUtility.cs b/libraries/MTConnect.NET-HTTP/Ceen/Common/ContextUtility.cs index 4dbe29f63..2ccf1dcc6 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Common/ContextUtility.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Common/ContextUtility.cs @@ -53,9 +53,10 @@ public void Dispose() /// /// The loader scope, using AsyncLocal /// - private static readonly System.Threading.AsyncLocal m_activeContext - = new System.Threading.AsyncLocal() { - Value = new ContextKeeper() + private static readonly System.Threading.AsyncLocal m_activeContext + = new System.Threading.AsyncLocal() + { + Value = new ContextKeeper() }; /// @@ -82,11 +83,11 @@ public static T EnsureSingletonInstance(Func creator) throw new ArgumentException("Cannot register instance after the context is frozen"); if (c.Instances.TryGetValue(typeof(T), out var n)) return (T)n; - + var inst = creator(); if (inst == null) throw new ArgumentException($"Creator function did not return an instance for type {typeof(T)}"); - + // Re-check, in case the creation of the item registers itself if (c.Instances.TryGetValue(typeof(T), out n)) return (T)n; @@ -218,7 +219,7 @@ public static Task LogDebugAsync(string message, Exception ex = null) public static Task LogDebugAsync(Exception ex) { return Current.LogDebugAsync(null, ex); - } + } /// /// Logs an error message diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Common/DerivedSettings.cs b/libraries/MTConnect.NET-HTTP/Ceen/Common/DerivedSettings.cs index 390645f82..b4a15c3b6 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Common/DerivedSettings.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Common/DerivedSettings.cs @@ -8,62 +8,62 @@ namespace Ceen /// A class that allows a base class to store common settings, that can then be overridden in the sub-classes /// internal abstract class DerivedSettings - { - /// - /// The base dictionary with all the settings - /// - // NOTE: Since this is a generic type, we get one _basesettings instance pr. TBaseClass as intended - protected static readonly Dictionary _basesettings = new Dictionary(); + { + /// + /// The base dictionary with all the settings + /// + // NOTE: Since this is a generic type, we get one _basesettings instance pr. TBaseClass as intended + protected static readonly Dictionary _basesettings = new Dictionary(); - /// - /// The instance setting overrides - /// - protected readonly Dictionary m_setttings = new Dictionary(); + /// + /// The instance setting overrides + /// + protected readonly Dictionary m_setttings = new Dictionary(); - /// - /// Gets the value for a given property. - /// - /// The value to get. - /// The name of the property. - /// The property type. - protected T GetValue([CallerMemberName] string propname = null) - { - if (propname == null) - throw new ArgumentNullException(nameof(propname)); + /// + /// Gets the value for a given property. + /// + /// The value to get. + /// The name of the property. + /// The property type. + protected T GetValue([CallerMemberName] string propname = null) + { + if (propname == null) + throw new ArgumentNullException(nameof(propname)); - if (this.GetType() != typeof(TBaseClass)) - { - object vx; - if (m_setttings.TryGetValue(propname, out vx)) - { - if (vx == null) - return default(T); - else - return (T)vx; - } - } + if (this.GetType() != typeof(TBaseClass)) + { + object vx; + if (m_setttings.TryGetValue(propname, out vx)) + { + if (vx == null) + return default(T); + else + return (T)vx; + } + } - object v; - if (_basesettings.TryGetValue(propname, out v)) - if (v == null) - return default(T); - else - return (T)v; + object v; + if (_basesettings.TryGetValue(propname, out v)) + if (v == null) + return default(T); + else + return (T)v; - throw new ArgumentException($"No such property ${propname}"); - } + throw new ArgumentException($"No such property ${propname}"); + } - /// - /// Sets the value for a given property. - /// - /// The property name. - /// The value to set. - protected void SetValue(object o, [CallerMemberName] string propname = null) - { - if (this.GetType() != typeof(TBaseClass)) - m_setttings[propname] = o; - else - _basesettings[propname] = o; - } - } + /// + /// Sets the value for a given property. + /// + /// The property name. + /// The value to set. + protected void SetValue(object o, [CallerMemberName] string propname = null) + { + if (this.GetType() != typeof(TBaseClass)) + m_setttings[propname] = o; + else + _basesettings[propname] = o; + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Common/Exceptions.cs b/libraries/MTConnect.NET-HTTP/Ceen/Common/Exceptions.cs index 3a63442f2..c14b20df4 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Common/Exceptions.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Common/Exceptions.cs @@ -2,40 +2,40 @@ namespace Ceen { - /// - /// Implements an exception that should be reported to the client - /// as an HTTP error message - /// - [Serializable] + /// + /// Implements an exception that should be reported to the client + /// as an HTTP error message + /// + [Serializable] internal class HttpException : Exception - { - /// - /// Gets the status code. - /// - /// The status code. - public HttpStatusCode StatusCode { get; private set; } - /// - /// Gets the status message. - /// - /// The status message. - public string StatusMessage { get; private set; } + { + /// + /// Gets the status code. + /// + /// The status code. + public HttpStatusCode StatusCode { get; private set; } + /// + /// Gets the status message. + /// + /// The status message. + public string StatusMessage { get; private set; } - /// - /// Initializes a new instance of the class. - /// - public HttpException() - : this(HttpStatusCode.InternalServerError) - { - } + /// + /// Initializes a new instance of the class. + /// + public HttpException() + : this(HttpStatusCode.InternalServerError) + { + } - /// - /// Initializes a new instance of the class. - /// - /// The statuscode. - public HttpException(HttpStatusCode statuscode) - : this(statuscode, HttpStatusMessages.DefaultMessage(statuscode)) - { - } + /// + /// Initializes a new instance of the class. + /// + /// The statuscode. + public HttpException(HttpStatusCode statuscode) + : this(statuscode, HttpStatusMessages.DefaultMessage(statuscode)) + { + } /// /// Initializes a new instance of the class. @@ -72,42 +72,42 @@ public HttpException(System.Net.HttpStatusCode statuscode, string statusmessage) /// Exception indicating that the stream closed without sending content /// [Serializable] - public class EmptyStreamClosedException : Exception - { - } + public class EmptyStreamClosedException : Exception + { + } - /// - /// Exception indicating that a requirement failed - /// - [Serializable] - public class RequirementFailedException : Exception - { - /// - /// Initializes a new instance of the class. - /// - public RequirementFailedException() - { - } + /// + /// Exception indicating that a requirement failed + /// + [Serializable] + public class RequirementFailedException : Exception + { + /// + /// Initializes a new instance of the class. + /// + public RequirementFailedException() + { + } - /// - /// Initializes a new instance of the class. - /// - /// The message to report. - public RequirementFailedException(string message) - : base(message) - { - } + /// + /// Initializes a new instance of the class. + /// + /// The message to report. + public RequirementFailedException(string message) + : base(message) + { + } - /// - /// Initializes a new instance of the class. - /// - /// The message to report. - /// The inner exception. - public RequirementFailedException(string message, Exception innerException) - : base(message, innerException) - { - } - } + /// + /// Initializes a new instance of the class. + /// + /// The message to report. + /// The inner exception. + public RequirementFailedException(string message, Exception innerException) + : base(message, innerException) + { + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Common/HttpProtocolDefinitions.cs b/libraries/MTConnect.NET-HTTP/Ceen/Common/HttpProtocolDefinitions.cs index ee1545896..a4b11fb92 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Common/HttpProtocolDefinitions.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Common/HttpProtocolDefinitions.cs @@ -6,208 +6,208 @@ namespace Ceen /// List of supported HTTP status codes /// internal enum HttpStatusCode - { - Continue = 100, - SwitchingProtocols = 101, - Processing = 102, + { + Continue = 100, + SwitchingProtocols = 101, + Processing = 102, - OK = 200, - Created = 201, - Accepted = 202, - NonAuthoritative = 203, - NoContent = 204, - ResetContent = 205, - PartialContent = 206, - Multistatus = 207, - Alreadyreported = 208, + OK = 200, + Created = 201, + Accepted = 202, + NonAuthoritative = 203, + NoContent = 204, + ResetContent = 205, + PartialContent = 206, + Multistatus = 207, + Alreadyreported = 208, - MultipleChoices = 300, - MovedPermanently = 301, - Found = 302, - SeeOther = 303, - NotModified = 304, - UseProxy = 305, - SwitchProxy = 306, - TemporaryRedirect = 307, - PermanentRedirect = 308, + MultipleChoices = 300, + MovedPermanently = 301, + Found = 302, + SeeOther = 303, + NotModified = 304, + UseProxy = 305, + SwitchProxy = 306, + TemporaryRedirect = 307, + PermanentRedirect = 308, - BadRequest = 400, - Unauthorized = 401, - PaymentRequired = 402, - Forbidden = 403, - NotFound = 404, - MethodNotAllowed = 405, - NotAcceptable = 406, - ProxyAuthenticationRequired = 407, - RequestTimeout = 408, - Conflict = 409, - Gone = 410, - LengthRequired = 411, - PreconditionFailed = 412, - PayloadTooLarge = 413, - URITooLong = 414, - UnsupportedMediaType = 415, - RangeNotSatisfiable = 416, - ExpectationFailed = 417, - MisdirectedRequest = 421, - UnprocessableEntity = 422, - Locked = 423, - FailedDependency = 424, - UpgradeRequired = 426, - PreconditionRequired = 428, - TooManyRequests = 429, - RequestHeaderFieldsTooLarge = 431, - UnavailableForLegalReasons = 451, + BadRequest = 400, + Unauthorized = 401, + PaymentRequired = 402, + Forbidden = 403, + NotFound = 404, + MethodNotAllowed = 405, + NotAcceptable = 406, + ProxyAuthenticationRequired = 407, + RequestTimeout = 408, + Conflict = 409, + Gone = 410, + LengthRequired = 411, + PreconditionFailed = 412, + PayloadTooLarge = 413, + URITooLong = 414, + UnsupportedMediaType = 415, + RangeNotSatisfiable = 416, + ExpectationFailed = 417, + MisdirectedRequest = 421, + UnprocessableEntity = 422, + Locked = 423, + FailedDependency = 424, + UpgradeRequired = 426, + PreconditionRequired = 428, + TooManyRequests = 429, + RequestHeaderFieldsTooLarge = 431, + UnavailableForLegalReasons = 451, - InternalServerError = 500, - NotImplemented = 501, - BadGateway = 502, - ServiceUnavailable = 503, - GatewayTimeout = 504, - HTTPVersionNotSupported = 505, - VariantAlsoNegotiates = 506, - InsufficientStorage = 507, - LoopDetected = 508, - NotExtended = 510, - NetworkAuthenticationRequired = 511, - } + InternalServerError = 500, + NotImplemented = 501, + BadGateway = 502, + ServiceUnavailable = 503, + GatewayTimeout = 504, + HTTPVersionNotSupported = 505, + VariantAlsoNegotiates = 506, + InsufficientStorage = 507, + LoopDetected = 508, + NotExtended = 510, + NetworkAuthenticationRequired = 511, + } /// /// List of default messags to return for a HTTP status code /// internal static class HttpStatusMessages - { - public static string DefaultMessage(HttpStatusCode code) - { - switch ((int)code) - { - case 100: - return "Continue"; - case 101: - return "Switching Protocols"; - case 102: - return "Processing"; + { + public static string DefaultMessage(HttpStatusCode code) + { + switch ((int)code) + { + case 100: + return "Continue"; + case 101: + return "Switching Protocols"; + case 102: + return "Processing"; - case 200: - return "OK"; - case 201: - return "Created"; - case 202: - return "Accepted"; - case 203: - return "Non-Authoritative"; - case 204: - return "No Content"; - case 205: - return "Reset Content"; - case 206: - return "Partial Content"; - case 207: - return "Multi-status"; - case 208: - return "Already reported"; + case 200: + return "OK"; + case 201: + return "Created"; + case 202: + return "Accepted"; + case 203: + return "Non-Authoritative"; + case 204: + return "No Content"; + case 205: + return "Reset Content"; + case 206: + return "Partial Content"; + case 207: + return "Multi-status"; + case 208: + return "Already reported"; - case 300: - return "Multiple Choices"; - case 301: - return "Moved Permanently"; - case 302: - return "Found"; - case 303: - return "See Other"; - case 304: - return "Not Modified"; - case 305: - return "Use Proxy"; - case 306: - return "Switch Proxy"; - case 307: - return "Temporary Redirect"; - case 308: - return "Permanent Redirect"; + case 300: + return "Multiple Choices"; + case 301: + return "Moved Permanently"; + case 302: + return "Found"; + case 303: + return "See Other"; + case 304: + return "Not Modified"; + case 305: + return "Use Proxy"; + case 306: + return "Switch Proxy"; + case 307: + return "Temporary Redirect"; + case 308: + return "Permanent Redirect"; - case 400: - return "Bad Request"; - case 401: - return "Unauthorized"; - case 402: - return "Payment Required"; - case 403: - return "Forbidden"; - case 404: - return "Not Found"; - case 405: - return "Method Not Allowed"; - case 406: - return "Not Acceptable"; - case 407: - return "Proxy Authentication Required"; - case 408: - return "Request Timeout"; - case 409: - return "Conflict"; - case 410: - return "Gone"; - case 411: - return "Length Required"; - case 412: - return "Precondition Failed"; - case 413: - return "Payload Too Large"; - case 414: - return "URI Too Long"; - case 415: - return "Unsupported Media Type"; - case 416: - return "Range Not Satisfiable"; - case 417: - return "Expectation Failed"; - case 421: - return "Misdirected Request"; - case 422: - return "Unprocessable Entity"; - case 423: - return "Locked"; - case 424: - return "Failed Dependency"; - case 426: - return "Upgrade Required"; - case 428: - return "Precondition Required"; - case 429: - return "Too Many Requests"; - case 431: - return "Request Header Fields Too Large"; - case 451: - return "Unavailable For Legal Reasons"; + case 400: + return "Bad Request"; + case 401: + return "Unauthorized"; + case 402: + return "Payment Required"; + case 403: + return "Forbidden"; + case 404: + return "Not Found"; + case 405: + return "Method Not Allowed"; + case 406: + return "Not Acceptable"; + case 407: + return "Proxy Authentication Required"; + case 408: + return "Request Timeout"; + case 409: + return "Conflict"; + case 410: + return "Gone"; + case 411: + return "Length Required"; + case 412: + return "Precondition Failed"; + case 413: + return "Payload Too Large"; + case 414: + return "URI Too Long"; + case 415: + return "Unsupported Media Type"; + case 416: + return "Range Not Satisfiable"; + case 417: + return "Expectation Failed"; + case 421: + return "Misdirected Request"; + case 422: + return "Unprocessable Entity"; + case 423: + return "Locked"; + case 424: + return "Failed Dependency"; + case 426: + return "Upgrade Required"; + case 428: + return "Precondition Required"; + case 429: + return "Too Many Requests"; + case 431: + return "Request Header Fields Too Large"; + case 451: + return "Unavailable For Legal Reasons"; - case 500: - return "Internal Server Error"; - case 501: - return "Not Implemented"; - case 502: - return "Bad Gateway"; - case 503: - return "Service Unavailable"; - case 504: - return "Gateway Timeout"; - case 505: - return "HTTP Version Not Supported"; - case 506: - return "Variant Also Negotiates"; - case 507: - return "Insufficient Storage"; - case 508: - return "Loop Detected"; - case 510: - return "Not Extended"; - case 511: - return "Network Authentication Required"; + case 500: + return "Internal Server Error"; + case 501: + return "Not Implemented"; + case 502: + return "Bad Gateway"; + case 503: + return "Service Unavailable"; + case 504: + return "Gateway Timeout"; + case 505: + return "HTTP Version Not Supported"; + case 506: + return "Variant Also Negotiates"; + case 507: + return "Insufficient Storage"; + case 508: + return "Loop Detected"; + case 510: + return "Not Extended"; + case 511: + return "Network Authentication Required"; - default: - return "Unknown status"; - } - } - } + default: + return "Unknown status"; + } + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Common/Interfaces.cs b/libraries/MTConnect.NET-HTTP/Ceen/Common/Interfaces.cs index fbab32515..2fdfb7051 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Common/Interfaces.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Common/Interfaces.cs @@ -15,126 +15,126 @@ namespace Ceen /// Interface for a multipart-item, from a multi-part form request /// internal interface IMultipartItem - { - /// - /// The headers associated with the item - /// - /// The headers. - IDictionary Headers { get; } - - /// - /// Gets or sets the form name. - /// - /// The name. - string Name { get; } - /// - /// Gets or sets the filename. - /// - /// The filename. - string Filename { get; } - /// - /// Gets the Content-Type header value. - /// - /// The type of the content. - string ContentType { get; } - /// - /// The data for this entry - /// - /// The data. - Stream Data { get; } - } - - /// - /// An interface describing a response cookie - /// - public interface IResponseCookie - { - /// - /// List of settings attached to the cookie - /// - /// The settings. - IDictionary Settings { get; } - - /// - /// The name of the cookie - /// - string Name { get; set; } - - /// - /// The value of the cookie - /// - string Value { get; set; } - - /// - /// Gets or sets the cookie path - /// - string Path { get; set; } - - /// - /// Gets or sets the cookie domain - /// - string Domain { get; set; } - - /// - /// Gets or sets the cookie expiration date - /// - DateTime? Expires { get; set; } - - /// - /// Gets or sets the cookie max age. - /// Zero or negative values means un-set - /// - long MaxAge { get; set; } - - /// - /// Gets or sets the cookie secure flag - /// - bool Secure { get; set; } - - /// - /// Gets or sets the cookie HttpOnly flag - /// - bool HttpOnly { get; set; } - } + { + /// + /// The headers associated with the item + /// + /// The headers. + IDictionary Headers { get; } + + /// + /// Gets or sets the form name. + /// + /// The name. + string Name { get; } + /// + /// Gets or sets the filename. + /// + /// The filename. + string Filename { get; } + /// + /// Gets the Content-Type header value. + /// + /// The type of the content. + string ContentType { get; } + /// + /// The data for this entry + /// + /// The data. + Stream Data { get; } + } + + /// + /// An interface describing a response cookie + /// + public interface IResponseCookie + { + /// + /// List of settings attached to the cookie + /// + /// The settings. + IDictionary Settings { get; } + + /// + /// The name of the cookie + /// + string Name { get; set; } + + /// + /// The value of the cookie + /// + string Value { get; set; } + + /// + /// Gets or sets the cookie path + /// + string Path { get; set; } + + /// + /// Gets or sets the cookie domain + /// + string Domain { get; set; } + + /// + /// Gets or sets the cookie expiration date + /// + DateTime? Expires { get; set; } + + /// + /// Gets or sets the cookie max age. + /// Zero or negative values means un-set + /// + long MaxAge { get; set; } + + /// + /// Gets or sets the cookie secure flag + /// + bool Secure { get; set; } + + /// + /// Gets or sets the cookie HttpOnly flag + /// + bool HttpOnly { get; set; } + } /// /// Interface for a http request. /// internal interface IHttpRequestInternal : IHttpRequest { - /// - /// Gets the posted files, if any. - /// Duplicate values are not represented, instead only the latest is stored - /// - IList Files { get; } - - /// - /// Gets the handlers that have processed this request - /// - IEnumerable HandlerStack { get; } - - /// - /// Registers a handler on the request stack - /// - void PushHandlerOnStack(IHttpModule handler); - - /// - /// Enforces that the handler stack obeys the requirements - /// - /// The list of attributes to check. - void RequireHandler(IEnumerable attributes); - - /// - /// Enforces that the given type has processed the request - /// - /// The type to check for. - /// A flag indicating if the type match must be exact, or if derived types are accepted - void RequireHandler(Type handler, bool allowderived = true); - - /// - /// Gets the request cancellation token that is triggered if the request times out - /// - CancellationToken TimeoutCancellationToken { get; } + /// + /// Gets the posted files, if any. + /// Duplicate values are not represented, instead only the latest is stored + /// + IList Files { get; } + + /// + /// Gets the handlers that have processed this request + /// + IEnumerable HandlerStack { get; } + + /// + /// Registers a handler on the request stack + /// + void PushHandlerOnStack(IHttpModule handler); + + /// + /// Enforces that the handler stack obeys the requirements + /// + /// The list of attributes to check. + void RequireHandler(IEnumerable attributes); + + /// + /// Enforces that the given type has processed the request + /// + /// The type to check for. + /// A flag indicating if the type match must be exact, or if derived types are accepted + void RequireHandler(Type handler, bool allowderived = true); + + /// + /// Gets the request cancellation token that is triggered if the request times out + /// + CancellationToken TimeoutCancellationToken { get; } /// /// Gets a value indicating whether this is connected. @@ -162,89 +162,89 @@ internal interface IHttpRequestInternal : IHttpRequest /// Interface for a http response. /// internal interface IHttpResponse - { - /// - /// Gets or sets the HTTP version to report. - /// - /// The http version. - string HttpVersion { get; set; } - /// - /// Gets or sets the status code to report. - /// - /// The status code. - HttpStatusCode StatusCode { get; set; } - /// - /// Gets or sets the status message to report. - /// If this is null, the default message for - /// the HTTP status code is used - /// - /// The status message. - string StatusMessage { get; set; } - /// - /// Gets a value indicating whether the sent headers are sent to the client. - /// Once the headers are sent, the header collection can no longer be modified - /// - /// true if this instance has sent headers; otherwise, false. - bool HasSentHeaders { get; } - /// - /// Dictionary with headers that are sent as part of the response. - /// Cannot be modified after the headers have been sent. - /// - /// The headers. - IDictionary Headers { get; } - - /// - /// Gets a list of cookies that are set with the response. - /// Cannot be modified after the headers have been sent. - /// - /// The cookies. - IList Cookies { get; } - - /// - /// Adds a cookie to the output - /// - /// The new cookie. - /// The name of the cookie. - /// The cookie value. - /// The optional path limiter. - /// The optional domain limiter. - /// The optional expiration date. - /// The optional maximum age. - /// A flag for making the cookie available over SSL only. - /// A flag indicating if the cookie should be hidden from the scripting environment. - /// The samesite attribute for the cookie - IResponseCookie AddCookie(string name, string value, string path = null, string domain = null, DateTime? expires = null, long maxage = -1, bool secure = false, bool httponly = false, string samesite = null); - - /// - /// Adds a header to the output, use null to delete a header. - /// This method throws an exception if the headers are already sent - /// - /// The header name. - /// The header value. - void AddHeader(string key, string value); - - /// - /// Performs an internal redirect - /// - /// The new path to use. - void InternalRedirect(string path); - - /// - /// Gets a value indicating if an internal redirect has been requested - /// - bool IsRedirectingInternally { get; } - - /// - /// Gets or sets the Content-Type header - /// - /// The type of the content. - string ContentType { get; set; } - - /// - /// Gets or sets the Content-Length header - /// - /// The length of the content. - long ContentLength { get; set; } + { + /// + /// Gets or sets the HTTP version to report. + /// + /// The http version. + string HttpVersion { get; set; } + /// + /// Gets or sets the status code to report. + /// + /// The status code. + HttpStatusCode StatusCode { get; set; } + /// + /// Gets or sets the status message to report. + /// If this is null, the default message for + /// the HTTP status code is used + /// + /// The status message. + string StatusMessage { get; set; } + /// + /// Gets a value indicating whether the sent headers are sent to the client. + /// Once the headers are sent, the header collection can no longer be modified + /// + /// true if this instance has sent headers; otherwise, false. + bool HasSentHeaders { get; } + /// + /// Dictionary with headers that are sent as part of the response. + /// Cannot be modified after the headers have been sent. + /// + /// The headers. + IDictionary Headers { get; } + + /// + /// Gets a list of cookies that are set with the response. + /// Cannot be modified after the headers have been sent. + /// + /// The cookies. + IList Cookies { get; } + + /// + /// Adds a cookie to the output + /// + /// The new cookie. + /// The name of the cookie. + /// The cookie value. + /// The optional path limiter. + /// The optional domain limiter. + /// The optional expiration date. + /// The optional maximum age. + /// A flag for making the cookie available over SSL only. + /// A flag indicating if the cookie should be hidden from the scripting environment. + /// The samesite attribute for the cookie + IResponseCookie AddCookie(string name, string value, string path = null, string domain = null, DateTime? expires = null, long maxage = -1, bool secure = false, bool httponly = false, string samesite = null); + + /// + /// Adds a header to the output, use null to delete a header. + /// This method throws an exception if the headers are already sent + /// + /// The header name. + /// The header value. + void AddHeader(string key, string value); + + /// + /// Performs an internal redirect + /// + /// The new path to use. + void InternalRedirect(string path); + + /// + /// Gets a value indicating if an internal redirect has been requested + /// + bool IsRedirectingInternally { get; } + + /// + /// Gets or sets the Content-Type header + /// + /// The type of the content. + string ContentType { get; set; } + + /// + /// Gets or sets the Content-Length header + /// + /// The length of the content. + long ContentLength { get; set; } /// /// Gets or sets the Keep-Alive header @@ -252,63 +252,63 @@ internal interface IHttpResponse /// true if keep alive; otherwise, false. bool KeepAlive { get; set; } - /// - /// Flush all headers async. - /// This method can be called multiple times if desired. - /// - /// The headers async. - Task FlushHeadersAsync(); - - /// - /// Copies the stream to the output. Note that the stream is copied from the current position to the end, and the stream must report the length. - /// - /// The awaitable task - /// The stream to copy. - /// An optional content type to set. Throws an exception if the headers are already sent. - Task WriteAllAsync(Stream data, string contenttype = null); - - /// - /// Writes the byte array to the output. - /// - /// The awaitable task - /// The data to write. - /// An optional content type to set. Throws an exception if the headers are already sent. - Task WriteAllAsync(byte[] data, string contenttype = null); - - /// - /// Writes the string to the output using UTF-8 encoding. - /// - /// The awaitable task - /// The data to write. - /// An optional content type to set. Throws an exception if the headers are already sent. - Task WriteAllAsync(string data, string contenttype = null); - - /// - /// Writes the string to the output. - /// - /// The awaitable task - /// The data to write. - /// The encoding to apply. - /// An optional content type to set. Throws an exception if the headers are already sent. - Task WriteAllAsync(string data, Encoding encoding, string contenttype = null); - - /// - /// Writes the json string to the output with UTF-8 encoding. - /// - /// The awaitable task - /// The JSON data to write. - Task WriteAllJsonAsync(string data); - - /// - /// Performs a 302 redirect - /// - /// The target url. - void Redirect(string newurl); - - /// - /// Sets headers that instruct the client and proxies to avoid caching the response - /// - void SetNonCacheable(); + /// + /// Flush all headers async. + /// This method can be called multiple times if desired. + /// + /// The headers async. + Task FlushHeadersAsync(); + + /// + /// Copies the stream to the output. Note that the stream is copied from the current position to the end, and the stream must report the length. + /// + /// The awaitable task + /// The stream to copy. + /// An optional content type to set. Throws an exception if the headers are already sent. + Task WriteAllAsync(Stream data, string contenttype = null); + + /// + /// Writes the byte array to the output. + /// + /// The awaitable task + /// The data to write. + /// An optional content type to set. Throws an exception if the headers are already sent. + Task WriteAllAsync(byte[] data, string contenttype = null); + + /// + /// Writes the string to the output using UTF-8 encoding. + /// + /// The awaitable task + /// The data to write. + /// An optional content type to set. Throws an exception if the headers are already sent. + Task WriteAllAsync(string data, string contenttype = null); + + /// + /// Writes the string to the output. + /// + /// The awaitable task + /// The data to write. + /// The encoding to apply. + /// An optional content type to set. Throws an exception if the headers are already sent. + Task WriteAllAsync(string data, Encoding encoding, string contenttype = null); + + /// + /// Writes the json string to the output with UTF-8 encoding. + /// + /// The awaitable task + /// The JSON data to write. + Task WriteAllJsonAsync(string data); + + /// + /// Performs a 302 redirect + /// + /// The target url. + void Redirect(string newurl); + + /// + /// Sets headers that instruct the client and proxies to avoid caching the response + /// + void SetNonCacheable(); /// /// Sets headers that instruct the client and proxies to allow caching for a limited time @@ -324,50 +324,50 @@ internal interface IHttpResponse /// A flag indicating if the response is public and can be cached by proxies void SetExpires(DateTime until, bool isPublic = true); - /// - /// Gets the response stream. - /// To avoid buffering the contents, make sure the - /// Content-Length header is set before writing to the stream - /// - /// The response stream. - Stream GetResponseStream(); - } + /// + /// Gets the response stream. + /// To avoid buffering the contents, make sure the + /// Content-Length header is set before writing to the stream + /// + /// The response stream. + Stream GetResponseStream(); + } /// /// Interface for a http handler /// internal interface IHttpContext - { - /// - /// Gets the request. - /// - IHttpRequestInternal Request { get; } - - /// - /// Gets the response - /// - IHttpResponse Response { get; } - - /// - /// Gets the storage creator - /// - IStorageCreator Storage { get; } - - /// - /// Gets or sets the session storage. - /// Note that this can be null if there is no session module loaded. - /// - IDictionary Session { get; set; } - - /// - /// Additional data that can be used in a logging module to tag the request or response - /// - IDictionary LogData { get; } - - /// - /// Information about loaded modules - /// - ILoadedModuleInfo LoadedModules { get; } + { + /// + /// Gets the request. + /// + IHttpRequestInternal Request { get; } + + /// + /// Gets the response + /// + IHttpResponse Response { get; } + + /// + /// Gets the storage creator + /// + IStorageCreator Storage { get; } + + /// + /// Gets or sets the session storage. + /// Note that this can be null if there is no session module loaded. + /// + IDictionary Session { get; set; } + + /// + /// Additional data that can be used in a logging module to tag the request or response + /// + IDictionary LogData { get; } + + /// + /// Information about loaded modules + /// + ILoadedModuleInfo LoadedModules { get; } /// /// Logs a message @@ -377,13 +377,13 @@ internal interface IHttpContext /// The exception to log /// An awaitable task Task LogMessageAsync(LogLevel level, string message, Exception ex); - } + } /// /// Interface for querying the current running server about the loaded modules /// internal interface ILoadedModuleInfo - { + { /// /// The handlers loaded by the router /// @@ -407,12 +407,12 @@ internal interface ILoadedModuleInfo /// allowing for easier access through the /// internal interface INamedModule - { - /// - /// The name of the module - /// - string Name { get; } - } + { + /// + /// The name of the module + /// + string Name { get; } + } /// /// Interface for implementing a routing provider @@ -426,13 +426,13 @@ internal interface IRouter /// The token indicating to stop handling. /// A value indicating if the request is now processed Task Process(IHttpContext context, CancellationToken cancellationToken); - } + } /// /// Shared interface for marking a module or logger as needing setup /// internal interface IWithSetup - { + { /// /// Method called after module is configured /// @@ -455,15 +455,15 @@ internal interface IWithShutdown /// Basic interface for a request handler /// internal interface IHttpModule - { - /// - /// Process the request for the specified context. - /// - /// The context to use. - /// The token indicating to stop handling. - /// A value indicating if the request is now processed - Task HandleAsync(IHttpContext context, CancellationToken cancellationToken); - } + { + /// + /// Process the request for the specified context. + /// + /// The context to use. + /// The token indicating to stop handling. + /// A value indicating if the request is now processed + Task HandleAsync(IHttpContext context, CancellationToken cancellationToken); + } /// /// A module based on which is notified after being configured. @@ -477,69 +477,69 @@ internal interface IHttpModuleWithSetup : IHttpModule, IWithSetup /// Interface for implementing a storage creator /// internal interface IStorageCreator - { - /// - /// Gets or creates a storage module with the given name - /// - /// The storage module or null. - /// The name of the module to get. - /// The session key of the module, or null. - /// The module time-to-live, zero or less means no expiration. - /// Automatically create storage if not found - Task GetStorageAsync(string name, string key, int ttl, bool autocreate); - } + { + /// + /// Gets or creates a storage module with the given name + /// + /// The storage module or null. + /// The name of the module to get. + /// The session key of the module, or null. + /// The module time-to-live, zero or less means no expiration. + /// Automatically create storage if not found + Task GetStorageAsync(string name, string key, int ttl, bool autocreate); + } /// /// Interface for storing data /// internal interface IStorageEntry : IDictionary - { - /// - /// Gets the name of the storage element - /// - string Name { get; } - /// - /// Gets or sets the time the dictionary expires - /// - DateTime Expires { get; set; } - } + { + /// + /// Gets the name of the storage element + /// + string Name { get; } + /// + /// Gets or sets the time the dictionary expires + /// + DateTime Expires { get; set; } + } /// /// The log levels /// internal enum LogLevel - { - /// The message is a debug message - Debug, - /// The message is an informational message - Information, - /// The message is a warning message - Warning, - /// The message is an error message - Error - } + { + /// The message is a debug message + Debug, + /// The message is an informational message + Information, + /// The message is a warning message + Warning, + /// The message is an error message + Error + } /// /// Interface for implementing a logging provider /// internal interface ILogger - { - /// - /// Logs a completed request. - /// - /// An awaitable task. - /// The execution context. - /// The exception being logged, may be null. - /// The time the request started. - /// The request duration. - Task LogRequestCompletedAsync(IHttpContext context, Exception ex, DateTime started, TimeSpan duration); - } + { + /// + /// Logs a completed request. + /// + /// An awaitable task. + /// The execution context. + /// The exception being logged, may be null. + /// The time the request started. + /// The request duration. + Task LogRequestCompletedAsync(IHttpContext context, Exception ex, DateTime started, TimeSpan duration); + } /// /// Interface for a logger that also accepts messages during requests /// internal interface IMessageLogger : ILogger - { + { /// /// Logs a message /// @@ -550,35 +550,35 @@ internal interface IMessageLogger : ILogger /// The time the log data was received /// An awaitable task Task LogMessageAsync(IHttpContext context, Exception ex, LogLevel loglevel, string message, DateTime when); - } + } /// /// Interface for logging requests before they are processed /// internal interface IStartLogger : ILogger - { - /// - /// Logs the start of a request. - /// - /// An awaitable task. - /// The request being started. - Task LogRequestStartedAsync(IHttpRequestInternal request); - } + { + /// + /// Logs the start of a request. + /// + /// An awaitable task. + /// The request being started. + Task LogRequestStartedAsync(IHttpRequestInternal request); + } /// /// Extensions to a logger module that requires configuration /// internal interface ILoggerWithSetup : ILogger, IWithSetup - { + { } /// /// Marker interface for a generic module /// internal interface IModule - { - } + { + } /// /// Extension to a generic module that requires configuration @@ -604,7 +604,7 @@ internal interface IPostProcessor /// Extension for a post-processing handler that requires configuration /// internal interface IPostProcessorWithSetup : IPostProcessor, IWithSetup - { - } + { + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Common/Log.cs b/libraries/MTConnect.NET-HTTP/Ceen/Common/Log.cs index 52d5be98c..59a321232 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Common/Log.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Common/Log.cs @@ -90,6 +90,6 @@ public static Task DebugAsync(Exception ex) public static Task DebugAsync(string message, Exception ex = null) { return Context.Current?.LogMessageAsync(LogLevel.Debug, message, ex) ?? Task.FromResult(true); - } + } } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Common/ParseUtil.cs b/libraries/MTConnect.NET-HTTP/Ceen/Common/ParseUtil.cs index 94e46aa62..574e6c382 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Common/ParseUtil.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Common/ParseUtil.cs @@ -155,7 +155,7 @@ public static IPAddress ParseIPAddress(string address) /// The prefix to a hostname that indicates a unix domain socket /// public const string UNIX_SOCKET_PREFIX = "unix:"; - + /// /// Parse an EndPoint Address, supporting "any", "*", "local", "loopback", and "unix:" /// @@ -169,7 +169,7 @@ public static EndPoint ParseEndPoint(string address, int port) if (!string.IsNullOrWhiteSpace(address) && address.StartsWith(UNIX_SOCKET_PREFIX, StringComparison.OrdinalIgnoreCase)) return new UnixDomainSocketEndPoint(address.Substring(UNIX_SOCKET_PREFIX.Length)); #endif - + // Support for having "localhost:1234" as the listen address if (address.Contains(":")) { @@ -180,6 +180,6 @@ public static EndPoint ParseEndPoint(string address, int port) return new IPEndPoint(ParseIPAddress(address), port); } - + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Common/PeriodicTask.cs b/libraries/MTConnect.NET-HTTP/Ceen/Common/PeriodicTask.cs index a0b45860c..bce556db0 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Common/PeriodicTask.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Common/PeriodicTask.cs @@ -9,111 +9,111 @@ namespace Ceen /// or when signalled explicitly /// internal class PeriodicTask - { - /// - /// Gets or sets the expiration check interval. - /// - public TimeSpan Interval { get; set; } - - /// - /// A task to signal checking for expiration - /// - private TaskCompletionSource m_check = new TaskCompletionSource(); - - /// - /// A token to signal stopping the check for expiration - /// - private CancellationTokenSource m_stop_token = new CancellationTokenSource(); - - /// - /// The task signaling expiration completion - /// - private readonly Task m_task; - - /// - /// The task to run - /// - private readonly Func m_handler; - - /// - /// Initializes a new instance of the class. - /// - /// The method to invoke, the argument indicates if this was a requested run or a periodic invocation. - /// The interval used. - public PeriodicTask(Func handler, TimeSpan interval) - { - m_handler = handler; - Interval = interval; - - m_task = Task.Run(async () => await RunLoopAsync()); - } - - /// - /// Runs an expire loop - /// - /// The loop. - private async Task RunLoopAsync() - { - while (true) - { - var requested = await Task.WhenAny(Task.Delay(Interval), m_check.Task) == m_check.Task; - m_check = new TaskCompletionSource(); - - if (m_stop_token.IsCancellationRequested) - return; - - await m_handler(requested); - } - } - - /// - /// Triggers an expire now - /// - public void RunNow() - { - m_check.TrySetResult(true); - } - - /// - /// Stop this instance. - /// - public Task StopAsync() - { - m_stop_token.Cancel(); - m_check.TrySetResult(true); - return m_task; - } - - /// - /// Gets a value indicating whether this is stopped. - /// - /// true if is stopped; otherwise, false. - public bool IsStopped - { - get { return m_task == null || m_task.IsFaulted || m_task.IsCanceled || m_task.IsCompleted; } - } - - /// - /// Releases all resource used by the object. - /// - /// Call when you are finished using the . The - /// method leaves the in an unusable state. After calling - /// , you must release all references to the so the garbage - /// collector can reclaim the memory that the was occupying. - public void Dispose() - { - StopAsync(); - } - - /// - /// Releases unmanaged resources and performs other cleanup operations before the is - /// reclaimed by garbage collection. - /// - ~PeriodicTask() - { - StopAsync(); - GC.SuppressFinalize(this); - } - - } + { + /// + /// Gets or sets the expiration check interval. + /// + public TimeSpan Interval { get; set; } + + /// + /// A task to signal checking for expiration + /// + private TaskCompletionSource m_check = new TaskCompletionSource(); + + /// + /// A token to signal stopping the check for expiration + /// + private CancellationTokenSource m_stop_token = new CancellationTokenSource(); + + /// + /// The task signaling expiration completion + /// + private readonly Task m_task; + + /// + /// The task to run + /// + private readonly Func m_handler; + + /// + /// Initializes a new instance of the class. + /// + /// The method to invoke, the argument indicates if this was a requested run or a periodic invocation. + /// The interval used. + public PeriodicTask(Func handler, TimeSpan interval) + { + m_handler = handler; + Interval = interval; + + m_task = Task.Run(async () => await RunLoopAsync()); + } + + /// + /// Runs an expire loop + /// + /// The loop. + private async Task RunLoopAsync() + { + while (true) + { + var requested = await Task.WhenAny(Task.Delay(Interval), m_check.Task) == m_check.Task; + m_check = new TaskCompletionSource(); + + if (m_stop_token.IsCancellationRequested) + return; + + await m_handler(requested); + } + } + + /// + /// Triggers an expire now + /// + public void RunNow() + { + m_check.TrySetResult(true); + } + + /// + /// Stop this instance. + /// + public Task StopAsync() + { + m_stop_token.Cancel(); + m_check.TrySetResult(true); + return m_task; + } + + /// + /// Gets a value indicating whether this is stopped. + /// + /// true if is stopped; otherwise, false. + public bool IsStopped + { + get { return m_task == null || m_task.IsFaulted || m_task.IsCanceled || m_task.IsCompleted; } + } + + /// + /// Releases all resource used by the object. + /// + /// Call when you are finished using the . The + /// method leaves the in an unusable state. After calling + /// , you must release all references to the so the garbage + /// collector can reclaim the memory that the was occupying. + public void Dispose() + { + StopAsync(); + } + + /// + /// Releases unmanaged resources and performs other cleanup operations before the is + /// reclaimed by garbage collection. + /// + ~PeriodicTask() + { + StopAsync(); + GC.SuppressFinalize(this); + } + + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Common/QueryStringSerializer.cs b/libraries/MTConnect.NET-HTTP/Ceen/Common/QueryStringSerializer.cs index 68cd3389c..fb441cf65 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Common/QueryStringSerializer.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Common/QueryStringSerializer.cs @@ -9,29 +9,29 @@ namespace Ceen /// Helper class to serialize and deserialize an object into a query string /// internal static class QueryStringSerializer - { - /// - /// Decodes querystring values with "+" values as spaces - /// - /// The encoded string to decode - /// The decoded string - public static string UnescapeDataString(string data) - => Uri.UnescapeDataString(data?.Replace('+', ' ')); - - /// - /// Builds a lookup table for a given type - /// - /// The type to get the lookup table for - /// A lookup table - public static Dictionary GetLookup(Type type) - { + { + /// + /// Decodes querystring values with "+" values as spaces + /// + /// The encoded string to decode + /// The decoded string + public static string UnescapeDataString(string data) + => Uri.UnescapeDataString(data?.Replace('+', ' ')); + + /// + /// Builds a lookup table for a given type + /// + /// The type to get the lookup table for + /// A lookup table + public static Dictionary GetLookup(Type type) + { var table = new Dictionary(StringComparer.OrdinalIgnoreCase); foreach (var n in type.GetFields(BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic)) table[n.Name] = n; foreach (var n in type.GetProperties(BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic)) table[n.Name] = n; - return table; + return table; } /// @@ -94,14 +94,14 @@ public static string SerializeElement(object value, Type entrytype) /// A pre-built lookup table to use, or null to generate one from the type. public static string Serialize(object item, Type type = null, Dictionary lookup = null) { - if (item == null) - return null; + if (item == null) + return null; - if (type == null) - type = item.GetType(); + if (type == null) + type = item.GetType(); - if(lookup == null) - lookup = GetLookup(type); + if (lookup == null) + lookup = GetLookup(type); return "?" @@ -112,101 +112,101 @@ public static string Serialize(object item, Type type = null, Dictionary Uri.EscapeDataString(SerializeElement(x, item))) ); - } - } - - /// - /// Helper class to serialize and deserialize an object into a query string - /// - public static class QueryStringSerializer - where T : new() - { - /// - /// A lookup table for the type, stores a table for each type being serialized - /// - private readonly static Dictionary _lookup; - - /// - /// Initializes the class. - /// - static QueryStringSerializer() - { - _lookup = QueryStringSerializer.GetLookup(typeof(T)); - } - - /// - /// Deserializes a string representation of a property or field to its native representation - /// - /// The native object. - /// The string value to deserialize. - /// The type of the field or property. - public static object DeserializeElement(string value, Type entrytype) - => QueryStringSerializer.DeserializeElement(value, entrytype); - - /// - /// Serializes a property or field value to a string presentation - /// - /// The serialized representation. - /// The value to serialize as a string. - /// The type of the field or property. - public static string SerializeElement(MemberInfo member, object instance) - => QueryStringSerializer.SerializeElement(member, instance); - - /// - /// Serializes a property or field value to a string presentation - /// - /// The serialized representation. - /// The value to serialize as a string. - /// The type of the field or property. - public static string SerializeElement(object value, Type entrytype) - => QueryStringSerializer.SerializeElement(value, entrytype); - - /// - /// Serialize the specified item. - /// - /// The item to serialize. - public static string Serialize(T item) - => QueryStringSerializer.Serialize(item, typeof(T), _lookup); - - /// - /// Deserialize the specified value. - /// - /// The serialized string. - /// True if extra data is ignored, if this is false an exception is thrown if extra data is found - public static T Deserialize(string input, bool ignoreextras) - { - if (string.IsNullOrWhiteSpace(input)) - return default(T); - - var item = new T(); - input = input.TrimStart('?'); - foreach (var el in input.Split('?')) - { - if (el == null) - continue; - var splitix = el.IndexOf('='); - if (splitix <= 0) - continue; - - var key = QueryStringSerializer.UnescapeDataString(el.Substring(0, splitix)); - var value = QueryStringSerializer.UnescapeDataString(el.Substring(splitix + 1)); - - MemberInfo member; - if (!_lookup.TryGetValue(key, out member)) - { - if (!ignoreextras) - throw new ArgumentException($"The item {key} is not found in {typeof(T).FullName}"); - } - else - { - if (member is PropertyInfo) - ((PropertyInfo)member).SetValue(item, DeserializeElement(value, ((PropertyInfo)member).PropertyType), null); - else - ((FieldInfo)member).SetValue(item, DeserializeElement(value, ((FieldInfo)member).FieldType)); - } - } - - return item; - } - } + } + } + + /// + /// Helper class to serialize and deserialize an object into a query string + /// + public static class QueryStringSerializer + where T : new() + { + /// + /// A lookup table for the type, stores a table for each type being serialized + /// + private readonly static Dictionary _lookup; + + /// + /// Initializes the class. + /// + static QueryStringSerializer() + { + _lookup = QueryStringSerializer.GetLookup(typeof(T)); + } + + /// + /// Deserializes a string representation of a property or field to its native representation + /// + /// The native object. + /// The string value to deserialize. + /// The type of the field or property. + public static object DeserializeElement(string value, Type entrytype) + => QueryStringSerializer.DeserializeElement(value, entrytype); + + /// + /// Serializes a property or field value to a string presentation + /// + /// The serialized representation. + /// The value to serialize as a string. + /// The type of the field or property. + public static string SerializeElement(MemberInfo member, object instance) + => QueryStringSerializer.SerializeElement(member, instance); + + /// + /// Serializes a property or field value to a string presentation + /// + /// The serialized representation. + /// The value to serialize as a string. + /// The type of the field or property. + public static string SerializeElement(object value, Type entrytype) + => QueryStringSerializer.SerializeElement(value, entrytype); + + /// + /// Serialize the specified item. + /// + /// The item to serialize. + public static string Serialize(T item) + => QueryStringSerializer.Serialize(item, typeof(T), _lookup); + + /// + /// Deserialize the specified value. + /// + /// The serialized string. + /// True if extra data is ignored, if this is false an exception is thrown if extra data is found + public static T Deserialize(string input, bool ignoreextras) + { + if (string.IsNullOrWhiteSpace(input)) + return default(T); + + var item = new T(); + input = input.TrimStart('?'); + foreach (var el in input.Split('?')) + { + if (el == null) + continue; + var splitix = el.IndexOf('='); + if (splitix <= 0) + continue; + + var key = QueryStringSerializer.UnescapeDataString(el.Substring(0, splitix)); + var value = QueryStringSerializer.UnescapeDataString(el.Substring(splitix + 1)); + + MemberInfo member; + if (!_lookup.TryGetValue(key, out member)) + { + if (!ignoreextras) + throw new ArgumentException($"The item {key} is not found in {typeof(T).FullName}"); + } + else + { + if (member is PropertyInfo) + ((PropertyInfo)member).SetValue(item, DeserializeElement(value, ((PropertyInfo)member).PropertyType), null); + else + ((FieldInfo)member).SetValue(item, DeserializeElement(value, ((FieldInfo)member).FieldType)); + } + } + + return item; + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Common/RequestUtility.cs b/libraries/MTConnect.NET-HTTP/Ceen/Common/RequestUtility.cs index d0f94f057..e3d15ee59 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Common/RequestUtility.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Common/RequestUtility.cs @@ -79,27 +79,27 @@ public CultureInfo TryParse(bool allowOnlyMajor = true, CultureInfo @default = n /// internal static class RequestUtility { - /// - /// Gets an encoding from a charset string - /// - /// The encoding for the charset. - /// The charset string. + /// + /// Gets an encoding from a charset string + /// + /// The encoding for the charset. + /// The charset string. public static Encoding GetEncodingForCharset(string charset) - { - if (string.Equals("utf-8", charset, StringComparison.OrdinalIgnoreCase)) - return Encoding.UTF8; - else if (string.Equals("ascii", charset, StringComparison.OrdinalIgnoreCase)) - return Encoding.ASCII; - else - return Encoding.GetEncoding(charset); - } - - /// - /// Gets an encoding from a charset string - /// - /// The encoding for the charset. - /// The content type string. - public static Encoding GetEncodingForContentType(string contenttype) + { + if (string.Equals("utf-8", charset, StringComparison.OrdinalIgnoreCase)) + return Encoding.UTF8; + else if (string.Equals("ascii", charset, StringComparison.OrdinalIgnoreCase)) + return Encoding.ASCII; + else + return Encoding.GetEncoding(charset); + } + + /// + /// Gets an encoding from a charset string + /// + /// The encoding for the charset. + /// The content type string. + public static Encoding GetEncodingForContentType(string contenttype) { var enc = GetHeaderComponent(contenttype, "encoding"); if (string.IsNullOrWhiteSpace(enc)) @@ -113,54 +113,54 @@ public static Encoding GetEncodingForContentType(string contenttype) : Encoding.ASCII; return GetEncodingForCharset(enc); - } - - /// - /// Gets an encoding from a charset string - /// - /// The encoding for the charset. - /// The request instance. - public static Encoding GetEncodingForCharset(this IHttpRequestInternal request, string charset) + } + + /// + /// Gets an encoding from a charset string + /// + /// The encoding for the charset. + /// The request instance. + public static Encoding GetEncodingForCharset(this IHttpRequestInternal request, string charset) => GetEncodingForCharset(charset); - /// - /// Gets an encoding from the content-type string - /// - /// The encoding for the content-type. - /// The request instance. - public static Encoding GetEncodingForContentType(this IHttpRequestInternal request) + /// + /// Gets an encoding from the content-type string + /// + /// The encoding for the content-type. + /// The request instance. + public static Encoding GetEncodingForContentType(this IHttpRequestInternal request) => GetEncodingForContentType(request.ContentType); - /// - /// Regular expression for parsing the Accept-Language header - /// - private static System.Text.RegularExpressions.Regex LANGUAGE_MATCHER = - new System.Text.RegularExpressions.Regex( + /// + /// Regular expression for parsing the Accept-Language header + /// + private static System.Text.RegularExpressions.Regex LANGUAGE_MATCHER = + new System.Text.RegularExpressions.Regex( @"\s*(?[A-z]+)(-(?[A-z-_]+))?(;(q=(?[0-9\.]+)))?\s*,?" - ); + ); - /// - /// The number style for parsing the language quality specifier - /// - private const System.Globalization.NumberStyles QUALITY_NUMBER_STYLE = + /// + /// The number style for parsing the language quality specifier + /// + private const System.Globalization.NumberStyles QUALITY_NUMBER_STYLE = System.Globalization.NumberStyles.AllowLeadingSign | System.Globalization.NumberStyles.AllowDecimalPoint | System.Globalization.NumberStyles.AllowLeadingWhite | System.Globalization.NumberStyles.AllowTrailingWhite; - /// - /// Gets the prefered language that the user accepts, which is also in the list of supported items. - /// Returns null if no languages are accepted. - /// Expects fully qualified language names (i.e. "en-US") - /// - /// The request to examine - /// The list of supported languages - /// The prefered language or null - public static LanguageTag GetAcceptLanguage(this IHttpRequestInternal request, params string[] supportedLanguages) - { - var lookup = supportedLanguages.ToLookup(x => x, StringComparer.InvariantCultureIgnoreCase); - return GetAcceptLanguages(request).FirstOrDefault(x => lookup.Contains(x.IANAName)); - } + /// + /// Gets the prefered language that the user accepts, which is also in the list of supported items. + /// Returns null if no languages are accepted. + /// Expects fully qualified language names (i.e. "en-US") + /// + /// The request to examine + /// The list of supported languages + /// The prefered language or null + public static LanguageTag GetAcceptLanguage(this IHttpRequestInternal request, params string[] supportedLanguages) + { + var lookup = supportedLanguages.ToLookup(x => x, StringComparer.InvariantCultureIgnoreCase); + return GetAcceptLanguages(request).FirstOrDefault(x => lookup.Contains(x.IANAName)); + } /// /// Gets the prefered language that the user accepts, which is also in the list of supported items. @@ -174,7 +174,7 @@ public static LanguageTag GetAcceptMajorLanguage(this IHttpRequestInternal reque { var lookup = supportedLanguages.ToLookup(x => x, StringComparer.InvariantCultureIgnoreCase); return GetAcceptLanguages(request) - .FirstOrDefault(x => lookup.Contains(x.Primary)); + .FirstOrDefault(x => lookup.Contains(x.Primary)); } /// @@ -183,31 +183,32 @@ public static LanguageTag GetAcceptMajorLanguage(this IHttpRequestInternal reque /// The request to examine /// The ordered list of accepted languages public static IOrderedEnumerable GetAcceptLanguages(this IHttpRequestInternal request) - { - return LANGUAGE_MATCHER - // Match the string - .Matches(request.Headers["Accept-Language"] ?? string.Empty) - // Old IEnumerable to Linq - .Cast() - // Parse each match - .Select(x => { - var quality = 1f; - if (x.Groups["quality"].Success && float.TryParse(x.Groups["quality"].Value, QUALITY_NUMBER_STYLE, System.Globalization.CultureInfo.InvariantCulture, out var q)) - quality = q; - - return new LanguageTag( - x.Groups["primary"].Value, - x.Groups["subtag"].Success ? x.Groups["subtag"].Value : string.Empty, - quality - ); - }) - // Filter out those with quality zero or less - .Where(x => x.Quality > 0) - // Order by quality - .OrderByDescending(x => x.Quality) - // But with same quality, we prefer those with a sub-tag - .ThenBy(x => string.IsNullOrWhiteSpace(x.Subtag)); - } + { + return LANGUAGE_MATCHER + // Match the string + .Matches(request.Headers["Accept-Language"] ?? string.Empty) + // Old IEnumerable to Linq + .Cast() + // Parse each match + .Select(x => + { + var quality = 1f; + if (x.Groups["quality"].Success && float.TryParse(x.Groups["quality"].Value, QUALITY_NUMBER_STYLE, System.Globalization.CultureInfo.InvariantCulture, out var q)) + quality = q; + + return new LanguageTag( + x.Groups["primary"].Value, + x.Groups["subtag"].Success ? x.Groups["subtag"].Value : string.Empty, + quality + ); + }) + // Filter out those with quality zero or less + .Where(x => x.Quality > 0) + // Order by quality + .OrderByDescending(x => x.Quality) + // But with same quality, we prefer those with a sub-tag + .ThenBy(x => string.IsNullOrWhiteSpace(x.Subtag)); + } /// /// Returns a value indicating if the request is a multi-part request @@ -219,15 +220,15 @@ public static bool IsMultipartRequest(this IHttpRequestInternal request) return IsMultipartRequest(request.ContentType); } - /// - /// Returns a value indicating if the request is a multi-part request - /// - /// true, if multi-part was used, false otherwise. - /// The request contenttype to examine. - public static bool IsMultipartRequest(string contenttype) - { + /// + /// Returns a value indicating if the request is a multi-part request + /// + /// true, if multi-part was used, false otherwise. + /// The request contenttype to examine. + public static bool IsMultipartRequest(string contenttype) + { return IsContentType(contenttype, "multipart/form-data"); - } + } /// /// Returns a value indicating if the content type is of a certain type @@ -257,21 +258,21 @@ public static bool IsContentType(string contenttype, string test) return string.Equals(contenttype.Substring(0, firstdelim), test, StringComparison.OrdinalIgnoreCase); } - /// - /// Returns a value indicating if the content type is indicating Json data - /// - /// true, if the content type is json, false otherwise. - /// The request instance. - public static bool IsJsonRequest(this IHttpRequestInternal request) + /// + /// Returns a value indicating if the content type is indicating Json data + /// + /// true, if the content type is json, false otherwise. + /// The request instance. + public static bool IsJsonRequest(this IHttpRequestInternal request) => IsJsonRequest(request.ContentType); - /// - /// Returns a value indicating if the content type is indicating Json data - /// - /// true, if the content type is json, false otherwise. - /// The request contenttype to examine. - public static bool IsJsonRequest(string contenttype) - { + /// + /// Returns a value indicating if the content type is indicating Json data + /// + /// true, if the content type is json, false otherwise. + /// The request contenttype to examine. + public static bool IsJsonRequest(string contenttype) + { var ct = contenttype ?? string.Empty; if (string.IsNullOrWhiteSpace(ct)) return false; @@ -282,77 +283,77 @@ public static bool IsJsonRequest(string contenttype) || IsContentType(contenttype, "text/javascript") || IsContentType(contenttype, "text/x-javascript") || IsContentType(contenttype, "text/x-json"); - } - - /// - /// Splits a header line into its key-value components - /// - /// The components. - /// The line to split. - public static IEnumerable> SplitHeaderLine(string line) - { - return (line ?? "").Split(new char[] { ';' }, StringSplitOptions.RemoveEmptyEntries).Select(x => - { - var c = x.Split(new char[] { '=' }, 2, StringSplitOptions.RemoveEmptyEntries); - var value = (c.Skip(1).FirstOrDefault() ?? "").Trim(); - if (value.StartsWith("\"", StringComparison.Ordinal) && value.EndsWith("\"", StringComparison.Ordinal)) - value = value.Substring(1, value.Length - 2); - return new KeyValuePair(c.First().Trim(), value); - }); - } - - - /// - /// Gets a named component from a header line - /// - /// The header component or null. - /// The header line. - /// The component to find. - public static string GetHeaderComponent(string line, string key) - { - return - SplitHeaderLine(line) - .Where(x => string.Equals(x.Key, key, StringComparison.OrdinalIgnoreCase)) - .Select(x => x.Value) - .FirstOrDefault(); - } - - /// - /// Reads all bytes from a stream into a string, using UTF8 encoding - /// - /// The string from the stream. - /// The stream to read from. - /// The cancellation token. - public static Task ReadAllAsStringAsync(this Stream stream, CancellationToken token = default(CancellationToken)) - { - return ReadAllAsStringAsync(stream, System.Text.Encoding.UTF8, token); - } - - /// - /// Reads all bytes from a stream into a string - /// - /// The string from the stream. - /// The stream to read from. - /// The encoding to use. - /// The cancellation token. - public static async Task ReadAllAsStringAsync(this Stream stream, System.Text.Encoding encoding, CancellationToken token = default(CancellationToken)) - { - if (encoding == null) - throw new ArgumentNullException(nameof(encoding)); - - using (var ms = new System.IO.MemoryStream()) - { - await stream.CopyToAsync(ms, 1024 * 8, token); - return encoding.GetString(ms.ToArray()); - } - } - - /// - /// Logs an exception error - /// - /// The context to log with - /// The exception to log - /// An awaitable task + } + + /// + /// Splits a header line into its key-value components + /// + /// The components. + /// The line to split. + public static IEnumerable> SplitHeaderLine(string line) + { + return (line ?? "").Split(new char[] { ';' }, StringSplitOptions.RemoveEmptyEntries).Select(x => + { + var c = x.Split(new char[] { '=' }, 2, StringSplitOptions.RemoveEmptyEntries); + var value = (c.Skip(1).FirstOrDefault() ?? "").Trim(); + if (value.StartsWith("\"", StringComparison.Ordinal) && value.EndsWith("\"", StringComparison.Ordinal)) + value = value.Substring(1, value.Length - 2); + return new KeyValuePair(c.First().Trim(), value); + }); + } + + + /// + /// Gets a named component from a header line + /// + /// The header component or null. + /// The header line. + /// The component to find. + public static string GetHeaderComponent(string line, string key) + { + return + SplitHeaderLine(line) + .Where(x => string.Equals(x.Key, key, StringComparison.OrdinalIgnoreCase)) + .Select(x => x.Value) + .FirstOrDefault(); + } + + /// + /// Reads all bytes from a stream into a string, using UTF8 encoding + /// + /// The string from the stream. + /// The stream to read from. + /// The cancellation token. + public static Task ReadAllAsStringAsync(this Stream stream, CancellationToken token = default(CancellationToken)) + { + return ReadAllAsStringAsync(stream, System.Text.Encoding.UTF8, token); + } + + /// + /// Reads all bytes from a stream into a string + /// + /// The string from the stream. + /// The stream to read from. + /// The encoding to use. + /// The cancellation token. + public static async Task ReadAllAsStringAsync(this Stream stream, System.Text.Encoding encoding, CancellationToken token = default(CancellationToken)) + { + if (encoding == null) + throw new ArgumentNullException(nameof(encoding)); + + using (var ms = new System.IO.MemoryStream()) + { + await stream.CopyToAsync(ms, 1024 * 8, token); + return encoding.GetString(ms.ToArray()); + } + } + + /// + /// Logs an exception error + /// + /// The context to log with + /// The exception to log + /// An awaitable task public static Task LogErrorAsync(this IHttpContext context, Exception ex) { return context.LogMessageAsync(LogLevel.Error, null, ex); @@ -366,9 +367,9 @@ public static Task LogErrorAsync(this IHttpContext context, Exception ex) /// The optional exception to log /// An awaitable task public static Task LogErrorAsync(this IHttpContext context, string message, Exception ex = null) - { - return context.LogMessageAsync(LogLevel.Error, message, ex); - } + { + return context.LogMessageAsync(LogLevel.Error, message, ex); + } /// /// Logs an exception warning diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Common/ResponseUtility.cs b/libraries/MTConnect.NET-HTTP/Ceen/Common/ResponseUtility.cs index 51521f350..f0b59c79d 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Common/ResponseUtility.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Common/ResponseUtility.cs @@ -96,9 +96,9 @@ public static bool SetResponseUnauthorized(this IHttpContext context, string mes /// true public static bool SetResponseRedirect(this IHttpContext context, string targeturl, HttpStatusCode code = HttpStatusCode.Found, string message = null) { - context.Response.Headers["Location"] = targeturl; - context.Response.StatusCode = code; - context.Response.StatusMessage = message ?? HttpStatusMessages.DefaultMessage(context.Response.StatusCode); + context.Response.Headers["Location"] = targeturl; + context.Response.StatusCode = code; + context.Response.StatusMessage = message ?? HttpStatusMessages.DefaultMessage(context.Response.StatusCode); return true; } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Common/SocketUtil.cs b/libraries/MTConnect.NET-HTTP/Ceen/Common/SocketUtil.cs index 8a27fd6fb..17ee50c3a 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Common/SocketUtil.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Common/SocketUtil.cs @@ -19,12 +19,12 @@ internal static class SocketUtil public static Socket CreateAndBindSocket(EndPoint addr, int backlog) { Socket socket; - if (addr is IPEndPoint) - socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.IP); + if (addr is IPEndPoint) + socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.IP); #if NET5_0_OR_GREATER - else if (addr is UnixDomainSocketEndPoint) - socket = new Socket(AddressFamily.Unix, SocketType.Stream, ProtocolType.IP); + else if (addr is UnixDomainSocketEndPoint) + socket = new Socket(AddressFamily.Unix, SocketType.Stream, ProtocolType.IP); #endif else @@ -42,7 +42,7 @@ public static Socket CreateAndBindSocket(EndPoint addr, int backlog) /// The backlog number to set public static void BindSocket(Socket socket, EndPoint addr, int backlog) { - try + try { socket.Bind(addr); } @@ -58,11 +58,11 @@ public static void BindSocket(Socket socket, EndPoint addr, int backlog) var failed = false; try { - using(var ts = new Socket(AddressFamily.Unix, SocketType.Stream, ProtocolType.IP)) + using (var ts = new Socket(AddressFamily.Unix, SocketType.Stream, ProtocolType.IP)) { var t = ts.ConnectAsync(addr); - t.Wait(TimeSpan.FromSeconds(1)); - } + t.Wait(TimeSpan.FromSeconds(1)); + } } catch { @@ -75,7 +75,7 @@ public static void BindSocket(Socket socket, EndPoint addr, int backlog) // Try to unlink the file try { File.Delete(path); } - catch {} + catch { } // And retry the bind socket.Bind(addr); diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Common/SyncAwaiter.cs b/libraries/MTConnect.NET-HTTP/Ceen/Common/SyncAwaiter.cs index 0ccdc9f50..a10f6ed61 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Common/SyncAwaiter.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Common/SyncAwaiter.cs @@ -80,13 +80,13 @@ public override void Send(SendOrPostCallback d, object state) { if (Current == this) { - // already on execution thread + // already on execution thread d(state); return; } var task = new Task(new Action(d), state); - m_queue.Add((x => ((Task) x).RunSynchronously(), task)); + m_queue.Add((x => ((Task)x).RunSynchronously(), task)); task.Wait(); } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/BufferedStreamReader.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/BufferedStreamReader.cs index 5e386fd60..e1f351d56 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/BufferedStreamReader.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/BufferedStreamReader.cs @@ -13,88 +13,88 @@ namespace Ceen.Httpd /// the stream untouched. /// internal class BufferedStreamReader : Stream - { - /// - /// The underlying network stream - /// - private Stream m_parent; - /// - /// The internal read-ahead buffer - /// - private byte[] m_buffer; - /// - /// The number of bytes in the internal buffer - /// - private int m_buffercount = 0; - /// - /// The offset in the internal buffer from where the data starts - /// - private int m_bufferoffset = 0; - /// - /// The CR ASCII value. - /// - private const byte CR = 13; - /// - /// The LF ASCII value. - /// - private const byte LF = 10; - /// - /// The number of bytes we are allowed to read - /// - private long m_remainingbytes = 0; - /// - /// The number of bytes read - /// - private long m_maxread = 0; - - /// - /// Initializes a new instance of the class. - /// - /// The parent stream. - /// Intitial size of the read-ahead buffer. - public BufferedStreamReader(Stream parent, int initialbuffersize = 1024) - { - if (parent == null) - throw new ArgumentNullException(nameof(parent)); - - m_parent = parent; - m_buffer = new byte[initialbuffersize]; - } - - /// - /// Resets the number of bytes read. - /// - /// The maximum number of bytes to allow reading - internal void ResetReadLength(long maxsize) - { - m_maxread = m_remainingbytes = maxsize; - } - - - /// - /// Reads all lines until an empty line (i.e. it reads until CR LF CR LF). - /// Each read line, except the empty line is send to the linehandler function - /// - /// An awaitable task. - /// The maximum size of a single line. - /// The maximum size of the headers. - /// The maximum time to remain idle. - /// Callback method that processes each line. - /// Awaitable task for stopping the request. - /// Awaitable task for stopping the request. - public async Task ReadHeaders(int maxlinesize, int maxheadersize, TimeSpan idletimeout, Action linehandler, Task timeouttask, Task stoptask) - { - var buf = new byte[maxlinesize]; - var bufoffset = 0; - var bufsize = 0; - var totalread = 0; - var lastlookoffset = 0; - - // Repeat the parsing until we time out or get an empty line - while (true) - { - if (totalread == maxheadersize) - throw new HttpException(HttpStatusCode.RequestHeaderFieldsTooLarge); + { + /// + /// The underlying network stream + /// + private Stream m_parent; + /// + /// The internal read-ahead buffer + /// + private byte[] m_buffer; + /// + /// The number of bytes in the internal buffer + /// + private int m_buffercount = 0; + /// + /// The offset in the internal buffer from where the data starts + /// + private int m_bufferoffset = 0; + /// + /// The CR ASCII value. + /// + private const byte CR = 13; + /// + /// The LF ASCII value. + /// + private const byte LF = 10; + /// + /// The number of bytes we are allowed to read + /// + private long m_remainingbytes = 0; + /// + /// The number of bytes read + /// + private long m_maxread = 0; + + /// + /// Initializes a new instance of the class. + /// + /// The parent stream. + /// Intitial size of the read-ahead buffer. + public BufferedStreamReader(Stream parent, int initialbuffersize = 1024) + { + if (parent == null) + throw new ArgumentNullException(nameof(parent)); + + m_parent = parent; + m_buffer = new byte[initialbuffersize]; + } + + /// + /// Resets the number of bytes read. + /// + /// The maximum number of bytes to allow reading + internal void ResetReadLength(long maxsize) + { + m_maxread = m_remainingbytes = maxsize; + } + + + /// + /// Reads all lines until an empty line (i.e. it reads until CR LF CR LF). + /// Each read line, except the empty line is send to the linehandler function + /// + /// An awaitable task. + /// The maximum size of a single line. + /// The maximum size of the headers. + /// The maximum time to remain idle. + /// Callback method that processes each line. + /// Awaitable task for stopping the request. + /// Awaitable task for stopping the request. + public async Task ReadHeaders(int maxlinesize, int maxheadersize, TimeSpan idletimeout, Action linehandler, Task timeouttask, Task stoptask) + { + var buf = new byte[maxlinesize]; + var bufoffset = 0; + var bufsize = 0; + var totalread = 0; + var lastlookoffset = 0; + + // Repeat the parsing until we time out or get an empty line + while (true) + { + if (totalread == maxheadersize) + throw new HttpException(HttpStatusCode.RequestHeaderFieldsTooLarge); Task rtask; Task rt; @@ -102,301 +102,301 @@ public async Task ReadHeaders(int maxlinesize, int maxheadersize, TimeSpan idlet using (var cs = new CancellationTokenSource(idletimeout)) { rtask = ReadAsync(buf, bufsize, Math.Min(buf.Length - bufsize, maxheadersize - totalread), cs.Token); - rt = await Task.WhenAny( stoptask, timeouttask, rtask); + rt = await Task.WhenAny(stoptask, timeouttask, rtask); } // Timeout or stop has happened - if (rt != rtask) - { - if (rt == stoptask) - throw new TaskCanceledException(); - else if (totalread == 0) - throw new EmptyStreamClosedException(); - else - throw new HttpException(HttpStatusCode.RequestTimeout); - } - - var r = rtask.Result; - totalread += r; - bufsize += r; - - // Stream closed - if (r == 0) - { - if (totalread == 0) - throw new EmptyStreamClosedException(); - else - throw new HttpException(HttpStatusCode.BadRequest); - } - - // Look for first CR - var ix = Array.IndexOf(buf, CR, lastlookoffset, bufsize - lastlookoffset); - while (ix >= 0 && ix < bufsize - 1) - { - // Check if the next byte is LF - if (buf[ix + 1] == LF) - { - var datalen = ix - bufoffset; - - // Check if the line is empty - if (datalen == 0) - { - bufoffset = ix + 2; - - // If we have more data, "unread it" - if (bufsize - bufoffset != 0) - UnreadBytesIntoBuffer(buf, bufoffset, bufsize - bufoffset); - - return; - } - else - { - linehandler(System.Text.Encoding.ASCII.GetString(buf, bufoffset, datalen)); - bufoffset = ix + 2; - lastlookoffset = bufoffset; - } - } - else - { - // False hit, or char hit a split with blocks - lastlookoffset = ix + 1; - } - - // Get the next entry - ix = Array.IndexOf(buf, CR, lastlookoffset, bufsize - lastlookoffset); - } - - // Move trailing bytes to the start of the buffer to reduce space use - // and make sure we do not search more than once for the CRLF - bufsize = bufsize - bufoffset; - if (bufoffset > 0 && bufsize > 0) - Array.Copy(buf, bufoffset, buf, 0, bufsize); - - bufoffset = 0; - lastlookoffset = Math.Max(0, bufsize - 1); - } - } - - /// - /// Keeps reading from the stream until the supplied number of bytes are read - /// - /// The awaitable task. - /// The number of bytes to read. - /// The time to wait while idle - /// The task that signals request timeout - /// The task that signals stop for the server - internal async Task RepeatReadAsync(int count, TimeSpan idletimeout, Task timeouttask, Task stoptask) - { - var buf = new byte[count]; - await RepeatReadAsync(buf, 0, count, idletimeout, timeouttask, stoptask); - return buf; - } - - /// - /// Gets the delimited sub stream. - /// - /// The delimited sub stream. - /// Delimiter. - /// The time to wait while idle - /// The task that signals request timeout - /// The task that signals stop for the server - internal Stream GetDelimitedSubStream(byte[] delimiter, TimeSpan idletime, Task timeouttask, Task stoptask) - { - return new DelimitedSubStream(this, delimiter, idletime, timeouttask, stoptask); - } - - /// - /// Keeps reading from the stream until the supplied number of bytes are read. - /// Throws an exception if the stream fails to provide the required bytes. - /// - /// The awaitable task. - /// The buffer to read into. - /// The offset into the buffer where data is written. - /// The number of bytes to read. - /// The time to wait while idle - /// The task that signals request timeout - /// The task that signals stop for the server - internal async Task RepeatReadAsync(byte[] buffer, int offset, int count, TimeSpan idletimeout, Task timeouttask, Task stoptask) - { - while (count > 0) - { + if (rt != rtask) + { + if (rt == stoptask) + throw new TaskCanceledException(); + else if (totalread == 0) + throw new EmptyStreamClosedException(); + else + throw new HttpException(HttpStatusCode.RequestTimeout); + } + + var r = rtask.Result; + totalread += r; + bufsize += r; + + // Stream closed + if (r == 0) + { + if (totalread == 0) + throw new EmptyStreamClosedException(); + else + throw new HttpException(HttpStatusCode.BadRequest); + } + + // Look for first CR + var ix = Array.IndexOf(buf, CR, lastlookoffset, bufsize - lastlookoffset); + while (ix >= 0 && ix < bufsize - 1) + { + // Check if the next byte is LF + if (buf[ix + 1] == LF) + { + var datalen = ix - bufoffset; + + // Check if the line is empty + if (datalen == 0) + { + bufoffset = ix + 2; + + // If we have more data, "unread it" + if (bufsize - bufoffset != 0) + UnreadBytesIntoBuffer(buf, bufoffset, bufsize - bufoffset); + + return; + } + else + { + linehandler(System.Text.Encoding.ASCII.GetString(buf, bufoffset, datalen)); + bufoffset = ix + 2; + lastlookoffset = bufoffset; + } + } + else + { + // False hit, or char hit a split with blocks + lastlookoffset = ix + 1; + } + + // Get the next entry + ix = Array.IndexOf(buf, CR, lastlookoffset, bufsize - lastlookoffset); + } + + // Move trailing bytes to the start of the buffer to reduce space use + // and make sure we do not search more than once for the CRLF + bufsize = bufsize - bufoffset; + if (bufoffset > 0 && bufsize > 0) + Array.Copy(buf, bufoffset, buf, 0, bufsize); + + bufoffset = 0; + lastlookoffset = Math.Max(0, bufsize - 1); + } + } + + /// + /// Keeps reading from the stream until the supplied number of bytes are read + /// + /// The awaitable task. + /// The number of bytes to read. + /// The time to wait while idle + /// The task that signals request timeout + /// The task that signals stop for the server + internal async Task RepeatReadAsync(int count, TimeSpan idletimeout, Task timeouttask, Task stoptask) + { + var buf = new byte[count]; + await RepeatReadAsync(buf, 0, count, idletimeout, timeouttask, stoptask); + return buf; + } + + /// + /// Gets the delimited sub stream. + /// + /// The delimited sub stream. + /// Delimiter. + /// The time to wait while idle + /// The task that signals request timeout + /// The task that signals stop for the server + internal Stream GetDelimitedSubStream(byte[] delimiter, TimeSpan idletime, Task timeouttask, Task stoptask) + { + return new DelimitedSubStream(this, delimiter, idletime, timeouttask, stoptask); + } + + /// + /// Keeps reading from the stream until the supplied number of bytes are read. + /// Throws an exception if the stream fails to provide the required bytes. + /// + /// The awaitable task. + /// The buffer to read into. + /// The offset into the buffer where data is written. + /// The number of bytes to read. + /// The time to wait while idle + /// The task that signals request timeout + /// The task that signals stop for the server + internal async Task RepeatReadAsync(byte[] buffer, int offset, int count, TimeSpan idletimeout, Task timeouttask, Task stoptask) + { + while (count > 0) + { Task rtask; Task rt; using (var cs = new CancellationTokenSource(idletimeout)) { rtask = ReadAsync(buffer, offset, count, cs.Token); - rt = await Task.WhenAny( stoptask, timeouttask, rtask); + rt = await Task.WhenAny(stoptask, timeouttask, rtask); } // Timeout or stop has happened - if (rt != rtask) - { - if (rt == stoptask) - throw new TaskCanceledException(); - else - throw new HttpException(HttpStatusCode.RequestTimeout); - } - - var r = rtask.Result; - offset += r; - count -= r; - if (r == 0) - throw new HttpException(HttpStatusCode.BadRequest); - } - } - - /// - /// Reads the stream until a CRLF pair is encountered - /// - /// The awaitable task. - /// The maximum number of bytes to read before failing. - /// The size of the read buffer. - /// The time to wait while idle - /// The task that signals request timeout - /// The task that signals stop for the server - internal async Task ReadUntilCrlfAsync(int maxcount, int buffersize, TimeSpan idletimeout, Task timeouttask, Task stoptask) - { - var buf = new byte[buffersize]; - var offset = 0; - - // Avoid the stream if it all fits in a single package - MemoryStream ms = null; - - while (maxcount > 0) - { + if (rt != rtask) + { + if (rt == stoptask) + throw new TaskCanceledException(); + else + throw new HttpException(HttpStatusCode.RequestTimeout); + } + + var r = rtask.Result; + offset += r; + count -= r; + if (r == 0) + throw new HttpException(HttpStatusCode.BadRequest); + } + } + + /// + /// Reads the stream until a CRLF pair is encountered + /// + /// The awaitable task. + /// The maximum number of bytes to read before failing. + /// The size of the read buffer. + /// The time to wait while idle + /// The task that signals request timeout + /// The task that signals stop for the server + internal async Task ReadUntilCrlfAsync(int maxcount, int buffersize, TimeSpan idletimeout, Task timeouttask, Task stoptask) + { + var buf = new byte[buffersize]; + var offset = 0; + + // Avoid the stream if it all fits in a single package + MemoryStream ms = null; + + while (maxcount > 0) + { Task rtask; Task rt; using (var cs = new CancellationTokenSource(idletimeout)) { rtask = ReadAsync(buf, offset, Math.Min(buf.Length - offset, maxcount), cs.Token); - rt = await Task.WhenAny( stoptask, timeouttask, rtask); + rt = await Task.WhenAny(stoptask, timeouttask, rtask); } // Timeout or stop has happened - if (rt != rtask) - { - if (rt == stoptask) - throw new TaskCanceledException(); - else - throw new HttpException(HttpStatusCode.RequestTimeout); - } - - var r = rtask.Result; - offset += r; - maxcount -= r; - if (r == 0) - throw new HttpException(HttpStatusCode.BadRequest); - - var ix = Array.IndexOf(buf, CR, 0, offset); - if (ix >= 0 && ix < offset - 1) - { - if (ix != offset - 1) - throw new HttpException(HttpStatusCode.BadRequest); - - if (ms == null) - { - Array.Resize(ref buf, ix); - return buf; - } - else - { - await ms.WriteAsync(buf, 0, ix); - return ms.ToArray(); - } - } - - // Allocate a stream to pick up the chunks - if (ms == null) - ms = new MemoryStream(); - ms.Write(buf, 0, r - 1); - buf[0] = buf[offset - 1]; - offset = 1; - } - - throw new HttpException(HttpStatusCode.PayloadTooLarge); - } - - /// - /// Appends bytes to the internal buffer. - /// - /// The data to add. - /// The data offset. - /// The number of bytes. - internal void UnreadBytesIntoBuffer(byte[] data, int offset, int count) - { - // If we have no buffered data, just add the new data to the buffer - if (m_buffercount == 0) - { - // Make sure there is space + if (rt != rtask) + { + if (rt == stoptask) + throw new TaskCanceledException(); + else + throw new HttpException(HttpStatusCode.RequestTimeout); + } + + var r = rtask.Result; + offset += r; + maxcount -= r; + if (r == 0) + throw new HttpException(HttpStatusCode.BadRequest); + + var ix = Array.IndexOf(buf, CR, 0, offset); + if (ix >= 0 && ix < offset - 1) + { + if (ix != offset - 1) + throw new HttpException(HttpStatusCode.BadRequest); + + if (ms == null) + { + Array.Resize(ref buf, ix); + return buf; + } + else + { + await ms.WriteAsync(buf, 0, ix); + return ms.ToArray(); + } + } + + // Allocate a stream to pick up the chunks + if (ms == null) + ms = new MemoryStream(); + ms.Write(buf, 0, r - 1); + buf[0] = buf[offset - 1]; + offset = 1; + } + + throw new HttpException(HttpStatusCode.PayloadTooLarge); + } + + /// + /// Appends bytes to the internal buffer. + /// + /// The data to add. + /// The data offset. + /// The number of bytes. + internal void UnreadBytesIntoBuffer(byte[] data, int offset, int count) + { + // If we have no buffered data, just add the new data to the buffer + if (m_buffercount == 0) + { + // Make sure there is space if (m_buffer.Length < count) Array.Resize(ref m_buffer, count); - // Copy in the data + // Copy in the data Array.Copy(data, offset, m_buffer, 0, count); - // Adjust the counters - m_buffercount = count; - m_bufferoffset = 0; - m_remainingbytes += count; + // Adjust the counters + m_buffercount = count; + m_bufferoffset = 0; + m_remainingbytes += count; } // We need to pre-pend the data else - { - // If we can add the data before the current cursor, we do it - if (m_bufferoffset < count) - { - Array.Copy(data, offset, m_buffer, m_bufferoffset - count, count); - m_bufferoffset -= count; - m_buffercount += count; - m_remainingbytes += count; - } - else - { - // Make sure we have space for it - if (m_buffer.Length < count + m_buffercount) + { + // If we can add the data before the current cursor, we do it + if (m_bufferoffset < count) + { + Array.Copy(data, offset, m_buffer, m_bufferoffset - count, count); + m_bufferoffset -= count; + m_buffercount += count; + m_remainingbytes += count; + } + else + { + // Make sure we have space for it + if (m_buffer.Length < count + m_buffercount) Array.Resize(ref m_buffer, m_buffer.Length + count); - // Move the current data so the new data fits before it - Array.Copy(m_buffer, m_bufferoffset, m_buffer, count, m_buffercount); - // Then copy the new data behind it - Array.Copy(data, offset, m_buffer, 0, count); - m_bufferoffset = 0; - m_buffercount += count; + // Move the current data so the new data fits before it + Array.Copy(m_buffer, m_bufferoffset, m_buffer, count, m_buffercount); + // Then copy the new data behind it + Array.Copy(data, offset, m_buffer, 0, count); + m_bufferoffset = 0; + m_buffercount += count; m_remainingbytes += count; - } - } - } - - /// - /// Reads data from the buffer - /// - /// The number of bytes read from the buffer. - /// The target buffer. - /// The target offset. - /// The maximum number of bytes to read. - private int ReadFromBuffer(byte[] buffer, int offset, int count) - { - if (m_buffercount > 0) - { - var size = Math.Min(count, m_buffercount); - Array.Copy(m_buffer, m_bufferoffset, buffer, offset, size); - m_buffercount -= size; - m_bufferoffset = m_buffercount == 0 ? 0 : m_bufferoffset + size; - - return size; - } - - return 0; - } - - #region implemented abstract members of Stream - /// - /// Flush this instance. - /// - public override void Flush() - { - m_parent.Flush(); - } + } + } + } + + /// + /// Reads data from the buffer + /// + /// The number of bytes read from the buffer. + /// The target buffer. + /// The target offset. + /// The maximum number of bytes to read. + private int ReadFromBuffer(byte[] buffer, int offset, int count) + { + if (m_buffercount > 0) + { + var size = Math.Min(count, m_buffercount); + Array.Copy(m_buffer, m_bufferoffset, buffer, offset, size); + m_buffercount -= size; + m_bufferoffset = m_buffercount == 0 ? 0 : m_bufferoffset + size; + + return size; + } + + return 0; + } + + #region implemented abstract members of Stream + /// + /// Flush this instance. + /// + public override void Flush() + { + m_parent.Flush(); + } /// /// Seek the specified offset and origin. /// @@ -419,52 +419,52 @@ public override void Flush() /// The number of bytes to read. /// Cancellation token. public override async Task ReadAsync(byte[] buffer, int offset, int count, System.Threading.CancellationToken cancellationToken) - { - if (m_remainingbytes == 0) - return 0; - - int res; - var mread = (int)Math.Min(count, m_remainingbytes + 1); - if (m_buffercount > 0) - res = ReadFromBuffer(buffer, offset, mread); - else - res = await m_parent.ReadAsync(buffer, offset, mread, cancellationToken); - - m_remainingbytes -= res; - if (m_remainingbytes < 0) - { - m_remainingbytes = 0; - throw new HttpException(HttpStatusCode.PayloadTooLarge); - } - return res; - } - - /// - /// Read data from the stream into the buffer, given offset and count. - /// - /// The buffer to read into. - /// The offset into the buffer where data is written. - /// The number of bytes to read. - public override int Read(byte[] buffer, int offset, int count) - { - if (m_remainingbytes == 0) - return 0; - - int res; - var mread = (int)Math.Min(count, m_remainingbytes + 1); - if (m_buffercount > 0) - res = ReadFromBuffer(buffer, offset, mread); - else - res = m_parent.Read(buffer, offset, mread); - - m_remainingbytes -= res; - if (m_remainingbytes < 0) - { - m_remainingbytes = 0; - throw new HttpException(HttpStatusCode.PayloadTooLarge); - } - return res; - } + { + if (m_remainingbytes == 0) + return 0; + + int res; + var mread = (int)Math.Min(count, m_remainingbytes + 1); + if (m_buffercount > 0) + res = ReadFromBuffer(buffer, offset, mread); + else + res = await m_parent.ReadAsync(buffer, offset, mread, cancellationToken); + + m_remainingbytes -= res; + if (m_remainingbytes < 0) + { + m_remainingbytes = 0; + throw new HttpException(HttpStatusCode.PayloadTooLarge); + } + return res; + } + + /// + /// Read data from the stream into the buffer, given offset and count. + /// + /// The buffer to read into. + /// The offset into the buffer where data is written. + /// The number of bytes to read. + public override int Read(byte[] buffer, int offset, int count) + { + if (m_remainingbytes == 0) + return 0; + + int res; + var mread = (int)Math.Min(count, m_remainingbytes + 1); + if (m_buffercount > 0) + res = ReadFromBuffer(buffer, offset, mread); + else + res = m_parent.Read(buffer, offset, mread); + + m_remainingbytes -= res; + if (m_remainingbytes < 0) + { + m_remainingbytes = 0; + throw new HttpException(HttpStatusCode.PayloadTooLarge); + } + return res; + } /// /// Writes data from the stream into the buffer, given offset and count. /// @@ -478,34 +478,34 @@ public override int Read(byte[] buffer, int offset, int count) /// /// true if this instance can read; otherwise, false. public override bool CanRead - { - get - { - return true; - } - } - /// - /// Gets a value indicating whether this instance can seek. - /// - /// true if this instance can seek; otherwise, false. - public override bool CanSeek - { - get - { - return false; - } - } - /// - /// Gets a value indicating whether this instance can be written. - /// - /// true if this instance can write; otherwise, false. - public override bool CanWrite - { - get - { - return false; - } - } + { + get + { + return true; + } + } + /// + /// Gets a value indicating whether this instance can seek. + /// + /// true if this instance can seek; otherwise, false. + public override bool CanSeek + { + get + { + return false; + } + } + /// + /// Gets a value indicating whether this instance can be written. + /// + /// true if this instance can write; otherwise, false. + public override bool CanWrite + { + get + { + return false; + } + } /// /// Gets the length of the stream. /// @@ -516,7 +516,7 @@ public override bool CanWrite /// Gets or sets the position. /// /// The position. - public override long Position + public override long Position { get => m_maxread - m_remainingbytes; set => throw new NotImplementedException(); diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/DefaultableDictionary.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/DefaultableDictionary.cs index 70ed5ba1e..26ca467c6 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/DefaultableDictionary.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/DefaultableDictionary.cs @@ -26,210 +26,210 @@ namespace Ceen.Httpd /// Implements default values for lookup in a standard dictionary /// internal class DefaultableDictionary : IDictionary - { - /// - /// The backing dictionary - /// - private readonly IDictionary dictionary; - /// - /// The value to return if no matching entry was found - /// - private readonly TValue defaultValue; - - /// - /// Initializes a new instance of the class. - /// - /// The backing dictionary. - /// The default value. - public DefaultableDictionary(IDictionary dictionary, TValue defaultValue = default(TValue)) - { - this.dictionary = dictionary; - this.defaultValue = defaultValue; - } - - /// - /// Gets an enumerator. - /// - public IEnumerator> GetEnumerator() - { - return dictionary.GetEnumerator(); - } - - /// - /// Gets an enumerator. - /// - IEnumerator IEnumerable.GetEnumerator() - { - return GetEnumerator(); - } - - /// - /// Add the specified item to the dictionary. - /// - /// The item to add. - public void Add(KeyValuePair item) - { - dictionary.Add(item); - } - - /// - /// Clear all entries. - /// - public void Clear() - { - dictionary.Clear(); - } - - /// - /// Returns true if the dictionary contains the item, false otherwise - /// - /// The item to look for. - public bool Contains(KeyValuePair item) - { - return dictionary.Contains(item); - } - - /// - /// Copies all entries to the array - /// - /// The target array. - /// The target index where copying starts. - public void CopyTo(KeyValuePair[] array, int arrayIndex) - { - dictionary.CopyTo(array, arrayIndex); - } - - /// - /// Removes an item from the collection - /// - /// true if the item was removed, false otherwise. - public bool Remove(KeyValuePair item) - { - return dictionary.Remove(item); - } - - /// - /// Gets the number of entries. - /// - public int Count - { - get { return dictionary.Count; } - } - - /// - /// Gets a value indicating whether this is read only. - /// - /// true if is read only; otherwise, false. - public bool IsReadOnly - { - get { return dictionary.IsReadOnly; } - } - - /// - /// Checks if an entry with the key exists. - /// - /// true, if key was found, false otherwise. - /// The key to look for. - public bool ContainsKey(TKey key) - { - return dictionary.ContainsKey(key); - } - - /// - /// Add the specified key and value to the dictionary. - /// - /// The key to add. - /// The value to add. - public void Add(TKey key, TValue value) - { - dictionary.Add(key, value); - } - - /// - /// Remove the item with the specified key. - /// - /// The key for the item to remove. - /// true, if key was found, false otherwise. - public bool Remove(TKey key) - { - return dictionary.Remove(key); - } - - /// - /// Tries to get get value for the specified key. - /// - /// true, if key was found, false otherwise. - /// The key to find. - /// The resulting value. - public bool TryGetValue(TKey key, out TValue value) - { - if (!dictionary.TryGetValue(key, out value)) - { - value = defaultValue; - return false; - } - - return true; - } - - /// - /// Gets or sets the with the specified key. - /// - /// The key to look for. - public TValue this[TKey key] - { - get - { - if (!dictionary.ContainsKey(key)) - return defaultValue; - - try - { - return dictionary[key]; - } - catch (KeyNotFoundException) - { - return defaultValue; - } - } - - set { dictionary[key] = value; } - } - - /// - /// Gets all the keys for this dictionary. - /// - public ICollection Keys - { - get { return dictionary.Keys; } - } - - /// - /// Gets all the values for this dictionary. - /// - public ICollection Values - { - get { return dictionary.Values; } - } - } - - /// - /// Defaultable dictionary extensions. - /// - public static class DefaultableDictionaryExtensions - { - /// - /// Returns a defaultable dictionary that wraps the given dictionary - /// - /// The wrapped dictionary value. - /// The wrapped dictionary. - /// The default value. - /// The key type parameter. - /// The data type parameter. - public static IDictionary WithDefaultValue(this IDictionary dictionary, TValue defaultValue = default(TValue)) - { - return new DefaultableDictionary(dictionary, defaultValue); - } - } + { + /// + /// The backing dictionary + /// + private readonly IDictionary dictionary; + /// + /// The value to return if no matching entry was found + /// + private readonly TValue defaultValue; + + /// + /// Initializes a new instance of the class. + /// + /// The backing dictionary. + /// The default value. + public DefaultableDictionary(IDictionary dictionary, TValue defaultValue = default(TValue)) + { + this.dictionary = dictionary; + this.defaultValue = defaultValue; + } + + /// + /// Gets an enumerator. + /// + public IEnumerator> GetEnumerator() + { + return dictionary.GetEnumerator(); + } + + /// + /// Gets an enumerator. + /// + IEnumerator IEnumerable.GetEnumerator() + { + return GetEnumerator(); + } + + /// + /// Add the specified item to the dictionary. + /// + /// The item to add. + public void Add(KeyValuePair item) + { + dictionary.Add(item); + } + + /// + /// Clear all entries. + /// + public void Clear() + { + dictionary.Clear(); + } + + /// + /// Returns true if the dictionary contains the item, false otherwise + /// + /// The item to look for. + public bool Contains(KeyValuePair item) + { + return dictionary.Contains(item); + } + + /// + /// Copies all entries to the array + /// + /// The target array. + /// The target index where copying starts. + public void CopyTo(KeyValuePair[] array, int arrayIndex) + { + dictionary.CopyTo(array, arrayIndex); + } + + /// + /// Removes an item from the collection + /// + /// true if the item was removed, false otherwise. + public bool Remove(KeyValuePair item) + { + return dictionary.Remove(item); + } + + /// + /// Gets the number of entries. + /// + public int Count + { + get { return dictionary.Count; } + } + + /// + /// Gets a value indicating whether this is read only. + /// + /// true if is read only; otherwise, false. + public bool IsReadOnly + { + get { return dictionary.IsReadOnly; } + } + + /// + /// Checks if an entry with the key exists. + /// + /// true, if key was found, false otherwise. + /// The key to look for. + public bool ContainsKey(TKey key) + { + return dictionary.ContainsKey(key); + } + + /// + /// Add the specified key and value to the dictionary. + /// + /// The key to add. + /// The value to add. + public void Add(TKey key, TValue value) + { + dictionary.Add(key, value); + } + + /// + /// Remove the item with the specified key. + /// + /// The key for the item to remove. + /// true, if key was found, false otherwise. + public bool Remove(TKey key) + { + return dictionary.Remove(key); + } + + /// + /// Tries to get get value for the specified key. + /// + /// true, if key was found, false otherwise. + /// The key to find. + /// The resulting value. + public bool TryGetValue(TKey key, out TValue value) + { + if (!dictionary.TryGetValue(key, out value)) + { + value = defaultValue; + return false; + } + + return true; + } + + /// + /// Gets or sets the with the specified key. + /// + /// The key to look for. + public TValue this[TKey key] + { + get + { + if (!dictionary.ContainsKey(key)) + return defaultValue; + + try + { + return dictionary[key]; + } + catch (KeyNotFoundException) + { + return defaultValue; + } + } + + set { dictionary[key] = value; } + } + + /// + /// Gets all the keys for this dictionary. + /// + public ICollection Keys + { + get { return dictionary.Keys; } + } + + /// + /// Gets all the values for this dictionary. + /// + public ICollection Values + { + get { return dictionary.Values; } + } + } + + /// + /// Defaultable dictionary extensions. + /// + public static class DefaultableDictionaryExtensions + { + /// + /// Returns a defaultable dictionary that wraps the given dictionary + /// + /// The wrapped dictionary value. + /// The wrapped dictionary. + /// The default value. + /// The key type parameter. + /// The data type parameter. + public static IDictionary WithDefaultValue(this IDictionary dictionary, TValue defaultValue = default(TValue)) + { + return new DefaultableDictionary(dictionary, defaultValue); + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/DelimitedSubStream.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/DelimitedSubStream.cs index 04721b335..a93716b5f 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/DelimitedSubStream.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/DelimitedSubStream.cs @@ -9,177 +9,177 @@ namespace Ceen.Httpd /// Class that exposes part of the underlying stream to the reader /// internal class DelimitedSubStream : Stream - { - /// - /// The underlying stream - /// - private readonly BufferedStreamReader m_parent; - - /// - /// The delimiter items - /// - private readonly byte[] m_delimiter; - - /// - /// The number of bytes read - /// - private int m_read; - - /// - /// The buffer - /// - private byte[] m_buf; - - /// - /// The number of bytes in the buffer - /// - private int m_buffersize; - - /// - /// A flag indicating that the stream has been read - /// - private bool m_completed; - - /// - /// The maximum idle time - /// - private readonly TimeSpan m_idletime; - - /// - /// The timeout task - /// - private readonly Task m_timeouttask; - - /// - /// The stop task - /// - private readonly Task m_stoptask; - - /// - /// Initializes a new instance of the class. - /// - /// The parent stream. - /// The stream delimiter. - /// The time to wait while idle - /// The task that signals request timeout - /// The task that signals stop for the server - public DelimitedSubStream(BufferedStreamReader parent, byte[] delimiter, TimeSpan idletime, Task timeouttask, Task stoptask) - { - m_parent = parent; - m_delimiter = delimiter; - m_idletime = idletime; - m_timeouttask = timeouttask; - m_stoptask = stoptask; - m_buf = new byte[Math.Max(8 * 1024, delimiter.Length * 2)]; - } - - /// - /// Finds the first match for the delimiter in the buffer. - /// The match may be partial, if insufficient bytes have been read. - /// - /// The delimiter match. - private int FindDelimiterMatch() - { - var lastlookoffset = 0; - var ix = Array.IndexOf(m_buf, m_delimiter[0], lastlookoffset, m_buffersize - lastlookoffset); - if (ix < 0) - return -1; - - do - { - bool match = true; - var counts = Math.Min(m_delimiter.Length, m_buffersize - ix); - for (var i = 1; match && i < counts; i++) - match = m_buf[ix + i] == m_delimiter[i]; - - if (match) - return ix; + { + /// + /// The underlying stream + /// + private readonly BufferedStreamReader m_parent; + + /// + /// The delimiter items + /// + private readonly byte[] m_delimiter; + + /// + /// The number of bytes read + /// + private int m_read; + + /// + /// The buffer + /// + private byte[] m_buf; + + /// + /// The number of bytes in the buffer + /// + private int m_buffersize; + + /// + /// A flag indicating that the stream has been read + /// + private bool m_completed; + + /// + /// The maximum idle time + /// + private readonly TimeSpan m_idletime; + + /// + /// The timeout task + /// + private readonly Task m_timeouttask; + + /// + /// The stop task + /// + private readonly Task m_stoptask; + + /// + /// Initializes a new instance of the class. + /// + /// The parent stream. + /// The stream delimiter. + /// The time to wait while idle + /// The task that signals request timeout + /// The task that signals stop for the server + public DelimitedSubStream(BufferedStreamReader parent, byte[] delimiter, TimeSpan idletime, Task timeouttask, Task stoptask) + { + m_parent = parent; + m_delimiter = delimiter; + m_idletime = idletime; + m_timeouttask = timeouttask; + m_stoptask = stoptask; + m_buf = new byte[Math.Max(8 * 1024, delimiter.Length * 2)]; + } + + /// + /// Finds the first match for the delimiter in the buffer. + /// The match may be partial, if insufficient bytes have been read. + /// + /// The delimiter match. + private int FindDelimiterMatch() + { + var lastlookoffset = 0; + var ix = Array.IndexOf(m_buf, m_delimiter[0], lastlookoffset, m_buffersize - lastlookoffset); + if (ix < 0) + return -1; + + do + { + bool match = true; + var counts = Math.Min(m_delimiter.Length, m_buffersize - ix); + for (var i = 1; match && i < counts; i++) + match = m_buf[ix + i] == m_delimiter[i]; + + if (match) + return ix; lastlookoffset = ix + 1; - ix = Array.IndexOf(m_buf, m_delimiter[0], lastlookoffset, m_buffersize - lastlookoffset); - } while (ix > 0); - - return -1; - } - - /// - /// Reads the data async. - /// - /// The awaitable task. - /// The buffer to read into. - /// The offset into the buffer where data is written. - /// The number of bytes to read. - /// Cancellation token. - public override async Task ReadAsync(byte[] buffer, int offset, int count, System.Threading.CancellationToken cancellationToken) - { - if (m_completed) - return 0; - - if (count > m_buf.Length) - Array.Resize(ref m_buf, count + 1024); - - Task rtask; - Task rt; - - using (var cs = new CancellationTokenSource(m_idletime)) - using (cancellationToken.Register(() => cs.Cancel())) - { - rtask = m_parent.ReadAsync(m_buf, m_buffersize, Math.Max(m_delimiter.Length - m_buffersize, Math.Min(count, m_buf.Length - m_buffersize)), cs.Token); - rt = await Task.WhenAny(m_timeouttask, m_stoptask, rtask); - } - - if (rt != rtask) - { - if (rt == m_stoptask) - throw new TaskCanceledException(); - else - throw new HttpException(HttpStatusCode.RequestTimeout); - } - - var r = rtask.Result; - m_buffersize += r; - if (r == 0) - return r; - - // Return as much as possible - var bytes = Math.Min(count, m_buffersize); - - // Check for the delimiter + ix = Array.IndexOf(m_buf, m_delimiter[0], lastlookoffset, m_buffersize - lastlookoffset); + } while (ix > 0); + + return -1; + } + + /// + /// Reads the data async. + /// + /// The awaitable task. + /// The buffer to read into. + /// The offset into the buffer where data is written. + /// The number of bytes to read. + /// Cancellation token. + public override async Task ReadAsync(byte[] buffer, int offset, int count, System.Threading.CancellationToken cancellationToken) + { + if (m_completed) + return 0; + + if (count > m_buf.Length) + Array.Resize(ref m_buf, count + 1024); + + Task rtask; + Task rt; + + using (var cs = new CancellationTokenSource(m_idletime)) + using (cancellationToken.Register(() => cs.Cancel())) + { + rtask = m_parent.ReadAsync(m_buf, m_buffersize, Math.Max(m_delimiter.Length - m_buffersize, Math.Min(count, m_buf.Length - m_buffersize)), cs.Token); + rt = await Task.WhenAny(m_timeouttask, m_stoptask, rtask); + } + + if (rt != rtask) + { + if (rt == m_stoptask) + throw new TaskCanceledException(); + else + throw new HttpException(HttpStatusCode.RequestTimeout); + } + + var r = rtask.Result; + m_buffersize += r; + if (r == 0) + return r; + + // Return as much as possible + var bytes = Math.Min(count, m_buffersize); + + // Check for the delimiter var ix = FindDelimiterMatch(); // If we found a (partial) delimiter match, // only return bytes leading up to the marker if (ix >= 0) - bytes = Math.Min(count, ix); + bytes = Math.Min(count, ix); - // Copy bytes to the reader - if (bytes != 0) - { - Array.Copy(m_buf, 0, buffer, offset, bytes); - } + // Copy bytes to the reader + if (bytes != 0) + { + Array.Copy(m_buf, 0, buffer, offset, bytes); + } - // Store what we read ahead in the buffer - if (bytes != m_buffersize) - Array.Copy(m_buf, ix, m_buf, 0, m_buffersize - ix); + // Store what we read ahead in the buffer + if (bytes != m_buffersize) + Array.Copy(m_buf, ix, m_buf, 0, m_buffersize - ix); - // Adjust with the bytes taken + // Adjust with the bytes taken m_buffersize -= bytes; // If we found the delimiter in full, we are done if (ix >= 0 && m_buffersize >= m_delimiter.Length) - { - m_completed = true; - // Drop the delimiter from the buffer - m_buffersize -= m_delimiter.Length; - // If we have more, stuff it back into the parent's buffer - if (m_buffersize != 0) - m_parent.UnreadBytesIntoBuffer(m_buf, m_delimiter.Length, m_buffersize); - m_buffersize = 0; - } - - m_read += bytes; - return bytes; - } + { + m_completed = true; + // Drop the delimiter from the buffer + m_buffersize -= m_delimiter.Length; + // If we have more, stuff it back into the parent's buffer + if (m_buffersize != 0) + m_parent.UnreadBytesIntoBuffer(m_buf, m_delimiter.Length, m_buffersize); + m_buffersize = 0; + } + + m_read += bytes; + return bytes; + } #region implemented abstract members of Stream public override int Read(byte[] buffer, int offset, int count) => this.ReadAsync(buffer, offset, count).Result; diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/CORSHandler.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/CORSHandler.cs index 2fbf966cb..af1d362ff 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/CORSHandler.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/CORSHandler.cs @@ -48,7 +48,7 @@ public void AfterConfigure() if (Array.IndexOf(AllowedOrigins, "*") >= 0) AllowedOrigins = new string[] { "*" }; - m_originMatcher = + m_originMatcher = new System.Text.RegularExpressions.Regex( string.Join("|", AllowedOrigins @@ -71,7 +71,7 @@ public Task HandleAsync(IHttpContext context, CancellationToken cancellati if (string.IsNullOrWhiteSpace(origin) || m_originMatcher.Match(origin).Length != origin.Length) { context.Response.StatusCode = Ceen.HttpStatusCode.NotAcceptable; - return Task.FromResult(preflight); + return Task.FromResult(preflight); } context.Response.Headers.Add("Access-Control-Allow-Origin", origin); diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/ClearRequestStateHandler.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/ClearRequestStateHandler.cs index e22cb9eae..e8b3885ef 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/ClearRequestStateHandler.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/ClearRequestStateHandler.cs @@ -8,7 +8,7 @@ namespace Ceen.Httpd.Handler /// A handler that clears the request state /// internal class ClearRequestStateHandler : IHttpModule - { + { /// /// Handles the request. /// @@ -16,9 +16,9 @@ internal class ClearRequestStateHandler : IHttpModule /// The http context. /// The token indicating to stop handling. public Task HandleAsync(IHttpContext context, CancellationToken cancellationToken) - { - context.Request.RequestState.Clear(); - return Task.FromResult(false); - } - } + { + context.Request.RequestState.Clear(); + return Task.FromResult(false); + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/FileHandler.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/FileHandler.cs index a57248b57..91cd220fa 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/FileHandler.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/FileHandler.cs @@ -611,7 +611,7 @@ protected virtual async Task ServeRequest(string path, string mimetype, IH context.Response.StatusCode = HttpStatusCode.OK; context.Response.AddHeader("Last-Modified", lastmodified.ToString("R", CultureInfo.InvariantCulture)); context.Response.AddHeader("Accept-Ranges", "bytes"); - + // If the VFS or something else handles cache headers, do not overwrite them here if (!context.Response.Headers.ContainsKey("Cache-Control") && !context.Response.Headers.ContainsKey("Expires")) context.Response.SetExpires(CacheSeconds); @@ -654,7 +654,7 @@ protected virtual async Task ServeRequest(string path, string mimetype, IH fs.Position = startoffset; var remain = context.Response.ContentLength; var buf = new byte[TransferChunkSize]; - + // Since this is a transfer, we do not honor the processing timeout here //var ct = context.Request.TimeoutCancellationToken; @@ -663,7 +663,7 @@ protected virtual async Task ServeRequest(string path, string mimetype, IH while (remain > 0) { var r = await fs.ReadAsync(buf, 0, (int)Math.Min(buf.Length, remain)); - using(var ct = new CancellationTokenSource(ActivityTimeoutSeconds)) + using (var ct = new CancellationTokenSource(ActivityTimeoutSeconds)) await os.WriteAsync(buf, 0, r, ct.Token); remain -= r; } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/FileMirrorHandler.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/FileMirrorHandler.cs index f5211cb4a..54fca3634 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/FileMirrorHandler.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/FileMirrorHandler.cs @@ -264,7 +264,7 @@ private async Task PiggyBackDownloadAsync(IHttpContext context, string localpath if (read == 0) break; - using(var ct = new CancellationTokenSource(ActivityTimeoutSeconds)) + using (var ct = new CancellationTokenSource(ActivityTimeoutSeconds)) await os.WriteAsync(buf, 0, read, ct.Token); written += read; } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/FunctionHandler.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/FunctionHandler.cs index f1330c06f..edb55d87e 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/FunctionHandler.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/FunctionHandler.cs @@ -8,20 +8,20 @@ namespace Ceen.Httpd.Handler /// Implementation of a handler that operates on a lambda method or other delegate /// internal class FunctionHandler : IHttpModule - { - /// - /// The actual handler - /// - private readonly HttpHandlerDelegate m_handler; + { + /// + /// The actual handler + /// + private readonly HttpHandlerDelegate m_handler; - /// - /// Initializes a new instance of the class. - /// - /// The handler to invoke. - public FunctionHandler(HttpHandlerDelegate handler) - { - m_handler = handler; - } + /// + /// Initializes a new instance of the class. + /// + /// The handler to invoke. + public FunctionHandler(HttpHandlerDelegate handler) + { + m_handler = handler; + } #region IHttpModule implementation @@ -32,21 +32,21 @@ public FunctionHandler(HttpHandlerDelegate handler) /// The request context. /// The token indicating to stop handling. public Task HandleAsync(IHttpContext context, CancellationToken cancellationToken) - { - return m_handler(context); - } + { + return m_handler(context); + } - #endregion + #endregion - /// - /// Implicit conversion from a delegate or lambda to a function handler - /// - /// The handler instance. - /// The delegate to invoke. - public static implicit operator FunctionHandler(HttpHandlerDelegate handler) - { - return new FunctionHandler(handler); - } - } + /// + /// Implicit conversion from a delegate or lambda to a function handler + /// + /// The handler instance. + /// The delegate to invoke. + public static implicit operator FunctionHandler(HttpHandlerDelegate handler) + { + return new FunctionHandler(handler); + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/RedirectHandler.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/RedirectHandler.cs index f294c61d3..7bb88663d 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/RedirectHandler.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/RedirectHandler.cs @@ -8,37 +8,37 @@ namespace Ceen.Httpd.Handler /// Simple handler that performs a redirect /// internal class RedirectHandler : IHttpModule - { - /// - /// Gets or sets the status code used to report the redirect. - /// - public HttpStatusCode StatusCode { get; set; } = HttpStatusCode.MovedPermanently; + { + /// + /// Gets or sets the status code used to report the redirect. + /// + public HttpStatusCode StatusCode { get; set; } = HttpStatusCode.MovedPermanently; - /// - /// Gets or sets the status message used to report the redirect. - /// - public string StatusMessage { get; set; } + /// + /// Gets or sets the status message used to report the redirect. + /// + public string StatusMessage { get; set; } - /// - /// Gets or sets a value indicating if the redirect is performed internally - /// - public bool InternalRedirect { get; set; } = false; + /// + /// Gets or sets a value indicating if the redirect is performed internally + /// + public bool InternalRedirect { get; set; } = false; - /// - /// Gets or sets the redirection target value - /// - public string RedirectTarget { get; set; } + /// + /// Gets or sets the redirection target value + /// + public string RedirectTarget { get; set; } - /// - /// Initializes a new instance of the class. - /// - public RedirectHandler() { } + /// + /// Initializes a new instance of the class. + /// + public RedirectHandler() { } - /// - /// Initializes a new instance of the class. - /// - /// The redirect target url. - public RedirectHandler(string target) { RedirectTarget = target; } + /// + /// Initializes a new instance of the class. + /// + /// The redirect target url. + public RedirectHandler(string target) { RedirectTarget = target; } /// /// Handles the request by sending a redirect @@ -47,19 +47,19 @@ public RedirectHandler() { } /// The http context. /// The token indicating to stop handling. public Task HandleAsync(IHttpContext context, CancellationToken cancellationToken) - { - if (InternalRedirect) - { - context.Response.InternalRedirect(RedirectTarget); - } - else - { - context.Response.StatusCode = StatusCode; - context.Response.StatusMessage = StatusMessage; - context.Response.AddHeader("Location", RedirectTarget); - } + { + if (InternalRedirect) + { + context.Response.InternalRedirect(RedirectTarget); + } + else + { + context.Response.StatusCode = StatusCode; + context.Response.StatusMessage = StatusMessage; + context.Response.AddHeader("Location", RedirectTarget); + } - return Task.FromResult(true); - } - } + return Task.FromResult(true); + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/SessionHandler.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/SessionHandler.cs index e4ec078f2..46e317c6f 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/SessionHandler.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/SessionHandler.cs @@ -5,27 +5,27 @@ namespace Ceen.Httpd.Handler { internal class SessionHandler : IHttpModule - { - /// - /// The name of the storage module - /// - public const string STORAGE_MODULE_NAME = "session-storage"; + { + /// + /// The name of the storage module + /// + public const string STORAGE_MODULE_NAME = "session-storage"; - /// - /// Gets or sets the name of the cookie with the token. - /// - public string CookieName { get; set; } = "ceen-session-token"; + /// + /// Gets or sets the name of the cookie with the token. + /// + public string CookieName { get; set; } = "ceen-session-token"; - /// - /// Gets or sets the number of seconds a session is valid. - /// - public TimeSpan ExpirationSeconds { get; set; } = TimeSpan.FromMinutes(30); + /// + /// Gets or sets the number of seconds a session is valid. + /// + public TimeSpan ExpirationSeconds { get; set; } = TimeSpan.FromMinutes(30); - /// - /// Gets or sets a value indicating if the session cookie gets the "secure" option set, - /// meaning that it will only be sent over HTTPS - /// - public bool SessionCookieSecure { get; set; } = false; + /// + /// Gets or sets a value indicating if the session cookie gets the "secure" option set, + /// meaning that it will only be sent over HTTPS + /// + public bool SessionCookieSecure { get; set; } = false; /// /// Gets or sets the value for the cookie "samesite" attribute. @@ -40,26 +40,26 @@ internal class SessionHandler : IHttpModule /// The requests context. /// The token indicating to stop handling. public async Task HandleAsync(IHttpContext context, CancellationToken cancellationToken) - { - if (context.Session != null) - return false; - - var sessiontoken = context.Request.SessionID = context.Request.Cookies[CookieName]; + { + if (context.Session != null) + return false; + + var sessiontoken = context.Request.SessionID = context.Request.Cookies[CookieName]; - if (!string.IsNullOrWhiteSpace(sessiontoken)) - { - // If the session exists, hook it up - context.Session = await context.Storage.GetStorageAsync(STORAGE_MODULE_NAME, sessiontoken, (int)ExpirationSeconds.TotalSeconds, false); - if (context.Session != null) - return false; - } + if (!string.IsNullOrWhiteSpace(sessiontoken)) + { + // If the session exists, hook it up + context.Session = await context.Storage.GetStorageAsync(STORAGE_MODULE_NAME, sessiontoken, (int)ExpirationSeconds.TotalSeconds, false); + if (context.Session != null) + return false; + } - // Create new storage - sessiontoken = context.Request.SessionID = Guid.NewGuid().ToString(); - context.Response.AddCookie(CookieName, sessiontoken, secure: SessionCookieSecure, httponly: true, samesite: SessionCookieSameSite); - context.Session = await context.Storage.GetStorageAsync(STORAGE_MODULE_NAME, sessiontoken, (int)ExpirationSeconds.TotalSeconds, true); + // Create new storage + sessiontoken = context.Request.SessionID = Guid.NewGuid().ToString(); + context.Response.AddCookie(CookieName, sessiontoken, secure: SessionCookieSecure, httponly: true, samesite: SessionCookieSameSite); + context.Session = await context.Storage.GetStorageAsync(STORAGE_MODULE_NAME, sessiontoken, (int)ExpirationSeconds.TotalSeconds, true); - return false; - } - } + return false; + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/SimpleProxyHandler.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/SimpleProxyHandler.cs index 5a5db2690..c2c69d5b2 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/SimpleProxyHandler.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Handler/SimpleProxyHandler.cs @@ -63,10 +63,10 @@ public async Task HandleAsync(IHttpContext context, CancellationToken canc wr.Method = context.Request.Method; if (context.Request.ContentLength > 0) - using(var rs = await wr.GetRequestStreamAsync()) + using (var rs = await wr.GetRequestStreamAsync()) await context.Request.Body.CopyToAsync(rs); - using(var res = await GetResponseWithoutExceptionAsync(wr)) + using (var res = await GetResponseWithoutExceptionAsync(wr)) { foreach (var key in res.Headers.AllKeys) context.Response.Headers[key] = res.Headers[key]; @@ -80,7 +80,7 @@ public async Task HandleAsync(IHttpContext context, CancellationToken canc await context.Response.FlushHeadersAsync(); using (var r = context.Response.GetResponseStream()) - using(var rr = res.GetResponseStream()) + using (var rr = res.GetResponseStream()) #if NET5_0_OR_GREATER await rr.CopyToAsync(r, context.Request.TimeoutCancellationToken); diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/HttpContext.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/HttpContext.cs index a050a63cc..754c07579 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/HttpContext.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/HttpContext.cs @@ -8,62 +8,62 @@ namespace Ceen.Httpd /// A http context /// internal class HttpContext : IHttpContext - { - /// - /// Gets the HTTP request - /// - public IHttpRequestInternal Request { get; private set; } - /// - /// Gets the HTTP response. - /// - public IHttpResponse Response { get; private set; } + { + /// + /// Gets the HTTP request + /// + public IHttpRequestInternal Request { get; private set; } + /// + /// Gets the HTTP response. + /// + public IHttpResponse Response { get; private set; } - /// - /// Gets the storage creator - /// - public IStorageCreator Storage { get; private set; } + /// + /// Gets the storage creator + /// + public IStorageCreator Storage { get; private set; } - /// - /// Gets the loaded module info - /// - /// - public ILoadedModuleInfo LoadedModules { get => m_config; } + /// + /// Gets the loaded module info + /// + /// + public ILoadedModuleInfo LoadedModules { get => m_config; } - /// - /// The runner executing the request - /// - private readonly ServerConfig m_config; + /// + /// The runner executing the request + /// + private readonly ServerConfig m_config; - /// - /// Gets or sets the session storage. - /// Note that this can be null if there is no session module loaded. - /// - public IDictionary Session { get; set; } + /// + /// Gets or sets the session storage. + /// Note that this can be null if there is no session module loaded. + /// + public IDictionary Session { get; set; } - /// - /// Additional data that can be used in a logging module to tag the request or response - /// - public IDictionary LogData { get; } = new Dictionary(); + /// + /// Additional data that can be used in a logging module to tag the request or response + /// + public IDictionary LogData { get; } = new Dictionary(); - /// - /// The delegate used to forward exceptions to the loggers - /// - internal Func LogHandlerDelegate { get; set;} + /// + /// The delegate used to forward exceptions to the loggers + /// + internal Func LogHandlerDelegate { get; set; } - /// - /// Initializes a new instance of the class. - /// - /// The HTTP request. - /// The HTTP response. - /// The storage instance - /// The server config - public HttpContext(HttpRequest request, HttpResponse response, IStorageCreator storage, ServerConfig config) - { - this.Request = request; - this.Response = response; - this.Storage = storage; - this.m_config = config; - } + /// + /// Initializes a new instance of the class. + /// + /// The HTTP request. + /// The HTTP response. + /// The storage instance + /// The server config + public HttpContext(HttpRequest request, HttpResponse response, IStorageCreator storage, ServerConfig config) + { + this.Request = request; + this.Response = response; + this.Storage = storage; + this.m_config = config; + } /// /// Logs a message diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/HttpRequest.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/HttpRequest.cs index a3a2b93a7..feac91ccb 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/HttpRequest.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/HttpRequest.cs @@ -77,12 +77,12 @@ internal class HttpRequest : IHttpRequestInternal, IDisposable /// Gets the http version string. /// public string HttpVersion { get; private set; } - /// - /// Gets or sets a user identifier attached to the request. - /// This can be set by handlers processing the request to simplify dealing with logged in users. - /// Handlers should only set this is the user is authenticated. - /// This value can be logged. - /// + /// + /// Gets or sets a user identifier attached to the request. + /// This can be set by handlers processing the request to simplify dealing with logged in users. + /// Handlers should only set this is the user is authenticated. + /// This value can be logged. + /// public string UserID { get; set; } /// /// Gets or sets a session tracking ID. @@ -183,16 +183,16 @@ public string ContentType } } - /// - /// Gets the HTTP request hostname, can be null for a HTTP/1.0 request - /// + /// + /// Gets the HTTP request hostname, can be null for a HTTP/1.0 request + /// public string Hostname { get { return Headers["Host"]; } - } + } /// /// Gets the HTTP Content-Length header value @@ -372,7 +372,7 @@ await reader.ReadHeaders( if (trail[0] != '-' || trail[1] != '-') - throw new HttpException(HttpStatusCode.BadRequest); + throw new HttpException(HttpStatusCode.BadRequest); await reader.RepeatReadAsync(trail, 0, 2, idletime, timeouttask, stoptask); if (trail[0] != '\r' || trail[1] != '\n') @@ -516,14 +516,14 @@ await reader.ReadHeaders( if (this.ContentLength > config.MaxPostSize) throw new HttpException(HttpStatusCode.PayloadTooLarge); - + // Disable HTTP/1.0 unless explictly allowed if (!config.AllowLegacyHttp && this.HttpVersion == HTTP_VERSION_1_0) throw new HttpException(HttpStatusCode.HTTPVersionNotSupported); // Enforce HTTP/1.1 requiring a header if (this.HttpVersion != HTTP_VERSION_1_0 && string.IsNullOrWhiteSpace(this.Headers["Host"])) - throw new HttpException(HttpStatusCode.BadRequest, "Host header missing"); + throw new HttpException(HttpStatusCode.BadRequest, "Host header missing"); if (config.AllowHttpMethodOverride) { diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/HttpResponse.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/HttpResponse.cs index 9d2b7544b..f01395eed 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/HttpResponse.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/HttpResponse.cs @@ -9,528 +9,528 @@ namespace Ceen.Httpd { - /// - /// Interface for providing a HTTP response - /// - internal class HttpResponse : IHttpResponse - { - /// - /// Dictionary wrapper to keep track of what headers to emit - /// - private class HttpResponseHeaders : IDictionary - { - /// - /// The wrapped parent - /// - private readonly HttpResponse m_parent; - - /// - /// Initializes a new instance of the class. - /// - /// The parent to wrap. - public HttpResponseHeaders(HttpResponse parent) - { - m_parent = parent; - } - - #region IDictionary implementation - public bool ContainsKey(string key) - { - return m_parent.m_headers.ContainsKey(key); - } - public void Add(string key, string value) - { - m_parent.AddHeader(key, value); - } - public bool Remove(string key) - { - var hasit = ContainsKey(key); - m_parent.AddHeader(key, null); - return hasit; - } - public bool TryGetValue(string key, out string value) - { - return m_parent.m_headers.TryGetValue(key, out value); - } - public string this[string index] - { - get - { - string s; - if (!TryGetValue(index, out s)) - s = null; - - return s; - } - set - { - m_parent.AddHeader(index, value); - } - } - public ICollection Keys - { - get - { - return m_parent.m_headers.Keys; - } - } - public ICollection Values - { - get - { - return m_parent.m_headers.Values; - } - } - #endregion - #region ICollection implementation - public void Add(KeyValuePair item) - { - m_parent.AddHeader(item.Key, item.Value); - } - public void Clear() - { - if (m_parent.HasSentHeaders) - m_parent.AddHeader("dummy", "dummy"); // Trigger exeception - m_parent.m_headers.Clear(); - } - public bool Contains(KeyValuePair item) - { - string value; - return TryGetValue(item.Key, out value) && value == item.Value; - } - public void CopyTo(KeyValuePair[] array, int arrayIndex) - { - throw new NotImplementedException(); - } - public bool Remove(KeyValuePair item) - { - if (Contains(item) || m_parent.HasSentHeaders) - { - Remove(item.Key); - return true; - } - - return false; - } - public int Count - { - get - { - return m_parent.m_headers.Count; - } - } - public bool IsReadOnly - { - get - { - return m_parent.HasSentHeaders; - } - } - #endregion - #region IEnumerable implementation - public IEnumerator> GetEnumerator() - { - return m_parent.m_headers.GetEnumerator(); - } - #endregion - #region IEnumerable implementation - System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator() - { - return this.GetEnumerator(); - } - #endregion - } - - /// - /// Gets or sets the HTTP version to report. - /// - /// The http version. - public string HttpVersion { get; set; } - /// - /// Gets or sets the status code to report. - /// - /// The status code. - public HttpStatusCode StatusCode { get; set; } - /// - /// Gets or sets the status message to report. - /// If this is null, the default message for - /// the HTTP status code is used - /// - /// The status message. - public string StatusMessage { get; set; } - /// - /// Gets a value indicating whether the sent headers are sent to the client. - /// Once the headers are sent, the header collection can no longer be modified - /// - /// true if this instance has sent headers; otherwise, false. - public bool HasSentHeaders { get { return m_hasSentHeaders; } } - /// - /// Dictionary with headers that are sent as part of the response. - /// Cannot be modified after the headers have been sent. - /// - /// The headers. - public IDictionary Headers { get { return m_headerwrapper; } } - - /// - /// Gets a list of cookies that are set with the response. - /// Cannot be modified after the headers have been sent. - /// - /// The cookies. - public IList Cookies { get; private set; } - - /// - /// The underlying output stream - /// - private Stream m_stream; - /// - /// The intercepting output stream exposed from this instance - /// - private ResponseOutputStream m_outstream; - /// - /// The wrapped output stream - /// - private Stream m_wrappedoutstream; - /// - /// The internal storage for the response headers - /// - private Dictionary m_headers; - /// - /// The value indicating if the headers have been sent - /// - private bool m_hasSentHeaders = false; - /// - /// The wrapper class for controlling headers - /// - private HttpResponseHeaders m_headerwrapper; - /// - /// The server configuration - /// - private readonly ServerConfig m_serverconfig; - /// - /// The internal redirect path - /// - private string m_internalredirectpath; - /// - /// The number of internal redirects used - /// - private int m_internalredirects; - - /// - /// The CRLF line termination string - /// - private const string CRLF = "\r\n"; - - /// - /// Initializes a new instance of the class. - /// - /// The underlying stream. - /// The server configuration. - public HttpResponse(Stream stream, ServerConfig config) - { - m_stream = stream; - m_serverconfig = config; - m_headerwrapper = new HttpResponseHeaders(this); - Cookies = new List(); - Reset(); - } - - /// - /// Resets this instance so it can be re-used - /// - private void Reset() - { - this.HttpVersion = "HTTP/1.1"; - this.StatusCode = HttpStatusCode.OK; - - m_headers = new Dictionary(); - m_outstream = new ResponseOutputStream(m_stream, this); - m_wrappedoutstream = m_outstream; - m_hasSentHeaders = false; - - AddDefaultHeaders(); - } - - /// - /// Adds the default headers - /// - private void AddDefaultHeaders() - { - if (m_serverconfig.AddDefaultResponseHeaders != null) - m_serverconfig.AddDefaultResponseHeaders(this); - } - - /// - /// Adds a header to the output, use null to delete a header. - /// This method throws an exception if the headers are already sent - /// - /// The header name. - /// The header value. - public void AddHeader(string key, string value) - { - if (m_hasSentHeaders) - throw new InvalidOperationException("Cannot set headers after they are sent"); - - if (value == null) - m_headers.Remove(key); - else - m_headers[key] = value; - } - - /// - /// Gets or sets the Content-Type header - /// - /// The type of the content. - public string ContentType - { - get - { - m_headers.TryGetValue("Content-Type", out var v); - return v; - } - set - { - AddHeader("Content-Type", value); - } - } - - /// - /// Gets or sets the Content-Length header - /// - /// The length of the content. - public long ContentLength - { - get - { - m_headers.TryGetValue("Content-Length", out var v); - - if (!long.TryParse(v, out var vv)) - return -1; - - return vv; - } - set - { - AddHeader("Content-Length", value == -1 ? null : value.ToString()); - } - } - - /// - /// Gets or sets the Keep-Alive header - /// - /// true if keep alive; otherwise, false. - public bool KeepAlive - { - get - { - m_headers.TryGetValue("Connection", out var v); - return string.Equals("keep-alive", v, StringComparison.OrdinalIgnoreCase); - } - set - { - AddHeader("Connection", value ? "keep-alive" : "close"); - } - } - - /// - /// Helper property to check if the internal stream has written the number of bytes - /// sent with Content-Length. Used to determine if keep-alive is possible - /// - /// true if this instance has written correct length; otherwise, false. - internal bool HasWrittenCorrectLength - { - get - { - if (ContentLength < 0) - return false; - - return m_outstream.Length == ContentLength; - } - } - - /// - /// Flush all headers async. - /// This method can be called multiple times if desired. - /// - /// The headers async. - public async Task FlushHeadersAsync() - { - if (!m_hasSentHeaders) - { - // Allow post-processor hook-ins - if (m_serverconfig.PostProcessors != null) - foreach(var p in m_serverconfig.PostProcessors) - await p.HandleAsync(this.Context); - - if (string.IsNullOrWhiteSpace(this.StatusMessage)) - this.StatusMessage = HttpStatusMessages.DefaultMessage(this.StatusCode); - - var line = Encoding.ASCII.GetBytes(string.Format("{0} {1} {2}{3}", this.HttpVersion, (int)this.StatusCode, this.StatusMessage, CRLF)); - await m_stream.WriteAsync(line, 0, line.Length); - - foreach (var e in m_headers) - { - line = Encoding.ASCII.GetBytes(string.Format("{0}: {1}{2}", e.Key, e.Value, CRLF)); - await m_stream.WriteAsync(line, 0, line.Length); - } - - foreach (var cookie in Cookies) - { - var sb = new StringBuilder(); - sb.Append("Set-Cookie: "); - sb.Append(cookie.Name); + /// + /// Interface for providing a HTTP response + /// + internal class HttpResponse : IHttpResponse + { + /// + /// Dictionary wrapper to keep track of what headers to emit + /// + private class HttpResponseHeaders : IDictionary + { + /// + /// The wrapped parent + /// + private readonly HttpResponse m_parent; + + /// + /// Initializes a new instance of the class. + /// + /// The parent to wrap. + public HttpResponseHeaders(HttpResponse parent) + { + m_parent = parent; + } + + #region IDictionary implementation + public bool ContainsKey(string key) + { + return m_parent.m_headers.ContainsKey(key); + } + public void Add(string key, string value) + { + m_parent.AddHeader(key, value); + } + public bool Remove(string key) + { + var hasit = ContainsKey(key); + m_parent.AddHeader(key, null); + return hasit; + } + public bool TryGetValue(string key, out string value) + { + return m_parent.m_headers.TryGetValue(key, out value); + } + public string this[string index] + { + get + { + string s; + if (!TryGetValue(index, out s)) + s = null; + + return s; + } + set + { + m_parent.AddHeader(index, value); + } + } + public ICollection Keys + { + get + { + return m_parent.m_headers.Keys; + } + } + public ICollection Values + { + get + { + return m_parent.m_headers.Values; + } + } + #endregion + #region ICollection implementation + public void Add(KeyValuePair item) + { + m_parent.AddHeader(item.Key, item.Value); + } + public void Clear() + { + if (m_parent.HasSentHeaders) + m_parent.AddHeader("dummy", "dummy"); // Trigger exeception + m_parent.m_headers.Clear(); + } + public bool Contains(KeyValuePair item) + { + string value; + return TryGetValue(item.Key, out value) && value == item.Value; + } + public void CopyTo(KeyValuePair[] array, int arrayIndex) + { + throw new NotImplementedException(); + } + public bool Remove(KeyValuePair item) + { + if (Contains(item) || m_parent.HasSentHeaders) + { + Remove(item.Key); + return true; + } + + return false; + } + public int Count + { + get + { + return m_parent.m_headers.Count; + } + } + public bool IsReadOnly + { + get + { + return m_parent.HasSentHeaders; + } + } + #endregion + #region IEnumerable implementation + public IEnumerator> GetEnumerator() + { + return m_parent.m_headers.GetEnumerator(); + } + #endregion + #region IEnumerable implementation + System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator() + { + return this.GetEnumerator(); + } + #endregion + } + + /// + /// Gets or sets the HTTP version to report. + /// + /// The http version. + public string HttpVersion { get; set; } + /// + /// Gets or sets the status code to report. + /// + /// The status code. + public HttpStatusCode StatusCode { get; set; } + /// + /// Gets or sets the status message to report. + /// If this is null, the default message for + /// the HTTP status code is used + /// + /// The status message. + public string StatusMessage { get; set; } + /// + /// Gets a value indicating whether the sent headers are sent to the client. + /// Once the headers are sent, the header collection can no longer be modified + /// + /// true if this instance has sent headers; otherwise, false. + public bool HasSentHeaders { get { return m_hasSentHeaders; } } + /// + /// Dictionary with headers that are sent as part of the response. + /// Cannot be modified after the headers have been sent. + /// + /// The headers. + public IDictionary Headers { get { return m_headerwrapper; } } + + /// + /// Gets a list of cookies that are set with the response. + /// Cannot be modified after the headers have been sent. + /// + /// The cookies. + public IList Cookies { get; private set; } + + /// + /// The underlying output stream + /// + private Stream m_stream; + /// + /// The intercepting output stream exposed from this instance + /// + private ResponseOutputStream m_outstream; + /// + /// The wrapped output stream + /// + private Stream m_wrappedoutstream; + /// + /// The internal storage for the response headers + /// + private Dictionary m_headers; + /// + /// The value indicating if the headers have been sent + /// + private bool m_hasSentHeaders = false; + /// + /// The wrapper class for controlling headers + /// + private HttpResponseHeaders m_headerwrapper; + /// + /// The server configuration + /// + private readonly ServerConfig m_serverconfig; + /// + /// The internal redirect path + /// + private string m_internalredirectpath; + /// + /// The number of internal redirects used + /// + private int m_internalredirects; + + /// + /// The CRLF line termination string + /// + private const string CRLF = "\r\n"; + + /// + /// Initializes a new instance of the class. + /// + /// The underlying stream. + /// The server configuration. + public HttpResponse(Stream stream, ServerConfig config) + { + m_stream = stream; + m_serverconfig = config; + m_headerwrapper = new HttpResponseHeaders(this); + Cookies = new List(); + Reset(); + } + + /// + /// Resets this instance so it can be re-used + /// + private void Reset() + { + this.HttpVersion = "HTTP/1.1"; + this.StatusCode = HttpStatusCode.OK; + + m_headers = new Dictionary(); + m_outstream = new ResponseOutputStream(m_stream, this); + m_wrappedoutstream = m_outstream; + m_hasSentHeaders = false; + + AddDefaultHeaders(); + } + + /// + /// Adds the default headers + /// + private void AddDefaultHeaders() + { + if (m_serverconfig.AddDefaultResponseHeaders != null) + m_serverconfig.AddDefaultResponseHeaders(this); + } + + /// + /// Adds a header to the output, use null to delete a header. + /// This method throws an exception if the headers are already sent + /// + /// The header name. + /// The header value. + public void AddHeader(string key, string value) + { + if (m_hasSentHeaders) + throw new InvalidOperationException("Cannot set headers after they are sent"); + + if (value == null) + m_headers.Remove(key); + else + m_headers[key] = value; + } + + /// + /// Gets or sets the Content-Type header + /// + /// The type of the content. + public string ContentType + { + get + { + m_headers.TryGetValue("Content-Type", out var v); + return v; + } + set + { + AddHeader("Content-Type", value); + } + } + + /// + /// Gets or sets the Content-Length header + /// + /// The length of the content. + public long ContentLength + { + get + { + m_headers.TryGetValue("Content-Length", out var v); + + if (!long.TryParse(v, out var vv)) + return -1; + + return vv; + } + set + { + AddHeader("Content-Length", value == -1 ? null : value.ToString()); + } + } + + /// + /// Gets or sets the Keep-Alive header + /// + /// true if keep alive; otherwise, false. + public bool KeepAlive + { + get + { + m_headers.TryGetValue("Connection", out var v); + return string.Equals("keep-alive", v, StringComparison.OrdinalIgnoreCase); + } + set + { + AddHeader("Connection", value ? "keep-alive" : "close"); + } + } + + /// + /// Helper property to check if the internal stream has written the number of bytes + /// sent with Content-Length. Used to determine if keep-alive is possible + /// + /// true if this instance has written correct length; otherwise, false. + internal bool HasWrittenCorrectLength + { + get + { + if (ContentLength < 0) + return false; + + return m_outstream.Length == ContentLength; + } + } + + /// + /// Flush all headers async. + /// This method can be called multiple times if desired. + /// + /// The headers async. + public async Task FlushHeadersAsync() + { + if (!m_hasSentHeaders) + { + // Allow post-processor hook-ins + if (m_serverconfig.PostProcessors != null) + foreach (var p in m_serverconfig.PostProcessors) + await p.HandleAsync(this.Context); + + if (string.IsNullOrWhiteSpace(this.StatusMessage)) + this.StatusMessage = HttpStatusMessages.DefaultMessage(this.StatusCode); + + var line = Encoding.ASCII.GetBytes(string.Format("{0} {1} {2}{3}", this.HttpVersion, (int)this.StatusCode, this.StatusMessage, CRLF)); + await m_stream.WriteAsync(line, 0, line.Length); + + foreach (var e in m_headers) + { + line = Encoding.ASCII.GetBytes(string.Format("{0}: {1}{2}", e.Key, e.Value, CRLF)); + await m_stream.WriteAsync(line, 0, line.Length); + } + + foreach (var cookie in Cookies) + { + var sb = new StringBuilder(); + sb.Append("Set-Cookie: "); + sb.Append(cookie.Name); sb.Append("="); - + if (!string.IsNullOrWhiteSpace(cookie.Value)) - { - // URL encoding not required, but common practice - sb.Append(Uri.EscapeDataString(cookie.Value)); - } - - foreach (var setting in cookie.Settings) - { - sb.Append("; "); - sb.Append(setting.Key); - if (!string.IsNullOrWhiteSpace(setting.Value)) - { - sb.Append("="); - sb.Append(setting.Value); - } - } - - sb.Append(CRLF); - line = Encoding.ASCII.GetBytes(sb.ToString()); - - await m_stream.WriteAsync(line, 0, line.Length); - } - - if (Cookies is List) - Cookies = ((List)Cookies).AsReadOnly(); - - line = Encoding.ASCII.GetBytes(CRLF); - await m_stream.WriteAsync(line, 0, line.Length); - - m_hasSentHeaders = true; - } - } - - /// - /// Flushes all headers and sets the length to the amount of data currently buffered in the output - /// - /// The cancellation token to use - /// An awaitable task - internal async Task FlushAndSetLengthAsync(CancellationToken token) - { - // Make sure any buffered data is flushed - if (m_wrappedoutstream != m_outstream) - await m_wrappedoutstream.FlushAsync(token); - - await m_outstream.SetLengthAndFlushAsync(true, token); - } - - /// - /// Flushes the underlying stream - /// - /// The cancellation token to use - /// An awaitable task - internal Task FlushStreamAsync(CancellationToken token) - => m_outstream.FlushAsync(token); - - /// - /// Flush the contents after an error occurred. - /// - /// An awaitable task - internal async Task FlushAsErrorAsync() - { - if (!m_hasSentHeaders) - await FlushHeadersAsync(); - m_outstream.Clear(); - } - - /// - /// Copies the stream to the output. Note that the stream is copied from the current position to the end, and the stream must report the length. - /// - /// The awaitable task - /// The stream to copy. - /// An optional content type to set. Throws an exception if the headers are already sent. - public Task WriteAllAsync(Stream data, string contenttype = null) - { - if (contenttype != null) - ContentType = contenttype; - if (!HasSentHeaders) - ContentLength = data.Length - data.Position; - return data.CopyToAsync(m_wrappedoutstream); - } - - /// - /// Writes the byte array to the output. - /// - /// The awaitable task - /// The data to write. - /// An optional content type to set. Throws an exception if the headers are already sent. - public Task WriteAllAsync(byte[] data, string contenttype = null) - { - if (contenttype != null) - ContentType = contenttype; - if (!HasSentHeaders) - ContentLength = data.Length; - return m_wrappedoutstream.WriteAsync(data, 0, data.Length); - } - - /// - /// Writes the string to the output using UTF-8 encoding. - /// - /// The awaitable task - /// The data to write. - /// The encoding to apply. - /// An optional content type to set. Throws an exception if the headers are already sent. - public Task WriteAllAsync(string data, string contenttype = null) - { - return WriteAllAsync(System.Text.Encoding.UTF8.GetBytes(data), contenttype); - } - - /// - /// Writes the string to the output. - /// - /// The awaitable task - /// The data to write. - /// The encoding to apply. - /// An optional content type to set. Throws an exception if the headers are already sent. - public Task WriteAllAsync(string data, Encoding encoding, string contenttype = null) - { - return WriteAllAsync(encoding.GetBytes(data), contenttype); - } - - /// - /// Writes the json string to the output with UTF-8 encoding. - /// - /// The awaitable task - /// The JSON data to write. - public Task WriteAllJsonAsync(string data) - { - if (!HasSentHeaders) - ContentType = "application/json; charset=utf-8"; - return WriteAllAsync(System.Text.Encoding.UTF8.GetBytes(data)); - } - - /// - /// Performs a 302 redirect - /// - /// The target url. - public void Redirect(string newurl) - { - Headers["Location"] = newurl; - StatusCode = HttpStatusCode.Found; - StatusMessage = HttpStatusMessages.DefaultMessage(StatusCode); - } - - /// - /// Sets headers that instruct the client and proxies to avoid caching the response - /// - public void SetNonCacheable() - { - Headers["Date"] = Headers["Expires"] = DateTime.Now.ToString("R", CultureInfo.InvariantCulture); + { + // URL encoding not required, but common practice + sb.Append(Uri.EscapeDataString(cookie.Value)); + } + + foreach (var setting in cookie.Settings) + { + sb.Append("; "); + sb.Append(setting.Key); + if (!string.IsNullOrWhiteSpace(setting.Value)) + { + sb.Append("="); + sb.Append(setting.Value); + } + } + + sb.Append(CRLF); + line = Encoding.ASCII.GetBytes(sb.ToString()); + + await m_stream.WriteAsync(line, 0, line.Length); + } + + if (Cookies is List) + Cookies = ((List)Cookies).AsReadOnly(); + + line = Encoding.ASCII.GetBytes(CRLF); + await m_stream.WriteAsync(line, 0, line.Length); + + m_hasSentHeaders = true; + } + } + + /// + /// Flushes all headers and sets the length to the amount of data currently buffered in the output + /// + /// The cancellation token to use + /// An awaitable task + internal async Task FlushAndSetLengthAsync(CancellationToken token) + { + // Make sure any buffered data is flushed + if (m_wrappedoutstream != m_outstream) + await m_wrappedoutstream.FlushAsync(token); + + await m_outstream.SetLengthAndFlushAsync(true, token); + } + + /// + /// Flushes the underlying stream + /// + /// The cancellation token to use + /// An awaitable task + internal Task FlushStreamAsync(CancellationToken token) + => m_outstream.FlushAsync(token); + + /// + /// Flush the contents after an error occurred. + /// + /// An awaitable task + internal async Task FlushAsErrorAsync() + { + if (!m_hasSentHeaders) + await FlushHeadersAsync(); + m_outstream.Clear(); + } + + /// + /// Copies the stream to the output. Note that the stream is copied from the current position to the end, and the stream must report the length. + /// + /// The awaitable task + /// The stream to copy. + /// An optional content type to set. Throws an exception if the headers are already sent. + public Task WriteAllAsync(Stream data, string contenttype = null) + { + if (contenttype != null) + ContentType = contenttype; + if (!HasSentHeaders) + ContentLength = data.Length - data.Position; + return data.CopyToAsync(m_wrappedoutstream); + } + + /// + /// Writes the byte array to the output. + /// + /// The awaitable task + /// The data to write. + /// An optional content type to set. Throws an exception if the headers are already sent. + public Task WriteAllAsync(byte[] data, string contenttype = null) + { + if (contenttype != null) + ContentType = contenttype; + if (!HasSentHeaders) + ContentLength = data.Length; + return m_wrappedoutstream.WriteAsync(data, 0, data.Length); + } + + /// + /// Writes the string to the output using UTF-8 encoding. + /// + /// The awaitable task + /// The data to write. + /// The encoding to apply. + /// An optional content type to set. Throws an exception if the headers are already sent. + public Task WriteAllAsync(string data, string contenttype = null) + { + return WriteAllAsync(System.Text.Encoding.UTF8.GetBytes(data), contenttype); + } + + /// + /// Writes the string to the output. + /// + /// The awaitable task + /// The data to write. + /// The encoding to apply. + /// An optional content type to set. Throws an exception if the headers are already sent. + public Task WriteAllAsync(string data, Encoding encoding, string contenttype = null) + { + return WriteAllAsync(encoding.GetBytes(data), contenttype); + } + + /// + /// Writes the json string to the output with UTF-8 encoding. + /// + /// The awaitable task + /// The JSON data to write. + public Task WriteAllJsonAsync(string data) + { + if (!HasSentHeaders) + ContentType = "application/json; charset=utf-8"; + return WriteAllAsync(System.Text.Encoding.UTF8.GetBytes(data)); + } + + /// + /// Performs a 302 redirect + /// + /// The target url. + public void Redirect(string newurl) + { + Headers["Location"] = newurl; + StatusCode = HttpStatusCode.Found; + StatusMessage = HttpStatusMessages.DefaultMessage(StatusCode); + } + + /// + /// Sets headers that instruct the client and proxies to avoid caching the response + /// + public void SetNonCacheable() + { + Headers["Date"] = Headers["Expires"] = DateTime.Now.ToString("R", CultureInfo.InvariantCulture); Headers["Cache-Control"] = "no-cache, no-store, must-revalidate, max-age=0"; - } + } /// /// Sets headers that instruct the client and proxies to allow caching for a limited time @@ -553,76 +553,76 @@ public void SetExpires(DateTime until, bool isPublic = true) SetExpires(until - DateTime.Now, isPublic); } - /// - /// Gets the response stream. - /// To avoid buffering the contents, make sure the - /// Content-Length header is set before writing to the stream - /// - /// The response stream. - public Stream GetResponseStream() - { - return m_wrappedoutstream; - } - - /// - /// Changes the output stream to a wrapped stream - /// - /// The stream that wraps the current output - public void SetOutputWrapperStream(Stream stream) - { + /// + /// Gets the response stream. + /// To avoid buffering the contents, make sure the + /// Content-Length header is set before writing to the stream + /// + /// The response stream. + public Stream GetResponseStream() + { + return m_wrappedoutstream; + } + + /// + /// Changes the output stream to a wrapped stream + /// + /// The stream that wraps the current output + public void SetOutputWrapperStream(Stream stream) + { if (stream == null) throw new ArgumentNullException(nameof(stream)); - - if (m_hasSentHeaders) - throw new InvalidOperationException("Cannot wrap the output stream after the headers have been sent"); - - if (m_wrappedoutstream != m_outstream) - throw new InvalidOperationException("Cannot re-wrap a wrapped output stream"); - - // Copy any currently buffered content into the new wrapper - m_outstream.Unbuffer(stream); - m_wrappedoutstream = stream; - - } - - /// - /// Adds a cookie to the output - /// - /// The new cookie. - /// The name of the cookie. - /// The cookie value. - /// The optional path limiter. - /// The optional domain limiter. - /// The optional expiration date. - /// The optional maximum age. - /// A flag for making the cookie available over SSL only. - /// A flag indicating if the cookie should be hidden from the scripting environment. - /// The samesite attribute for the cookie - public IResponseCookie AddCookie(string name, string value, string path = null, string domain = null, DateTime? expires = null, long maxage = -1, bool secure = false, bool httponly = false, string samesite = null) - { - var cookie = new ResponseCookie(name, value) - { - Path = path, - Domain = domain, - Expires = expires, - MaxAge = maxage, - Secure = secure, - HttpOnly = httponly, - SameSite = samesite - }; - this.Cookies.Add(cookie); - - return cookie; - } - - /// - /// Gets a value indicating whether this is redirecting internally. - /// - public bool IsRedirectingInternally { get { return !string.IsNullOrWhiteSpace(m_internalredirectpath); } } - - /// - /// The context this response belongs to - /// + + if (m_hasSentHeaders) + throw new InvalidOperationException("Cannot wrap the output stream after the headers have been sent"); + + if (m_wrappedoutstream != m_outstream) + throw new InvalidOperationException("Cannot re-wrap a wrapped output stream"); + + // Copy any currently buffered content into the new wrapper + m_outstream.Unbuffer(stream); + m_wrappedoutstream = stream; + + } + + /// + /// Adds a cookie to the output + /// + /// The new cookie. + /// The name of the cookie. + /// The cookie value. + /// The optional path limiter. + /// The optional domain limiter. + /// The optional expiration date. + /// The optional maximum age. + /// A flag for making the cookie available over SSL only. + /// A flag indicating if the cookie should be hidden from the scripting environment. + /// The samesite attribute for the cookie + public IResponseCookie AddCookie(string name, string value, string path = null, string domain = null, DateTime? expires = null, long maxage = -1, bool secure = false, bool httponly = false, string samesite = null) + { + var cookie = new ResponseCookie(name, value) + { + Path = path, + Domain = domain, + Expires = expires, + MaxAge = maxage, + Secure = secure, + HttpOnly = httponly, + SameSite = samesite + }; + this.Cookies.Add(cookie); + + return cookie; + } + + /// + /// Gets a value indicating whether this is redirecting internally. + /// + public bool IsRedirectingInternally { get { return !string.IsNullOrWhiteSpace(m_internalredirectpath); } } + + /// + /// The context this response belongs to + /// internal HttpContext Context { get; set; } /// @@ -630,30 +630,30 @@ public IResponseCookie AddCookie(string name, string value, string path = null, /// /// The new path to use. public void InternalRedirect(string path) - { - if (HasSentHeaders) - throw new Exception("Cannot redirect after headers have been sent"); - if (IsRedirectingInternally) - throw new Exception("An internal redirect is already in progress"); - if (string.IsNullOrWhiteSpace(path) || !path.StartsWith("/", StringComparison.Ordinal)) - throw new ArgumentException("The path must start with a forward slash '/'", nameof(path)); - if (m_internalredirects >= m_serverconfig.MaxInternalRedirects) - throw new Exception($"Cannot perform more than {m_serverconfig.MaxInternalRedirects} redirects"); - - m_internalredirects++; - m_internalredirectpath = path; - } - - /// - /// Clears the internal redirect status. - /// - /// The redirected path - public string ClearInternalRedirect() - { - var prev = m_internalredirectpath; - m_internalredirectpath = null; - return prev; - } - } + { + if (HasSentHeaders) + throw new Exception("Cannot redirect after headers have been sent"); + if (IsRedirectingInternally) + throw new Exception("An internal redirect is already in progress"); + if (string.IsNullOrWhiteSpace(path) || !path.StartsWith("/", StringComparison.Ordinal)) + throw new ArgumentException("The path must start with a forward slash '/'", nameof(path)); + if (m_internalredirects >= m_serverconfig.MaxInternalRedirects) + throw new Exception($"Cannot perform more than {m_serverconfig.MaxInternalRedirects} redirects"); + + m_internalredirects++; + m_internalredirectpath = path; + } + + /// + /// Clears the internal redirect status. + /// + /// The redirected path + public string ClearInternalRedirect() + { + var prev = m_internalredirectpath; + m_internalredirectpath = null; + return prev; + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/HttpServer.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/HttpServer.cs index 5acbea251..1dcdc1d4f 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/HttpServer.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/HttpServer.cs @@ -16,7 +16,7 @@ namespace Ceen.Httpd /// The Http server implementation /// internal static class HttpServer - { + { /// /// Handler class that encapsulates a configured server, /// such that it is callable by an interprocess setup @@ -122,102 +122,102 @@ public void Stop() } - /// - /// Handler class that encapsulates a configured server setup, - /// in a way that is callable from another AppDomain - /// - public class AppDomainBridge : MarshalByRefObject - { - /// - /// The controller instance - /// - private RunnerControl Controller; - /// - /// The stop token source - /// - private CancellationTokenSource StopToken; - - /// - /// Initializes a new instance of the class. - /// - public AppDomainBridge() { } - - /// - /// Initializes a new instance of the class. - /// - /// If set to true use ssl. - /// The server config. - public AppDomainBridge(bool usessl, ServerConfig config) { Setup(usessl, config); } - - /// - /// Setup this instance - /// - /// If set to true usessl. - /// Config. - public void Setup(bool usessl, ServerConfig config) - { - if (StopToken != null) - throw new Exception("Cannot call setup more than once"); - if (config == null) - throw new ArgumentNullException(nameof(config)); - - StopToken = new CancellationTokenSource(); - Controller = new RunnerControl(StopToken.Token, usessl, config); - } - - /// - /// Handles a request - /// - /// The socket handle. - /// The remote endpoint. - /// The task ID to use. - public void HandleRequest(SocketInformation socket, EndPoint remoteEndPoint, string logtaskid) - { - RunClient(socket, remoteEndPoint, logtaskid, Controller); - } - - /// - /// Requests that this instance stops serving requests - /// - public void Stop() - { - StopToken.Cancel(); - } - - /// - /// Waits for all clients to finish processing - /// - /// true, if for stop succeeded, false otherwise. - /// The maximum time to wait for the clients to stop. - public bool WaitForStop(TimeSpan waitdelay) - { - return Controller.FinishedTask.Wait(waitdelay); - } - - /// - /// Gets the number of active clients. - /// - public int ActiveClients { get { return Controller.ActiveClients; } } - - /// - /// Initializes the lifetime service. - /// - /// The lifetime service. - public override object InitializeLifetimeService() - { - return null; - } - } - - /// - /// Helper class to keep track of all active requests and potentially abort them - /// - private class RunnerControl - { - /// - /// Backing field for the total number of active clients - /// - private static int m_totalActiveClients; + /// + /// Handler class that encapsulates a configured server setup, + /// in a way that is callable from another AppDomain + /// + public class AppDomainBridge : MarshalByRefObject + { + /// + /// The controller instance + /// + private RunnerControl Controller; + /// + /// The stop token source + /// + private CancellationTokenSource StopToken; + + /// + /// Initializes a new instance of the class. + /// + public AppDomainBridge() { } + + /// + /// Initializes a new instance of the class. + /// + /// If set to true use ssl. + /// The server config. + public AppDomainBridge(bool usessl, ServerConfig config) { Setup(usessl, config); } + + /// + /// Setup this instance + /// + /// If set to true usessl. + /// Config. + public void Setup(bool usessl, ServerConfig config) + { + if (StopToken != null) + throw new Exception("Cannot call setup more than once"); + if (config == null) + throw new ArgumentNullException(nameof(config)); + + StopToken = new CancellationTokenSource(); + Controller = new RunnerControl(StopToken.Token, usessl, config); + } + + /// + /// Handles a request + /// + /// The socket handle. + /// The remote endpoint. + /// The task ID to use. + public void HandleRequest(SocketInformation socket, EndPoint remoteEndPoint, string logtaskid) + { + RunClient(socket, remoteEndPoint, logtaskid, Controller); + } + + /// + /// Requests that this instance stops serving requests + /// + public void Stop() + { + StopToken.Cancel(); + } + + /// + /// Waits for all clients to finish processing + /// + /// true, if for stop succeeded, false otherwise. + /// The maximum time to wait for the clients to stop. + public bool WaitForStop(TimeSpan waitdelay) + { + return Controller.FinishedTask.Wait(waitdelay); + } + + /// + /// Gets the number of active clients. + /// + public int ActiveClients { get { return Controller.ActiveClients; } } + + /// + /// Initializes the lifetime service. + /// + /// The lifetime service. + public override object InitializeLifetimeService() + { + return null; + } + } + + /// + /// Helper class to keep track of all active requests and potentially abort them + /// + private class RunnerControl + { + /// + /// Backing field for the total number of active clients + /// + private static int m_totalActiveClients; /// /// Gets the total number of active clients. /// @@ -252,18 +252,18 @@ private class RunnerControl /// The config. public ServerConfig Config { get; private set; } - /// - /// The stop token - /// - public readonly CancellationToken StopToken; - /// - /// A flag indicating if SSL is used - /// - public readonly bool m_useSSL; - /// - /// A value indicating if the server is stopped - /// - public volatile bool m_isStopped; + /// + /// The stop token + /// + public readonly CancellationToken StopToken; + /// + /// A flag indicating if SSL is used + /// + public readonly bool m_useSSL; + /// + /// A value indicating if the server is stopped + /// + public volatile bool m_isStopped; /// /// Gets a value indicating whether this is stopped. /// @@ -272,251 +272,251 @@ private class RunnerControl /// The maximum number of active handlers /// private readonly int m_maxactive; - /// - /// The lock object - /// - private readonly object m_lock = new object(); - - /// - /// The task used to signal all requests are stopped - /// - private readonly TaskCompletionSource m_finishedtask = new TaskCompletionSource(TaskCreationOptions.RunContinuationsAsynchronously); - /// - /// The task used to signal all handlers to stop - /// - private readonly TaskCompletionSource m_stoptask = new TaskCompletionSource(TaskCreationOptions.RunContinuationsAsynchronously); - /// - /// The task used to signal waiting for handlers to complete before starting new handlers - /// - private TaskCompletionSource m_throttletask = new TaskCompletionSource(TaskCreationOptions.RunContinuationsAsynchronously); - - /// - /// A logger for reporting the internal log state - /// - private readonly DebugLogDelegate m_debuglogger; - - /// - /// Initializes a new instance of the class. - /// - /// The stoptoken. - /// A flag indicating if this runner is using SSL - /// The server config. - public RunnerControl(CancellationToken stoptoken, bool usessl, ServerConfig config) - { - if (config == null) - throw new ArgumentNullException(nameof(config)); - - StopToken = stoptoken; - StopToken.Register(() => Stop("_")); - Config = config; - m_maxactive = config.MaxActiveRequests; - m_throttletask.SetResult(true); - m_debuglogger = config.DebugLogHandler; - m_useSSL = usessl; - } - - /// - /// Called by a handler to signal it is in the active state - /// - /// The task id used for logging and tracing - /// true, if active was registered, false otherwise. - public bool RegisterActive(string logtaskid) - { - if (m_debuglogger != null) m_debuglogger("RegisterActive", logtaskid, null); - - if (m_isStopped) - return false; - - var res = Interlocked.Increment(ref m_activeClients); - Interlocked.Increment(ref m_totalActiveClients); - - if (m_debuglogger != null) m_debuglogger(string.Format("RegisterActive: {0}", res), logtaskid, null); - - // If we have too many active, block the throttle task - if (res >= m_maxactive) - { - if (m_debuglogger != null) m_debuglogger("Blocking throttle", logtaskid, null); - lock (m_lock) - if (m_throttletask.Task.IsCompleted) - m_throttletask = new TaskCompletionSource(TaskCreationOptions.RunContinuationsAsynchronously); - } - - return true; - } - - /// - /// Called by a handler to signal it has completed handling a request - /// The task id used for logging and tracing - /// - public void RegisterStopped(string logtaskid) - { - var res = Interlocked.Decrement(ref m_activeClients); - Interlocked.Decrement(ref m_totalActiveClients); - - if (m_debuglogger != null) m_debuglogger(string.Format("RegisterStopped: {0}", res), logtaskid, null); - - // If the throttle task is blocked and we have few active, unblock it - if (res < m_maxactive && !m_throttletask.Task.IsCompleted) - { - if (m_debuglogger != null) m_debuglogger("Un-blocking throttle", logtaskid, null); - lock (m_lock) - if (!m_throttletask.Task.IsCompleted) - m_throttletask.SetResult(true); - } - - - if (m_isStopped && res == 0) - { - if (m_debuglogger != null) m_debuglogger("Stopped and setting finish task", logtaskid, null); - m_finishedtask.TrySetResult(true); - } - } - - /// - /// Called to stop handling requests - /// - public void Stop(string logtaskid) - { - m_stoptask.TrySetCanceled(); - m_isStopped = true; - - lock (m_lock) - { - if (m_activeClients == 0) - { - if (m_debuglogger != null) m_debuglogger("Stopping, no active workers", logtaskid, null); - m_finishedtask.TrySetResult(true); - } - else - { - if (m_debuglogger != null) m_debuglogger(string.Format("Stopping with {0} active workers", m_activeClients), logtaskid, null); - } - } - } - } - - /// - /// Gets the total number of active clients - /// - /// The total active clients. - public static int TotalActiveClientCount { get { return RunnerControl.TotalActiveClients; } } - - /// - /// The method used to set the current socket handlerID in log4net, if available. - /// This redirection method is used to avoid depending on log4net. - /// - private static readonly Func SetLoggingSocketHandlerID; - - /// - /// The method used to set the current taskID in log4net, if available. - /// This redirection method is used to avoid depending on log4net. - /// - private static readonly Func SetLoggingTaskHandlerID; - - /// - /// The method used to set the current requestID in log4net, if available. - /// This redirection method is used to avoid depending on log4net. - /// - private static readonly Func SetLoggingRequestID; - - /// - /// The method used to copy logdata to log4net properties, if available. - /// This redirection method is used to avoid depending on log4net. - /// - private static readonly Action CopyLogData; - - /// - /// The name of the log4net property that has the socket handler ID - /// - public static readonly string Log4Net_SocketHandlerID = "ceen:SocketHandlerID"; - /// - /// The name of the log4net property that has the task handler ID - /// - public static readonly string Log4Net_TaskHandlerID = "ceen:TaskHandlerID"; - /// - /// The name of the log4net property that has the request ID - /// - public static readonly string Log4Net_RequestID = "ceen:RequestID"; - - /// - /// Static initialization for the HttpServer class, - /// used to check for log4net dynamically - /// - static HttpServer() - { - Func socketId = () => Guid.NewGuid().ToString("N"); - Func taskId = () => Guid.NewGuid().ToString("N"); - Func requestId = () => Guid.NewGuid().ToString("N"); - Action copylogdata = null; - - // Slowly probe through to get the method - var t = Type.GetType("log4net.LogicalThreadContext, log4net, Culture=neutral"); - - var index_socket = new object[] { Log4Net_SocketHandlerID }; - var index_task = new object[] { Log4Net_TaskHandlerID }; - var index_request = new object[] { Log4Net_RequestID }; - - if (t != null) - { - var m = t.GetProperty("Properties"); - if (m != null) - { - var ins = m.GetValue(null, null); - if (ins != null) - { - var rm = ins.GetType().GetProperties().FirstOrDefault(x => x.GetIndexParameters().Length > 0); - if (rm != null) - { - // We have a default indexer, set up the helper methods - socketId = () => - { - var g = Guid.NewGuid().ToString("N"); - rm.SetValue(ins, g, index_socket); - return g; - }; - - taskId = () => - { - var g = Guid.NewGuid().ToString("N"); - rm.SetValue(ins, g, index_task); - return g; - }; - - requestId = () => - { - var g = Guid.NewGuid().ToString("N"); - rm.SetValue(ins, g, index_request); - return g; - }; - - copylogdata = (context) => - { - if (context != null && context.LogData != null) - foreach (var kp in context.LogData) - rm.SetValue(ins, kp.Value, new object[] { kp.Key }); - }; - } - } - } - } - - // Assign whatever value we had - SetLoggingSocketHandlerID = socketId; - SetLoggingTaskHandlerID = taskId; - SetLoggingRequestID = requestId; - CopyLogData = copylogdata; - } - - /// - /// Creates and initializes a new AppDomain bridge - /// - /// The app domain bridge. - /// If set to true use ssl. - /// The server config. - public static AppDomainBridge CreateAppDomainBridge(bool usessl, ServerConfig config) - { - return new AppDomainBridge(usessl, config); - } + /// + /// The lock object + /// + private readonly object m_lock = new object(); + + /// + /// The task used to signal all requests are stopped + /// + private readonly TaskCompletionSource m_finishedtask = new TaskCompletionSource(TaskCreationOptions.RunContinuationsAsynchronously); + /// + /// The task used to signal all handlers to stop + /// + private readonly TaskCompletionSource m_stoptask = new TaskCompletionSource(TaskCreationOptions.RunContinuationsAsynchronously); + /// + /// The task used to signal waiting for handlers to complete before starting new handlers + /// + private TaskCompletionSource m_throttletask = new TaskCompletionSource(TaskCreationOptions.RunContinuationsAsynchronously); + + /// + /// A logger for reporting the internal log state + /// + private readonly DebugLogDelegate m_debuglogger; + + /// + /// Initializes a new instance of the class. + /// + /// The stoptoken. + /// A flag indicating if this runner is using SSL + /// The server config. + public RunnerControl(CancellationToken stoptoken, bool usessl, ServerConfig config) + { + if (config == null) + throw new ArgumentNullException(nameof(config)); + + StopToken = stoptoken; + StopToken.Register(() => Stop("_")); + Config = config; + m_maxactive = config.MaxActiveRequests; + m_throttletask.SetResult(true); + m_debuglogger = config.DebugLogHandler; + m_useSSL = usessl; + } + + /// + /// Called by a handler to signal it is in the active state + /// + /// The task id used for logging and tracing + /// true, if active was registered, false otherwise. + public bool RegisterActive(string logtaskid) + { + if (m_debuglogger != null) m_debuglogger("RegisterActive", logtaskid, null); + + if (m_isStopped) + return false; + + var res = Interlocked.Increment(ref m_activeClients); + Interlocked.Increment(ref m_totalActiveClients); + + if (m_debuglogger != null) m_debuglogger(string.Format("RegisterActive: {0}", res), logtaskid, null); + + // If we have too many active, block the throttle task + if (res >= m_maxactive) + { + if (m_debuglogger != null) m_debuglogger("Blocking throttle", logtaskid, null); + lock (m_lock) + if (m_throttletask.Task.IsCompleted) + m_throttletask = new TaskCompletionSource(TaskCreationOptions.RunContinuationsAsynchronously); + } + + return true; + } + + /// + /// Called by a handler to signal it has completed handling a request + /// The task id used for logging and tracing + /// + public void RegisterStopped(string logtaskid) + { + var res = Interlocked.Decrement(ref m_activeClients); + Interlocked.Decrement(ref m_totalActiveClients); + + if (m_debuglogger != null) m_debuglogger(string.Format("RegisterStopped: {0}", res), logtaskid, null); + + // If the throttle task is blocked and we have few active, unblock it + if (res < m_maxactive && !m_throttletask.Task.IsCompleted) + { + if (m_debuglogger != null) m_debuglogger("Un-blocking throttle", logtaskid, null); + lock (m_lock) + if (!m_throttletask.Task.IsCompleted) + m_throttletask.SetResult(true); + } + + + if (m_isStopped && res == 0) + { + if (m_debuglogger != null) m_debuglogger("Stopped and setting finish task", logtaskid, null); + m_finishedtask.TrySetResult(true); + } + } + + /// + /// Called to stop handling requests + /// + public void Stop(string logtaskid) + { + m_stoptask.TrySetCanceled(); + m_isStopped = true; + + lock (m_lock) + { + if (m_activeClients == 0) + { + if (m_debuglogger != null) m_debuglogger("Stopping, no active workers", logtaskid, null); + m_finishedtask.TrySetResult(true); + } + else + { + if (m_debuglogger != null) m_debuglogger(string.Format("Stopping with {0} active workers", m_activeClients), logtaskid, null); + } + } + } + } + + /// + /// Gets the total number of active clients + /// + /// The total active clients. + public static int TotalActiveClientCount { get { return RunnerControl.TotalActiveClients; } } + + /// + /// The method used to set the current socket handlerID in log4net, if available. + /// This redirection method is used to avoid depending on log4net. + /// + private static readonly Func SetLoggingSocketHandlerID; + + /// + /// The method used to set the current taskID in log4net, if available. + /// This redirection method is used to avoid depending on log4net. + /// + private static readonly Func SetLoggingTaskHandlerID; + + /// + /// The method used to set the current requestID in log4net, if available. + /// This redirection method is used to avoid depending on log4net. + /// + private static readonly Func SetLoggingRequestID; + + /// + /// The method used to copy logdata to log4net properties, if available. + /// This redirection method is used to avoid depending on log4net. + /// + private static readonly Action CopyLogData; + + /// + /// The name of the log4net property that has the socket handler ID + /// + public static readonly string Log4Net_SocketHandlerID = "ceen:SocketHandlerID"; + /// + /// The name of the log4net property that has the task handler ID + /// + public static readonly string Log4Net_TaskHandlerID = "ceen:TaskHandlerID"; + /// + /// The name of the log4net property that has the request ID + /// + public static readonly string Log4Net_RequestID = "ceen:RequestID"; + + /// + /// Static initialization for the HttpServer class, + /// used to check for log4net dynamically + /// + static HttpServer() + { + Func socketId = () => Guid.NewGuid().ToString("N"); + Func taskId = () => Guid.NewGuid().ToString("N"); + Func requestId = () => Guid.NewGuid().ToString("N"); + Action copylogdata = null; + + // Slowly probe through to get the method + var t = Type.GetType("log4net.LogicalThreadContext, log4net, Culture=neutral"); + + var index_socket = new object[] { Log4Net_SocketHandlerID }; + var index_task = new object[] { Log4Net_TaskHandlerID }; + var index_request = new object[] { Log4Net_RequestID }; + + if (t != null) + { + var m = t.GetProperty("Properties"); + if (m != null) + { + var ins = m.GetValue(null, null); + if (ins != null) + { + var rm = ins.GetType().GetProperties().FirstOrDefault(x => x.GetIndexParameters().Length > 0); + if (rm != null) + { + // We have a default indexer, set up the helper methods + socketId = () => + { + var g = Guid.NewGuid().ToString("N"); + rm.SetValue(ins, g, index_socket); + return g; + }; + + taskId = () => + { + var g = Guid.NewGuid().ToString("N"); + rm.SetValue(ins, g, index_task); + return g; + }; + + requestId = () => + { + var g = Guid.NewGuid().ToString("N"); + rm.SetValue(ins, g, index_request); + return g; + }; + + copylogdata = (context) => + { + if (context != null && context.LogData != null) + foreach (var kp in context.LogData) + rm.SetValue(ins, kp.Value, new object[] { kp.Key }); + }; + } + } + } + } + + // Assign whatever value we had + SetLoggingSocketHandlerID = socketId; + SetLoggingTaskHandlerID = taskId; + SetLoggingRequestID = requestId; + CopyLogData = copylogdata; + } + + /// + /// Creates and initializes a new AppDomain bridge + /// + /// The app domain bridge. + /// If set to true use ssl. + /// The server config. + public static AppDomainBridge CreateAppDomainBridge(bool usessl, ServerConfig config) + { + return new AppDomainBridge(usessl, config); + } /// /// Creates and initializes a new InterProcess bridge @@ -529,24 +529,24 @@ public static InterProcessBridge CreateInterProcessBridge(bool usessl, ServerCon return new InterProcessBridge(usessl, config); } - /// - /// Listens to incoming connections and calls the spawner method for each new connection - /// - /// Awaitable task. - /// The address to listen to. - /// A flag indicating if the socket listens for SSL requests - /// The stoptoken. - /// The server configuration - /// The method handling the new connection. - public static Task ListenToSocketAsync(EndPoint addr, bool usessl, CancellationToken stoptoken, ServerConfig config, Action spawner) - { - return ListenToSocketInternalAsync( - addr, - usessl, - stoptoken, - config, + /// + /// Listens to incoming connections and calls the spawner method for each new connection + /// + /// Awaitable task. + /// The address to listen to. + /// A flag indicating if the socket listens for SSL requests + /// The stoptoken. + /// The server configuration + /// The method handling the new connection. + public static Task ListenToSocketAsync(EndPoint addr, bool usessl, CancellationToken stoptoken, ServerConfig config, Action spawner) + { + return ListenToSocketInternalAsync( + addr, + usessl, + stoptoken, + config, (client, remoteendpoint, logid, controller) => spawner(client, remoteendpoint, logid)); - } + } /// /// Listens to incoming connections and calls the spawner method for each new connection @@ -632,10 +632,10 @@ private static async Task ListenToSocketInternalAsync(FuncThe server configuration /// The method handling the new connection. private static async Task ListenToSocketInternalAsync( - EndPoint addr, - bool usessl, - CancellationToken stoptoken, - ServerConfig config, + EndPoint addr, + bool usessl, + CancellationToken stoptoken, + ServerConfig config, Action spawner) { var rc = new RunnerControl(stoptoken, usessl, config); @@ -781,7 +781,7 @@ private static async Task ListenToSocketInternalAsync( /// The time the message was logged /// An awaitable task private static Task LogProcessingMessage(RunnerControl controller, HttpContext context, Exception ex, LogLevel loglevel, string message, DateTime when) - { + { var config = controller.Config; if (config.Loggers == null) return Task.FromResult(true); @@ -792,80 +792,80 @@ private static Task LogProcessingMessage(RunnerControl controller, HttpContext c if (count == 0) return Task.FromResult(true); else if (count == 1) - { - if (!(config.Loggers[0] is IMessageLogger msl)) - return Task.FromResult(true); + { + if (!(config.Loggers[0] is IMessageLogger msl)) + return Task.FromResult(true); return msl.LogMessageAsync(context, ex, loglevel, message, when); - } + } else return Task.WhenAll(config.Loggers.OfType().Select(x => x.LogMessageAsync(context, ex, loglevel, message, when))); - } - - /// - /// Logs a message signalling that a request has completed to all configured loggers - /// - /// The awaitable task. - /// The controller to get loggers from - /// The request context. - /// Exception data, if any. - /// The request start time. - /// The request duration. - private static Task LogRequestCompletedMessageAsync(RunnerControl controller, HttpContext context, Exception ex, DateTime start, TimeSpan duration) - { - var config = controller.Config; - if (config.Loggers == null) - return Task.FromResult(true); + } + + /// + /// Logs a message signalling that a request has completed to all configured loggers + /// + /// The awaitable task. + /// The controller to get loggers from + /// The request context. + /// Exception data, if any. + /// The request start time. + /// The request duration. + private static Task LogRequestCompletedMessageAsync(RunnerControl controller, HttpContext context, Exception ex, DateTime start, TimeSpan duration) + { + var config = controller.Config; + if (config.Loggers == null) + return Task.FromResult(true); CopyLogData?.Invoke(context); var count = config.Loggers.Count; - if (count == 0) - return Task.FromResult(true); - else if (count == 1) - return config.Loggers[0].LogRequestCompletedAsync(context, ex, start, duration); - else - return Task.WhenAll(config.Loggers.Select(x => x.LogRequestCompletedAsync(context, ex, start, duration))); - } - - /// - /// Listens to a port, using the given endpoint. - /// - /// The awaitable task. - /// The address to listen to. - /// A flag indicating if this instance should use SSL - /// The server configuration - /// The stoptoken. - public static Task ListenAsync( - EndPoint addr, - bool usessl, + if (count == 0) + return Task.FromResult(true); + else if (count == 1) + return config.Loggers[0].LogRequestCompletedAsync(context, ex, start, duration); + else + return Task.WhenAll(config.Loggers.Select(x => x.LogRequestCompletedAsync(context, ex, start, duration))); + } + + /// + /// Listens to a port, using the given endpoint. + /// + /// The awaitable task. + /// The address to listen to. + /// A flag indicating if this instance should use SSL + /// The server configuration + /// The stoptoken. + public static Task ListenAsync( + EndPoint addr, + bool usessl, ServerConfig config, CancellationToken stoptoken = default(CancellationToken)) - { - if (usessl && (config.SSLCertificate as X509Certificate2 == null || !(config.SSLCertificate as X509Certificate2).HasPrivateKey)) - throw new Exception("Certificate does not have a private key and cannot be used for signing"); - - if (config.Storage == null) - config.Storage = new MemoryStorageCreator(); - - return ListenToSocketInternalAsync( - addr, - usessl, - stoptoken, - config, + { + if (usessl && (config.SSLCertificate as X509Certificate2 == null || !(config.SSLCertificate as X509Certificate2).HasPrivateKey)) + throw new Exception("Certificate does not have a private key and cannot be used for signing"); + + if (config.Storage == null) + config.Storage = new MemoryStorageCreator(); + + return ListenToSocketInternalAsync( + addr, + usessl, + stoptoken, + config, RunClient); - } - - /// - /// Runs a client, using a socket handle from DuplicateAndClose - /// - /// The socket handle. - /// The remote endpoint. - /// The log task ID. - /// The controller instance - private static void RunClient(SocketInformation socketinfo, EndPoint remoteEndPoint, string logtaskid, RunnerControl controller) - { - RunClient(new Socket(socketinfo), remoteEndPoint, logtaskid, controller); - } + } + + /// + /// Runs a client, using a socket handle from DuplicateAndClose + /// + /// The socket handle. + /// The remote endpoint. + /// The log task ID. + /// The controller instance + private static void RunClient(SocketInformation socketinfo, EndPoint remoteEndPoint, string logtaskid, RunnerControl controller) + { + RunClient(new Socket(socketinfo), remoteEndPoint, logtaskid, controller); + } /// /// Handler method for connections @@ -888,31 +888,31 @@ private static async void RunClient(Socket client, EndPoint remoteEndPoint, stri /// The task id for logging and tracing /// The runner controller. private static async Task RunClient(Stream stream, EndPoint remoteEndPoint, string logtaskid, RunnerControl controller, Func isConnected) - { - var config = controller.Config; - var storage = config.Storage; + { + var config = controller.Config; + var storage = config.Storage; using (stream) - using (var ssl = controller.m_useSSL ? new SslStream(stream, false) : null) - { + using (var ssl = controller.m_useSSL ? new SslStream(stream, false) : null) + { config.DebugLogHandler?.Invoke(string.Format("Running {0}", controller.m_useSSL ? "SSL" : "plain"), logtaskid, remoteEndPoint); // Slightly higher value here to avoid races with the other timeout mechanisms stream.ReadTimeout = stream.WriteTimeout = (controller.Config.RequestIdleTimeoutSeconds + 1) * 1000; - X509Certificate clientcert = null; + X509Certificate clientcert = null; - // For SSL only: negotiate the connection - if (ssl != null) - { + // For SSL only: negotiate the connection + if (ssl != null) + { config.DebugLogHandler?.Invoke("Authenticate SSL", logtaskid, remoteEndPoint); try - { - await ssl.AuthenticateAsServerAsync(config.SSLCertificate, config.SSLRequireClientCert, config.SSLEnabledProtocols, config.SSLCheckCertificateRevocation); - } - catch (Exception aex) - { + { + await ssl.AuthenticateAsServerAsync(config.SSLCertificate, config.SSLRequireClientCert, config.SSLEnabledProtocols, config.SSLCheckCertificateRevocation); + } + catch (Exception aex) + { config.DebugLogHandler?.Invoke("Failed setting up SSL", logtaskid, remoteEndPoint); // Log a message indicating that we failed setting up SSL @@ -920,50 +920,50 @@ private static async Task RunClient(Stream stream, EndPoint remoteEndPoint, stri await LogRequestCompletedMessageAsync(controller, new HttpContext(httpRequest, null, storage, config), aex, DateTime.Now, new TimeSpan()); return; - } + } config.DebugLogHandler?.Invoke("Run SSL", logtaskid, remoteEndPoint); clientcert = ssl.RemoteCertificate; - } + } await Runner(ssl == null ? (Stream)stream : ssl, remoteEndPoint, logtaskid, clientcert, ssl == null ? SslProtocols.None : ssl.SslProtocol, controller, isConnected); config.DebugLogHandler?.Invoke("Done running", logtaskid, remoteEndPoint); } - } - - /// - /// Dispatcher method for handling a request - /// - /// The underlying stream. - /// The remote endpoint. - /// The task id for logging and tracing the connection - /// The client certificate if any. - /// The runner controller. + } + + /// + /// Dispatcher method for handling a request + /// + /// The underlying stream. + /// The remote endpoint. + /// The task id for logging and tracing the connection + /// The client certificate if any. + /// The runner controller. /// The SSL protocol being used /// A method for checking if the socket is connected - private static async Task Runner(Stream stream, EndPoint endpoint, string logtaskid, X509Certificate clientcert, SslProtocols sslProtocol, RunnerControl controller, Func isConnected) - { - var config = controller.Config; - var storage = config.Storage; - var requests = config.KeepAliveMaxRequests; - - bool keepingalive = false; - - HttpContext context = null; - HttpRequest cur = null; - HttpResponse resp = null; - DateTime started = new DateTime(); - - using (var bs = new BufferedStreamReader(stream)) - { - try - { + private static async Task Runner(Stream stream, EndPoint endpoint, string logtaskid, X509Certificate clientcert, SslProtocols sslProtocol, RunnerControl controller, Func isConnected) + { + var config = controller.Config; + var storage = config.Storage; + var requests = config.KeepAliveMaxRequests; + + bool keepingalive = false; + + HttpContext context = null; + HttpRequest cur = null; + HttpResponse resp = null; + DateTime started = new DateTime(); + + using (var bs = new BufferedStreamReader(stream)) + { + try + { config.DebugLogHandler?.Invoke("Running task", logtaskid, endpoint); if (!controller.RegisterActive(logtaskid)) - return; + return; - do + do { cur?.Dispose(); @@ -1007,7 +1007,7 @@ private static async Task Runner(Stream stream, EndPoint endpoint, string logtas } catch (HttpException hex) { - // Since we throw, make sure we log this incomplete request + // Since we throw, make sure we log this incomplete request await LogRequestStartedAsync(config, cur); // Errors during header parsing are unlikely to @@ -1040,7 +1040,7 @@ private static async Task Runner(Stream stream, EndPoint endpoint, string logtas else resp.KeepAlive = false; - // Inform loggers of the request with all fields filled + // Inform loggers of the request with all fields filled await LogRequestStartedAsync(config, cur); config.DebugLogHandler?.Invoke("Running handler", logtaskid, cur); @@ -1089,13 +1089,13 @@ private static async Task Runner(Stream stream, EndPoint endpoint, string logtas config.DebugLogHandler?.Invoke("Flushing response", logtaskid, cur); - // We must consume the entire body, - // otherwise we do not know when the next header starts - var allBytesRead = false; + // We must consume the entire body, + // otherwise we do not know when the next header starts + var allBytesRead = false; - // Empty the body, if possible - if (resp.KeepAlive && cur.Body is LimitedBodyStream lbs) - allBytesRead = await lbs.DiscardAllAsync(cur.TimeoutCancellationToken); + // Empty the body, if possible + if (resp.KeepAlive && cur.Body is LimitedBodyStream lbs) + allBytesRead = await lbs.DiscardAllAsync(cur.TimeoutCancellationToken); // Toggle the keep-alive flag if possible if (resp.KeepAlive && !resp.HasSentHeaders && !allBytesRead) @@ -1103,9 +1103,9 @@ private static async Task Runner(Stream stream, EndPoint endpoint, string logtas // If the handler has not flushed, we do it await resp.FlushAndSetLengthAsync(cur.TimeoutCancellationToken); - await resp.FlushStreamAsync(cur.TimeoutCancellationToken); + await resp.FlushStreamAsync(cur.TimeoutCancellationToken); - // Request completed without failures + // Request completed without failures await LogRequestCompletedMessageAsync(controller, context, null, started, DateTime.Now - started); // Check if keep-alive is possible @@ -1114,43 +1114,43 @@ private static async Task Runner(Stream stream, EndPoint endpoint, string logtas } while (keepingalive); - // Prevent flushing synchronously by the Close() or Dispose() call - using(var cts = new CancellationTokenSource(1000)) - { - try { await stream.FlushAsync(cts.Token); } - catch (Exception nex) { config.DebugLogHandler?.Invoke($"Failed to flush stream: {nex}", logtaskid, cur); } - } - } - catch (Exception ex) - { - // If possible, report a 500 error to the client + // Prevent flushing synchronously by the Close() or Dispose() call + using (var cts = new CancellationTokenSource(1000)) + { + try { await stream.FlushAsync(cts.Token); } + catch (Exception nex) { config.DebugLogHandler?.Invoke($"Failed to flush stream: {nex}", logtaskid, cur); } + } + } + catch (Exception ex) + { + // If possible, report a 500 error to the client if (resp != null) - { - try - { - if (!resp.HasSentHeaders) - { - resp.KeepAlive = false; - resp.StatusCode = Ceen.HttpStatusCode.InternalServerError; - resp.StatusMessage = HttpStatusMessages.DefaultMessage(Ceen.HttpStatusCode.InternalServerError); - } - } + { + try + { + if (!resp.HasSentHeaders) + { + resp.KeepAlive = false; + resp.StatusCode = Ceen.HttpStatusCode.InternalServerError; + resp.StatusMessage = HttpStatusMessages.DefaultMessage(Ceen.HttpStatusCode.InternalServerError); + } + } catch (Exception nex) { config.DebugLogHandler?.Invoke($"Failed to send headers: {nex}", logtaskid, cur); } - try { await resp.FlushAsErrorAsync(); } + try { await resp.FlushAsErrorAsync(); } catch (Exception nex) { config.DebugLogHandler?.Invoke($"Failed to FlushAsErrors: {nex}", logtaskid, cur); } } - // Prevent flushing synchronously by the Close() or Dispose() call - using(var cts = new CancellationTokenSource(1000)) - { - if (resp != null) - try { await resp.FlushStreamAsync(cts.Token); } - catch (Exception nex) { config.DebugLogHandler?.Invoke($"Failed to flush resp: {nex}", logtaskid, cur); } - - try { await stream.FlushAsync(cts.Token); } - catch (Exception nex) { config.DebugLogHandler?.Invoke($"Failed to flush stream: {nex}", logtaskid, cur); } - } + // Prevent flushing synchronously by the Close() or Dispose() call + using (var cts = new CancellationTokenSource(1000)) + { + if (resp != null) + try { await resp.FlushStreamAsync(cts.Token); } + catch (Exception nex) { config.DebugLogHandler?.Invoke($"Failed to flush resp: {nex}", logtaskid, cur); } + + try { await stream.FlushAsync(cts.Token); } + catch (Exception nex) { config.DebugLogHandler?.Invoke($"Failed to flush stream: {nex}", logtaskid, cur); } + } try { stream.Close(); } catch (Exception nex) { config.DebugLogHandler?.Invoke($"Failed to close stream: {nex}", logtaskid, cur); } @@ -1162,13 +1162,13 @@ private static async Task Runner(Stream stream, EndPoint endpoint, string logtas config.DebugLogHandler?.Invoke("Failed handler", logtaskid, cur); } - finally - { - controller.RegisterStopped(logtaskid); + finally + { + controller.RegisterStopped(logtaskid); config.DebugLogHandler?.Invoke("Terminating handler", logtaskid, cur); } - } - } + } + } private static async Task LogRequestStartedAsync(ServerConfig config, HttpRequest cur) { diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/LimitedBodyStream.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/LimitedBodyStream.cs index 1b7403759..fb2fa0cc6 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/LimitedBodyStream.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/LimitedBodyStream.cs @@ -100,7 +100,7 @@ public override async Task ReadAsync(byte[] buffer, int offset, int count, using (var cs = new CancellationTokenSource(m_idletime)) using (cancellationToken.Register(() => cs.Cancel())) { - rtask = m_parent.ReadAsync(buffer, offset, (int) Math.Min(count, m_bytesleft), cs.Token); + rtask = m_parent.ReadAsync(buffer, offset, (int)Math.Min(count, m_bytesleft), cs.Token); rt = await Task.WhenAny(m_timeouttask, m_stoptask, rtask); } @@ -151,7 +151,7 @@ public async Task DiscardAllAsync(System.Threading.CancellationToken cance return false; var buf = new byte[1024 * 8]; - while(m_bytesleft > 0) + while (m_bytesleft > 0) await ReadAsync(buf, 0, buf.Length, cancellationToken); return true; diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Logging/CLFLogger.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Logging/CLFLogger.cs index f1db4a8cb..3be077298 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Logging/CLFLogger.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Logging/CLFLogger.cs @@ -10,185 +10,186 @@ namespace Ceen.Httpd.Logging /// Implementation of a logger for the Combined Log Format /// internal class CLFLogger : ILogger, IDisposable - { - /// - /// The stream to write to - /// - protected StreamWriter m_stream; - /// - /// The lock used to provide exclusive access to the stream - /// - protected readonly AsyncLock m_lock = new AsyncLock(); - /// - /// Trueif the stream should be closed when the logger is disposed - /// - protected readonly bool m_closeOnDispose; - /// - /// True if the logging should be in combined format, false otherwise - /// - protected readonly bool m_useCombinedFormat; - /// - /// True if the logging should contain cookies in the combined format, false otherwise - /// - protected readonly bool m_logCookies; - /// - /// The log format string - /// - protected readonly string m_logFormatString; - - /// - /// Cached instance of the timezone for use in the log output - /// - private static readonly string TIME_ZONE_SPECIFIER = new DateTime().ToString("zzz").Replace(":", ""); - - - /// - /// Initializes a new instance of the class. - /// - /// The file to write log data into. - /// True if the logging should be in combined format, false otherwise. - /// True if the logging should contain cookies in the combined format, false otherwise. - public CLFLogger(string filename, bool useCombinedFormat = true, bool logCookies = false) - : this(File.Open(filename, FileMode.Append, FileAccess.Write, FileShare.Read), useCombinedFormat, logCookies, true) - { - } - - /// - /// Initializes a new instance of the class. - /// - /// The stream to write to. - /// True if the logging should be in combined format, false otherwise. - /// True if the logging should contain cookies in the combined format, false otherwise. - /// Trueif the stream should be closed when the logger is disposed. - public CLFLogger(Stream destination, bool useCombinedFormat = true, bool logCookies = false, bool closeOnDispose = false) - { - m_stream = new StreamWriter(destination); - m_closeOnDispose = closeOnDispose; - m_useCombinedFormat = useCombinedFormat; - m_logCookies = logCookies; - - var logstr = m_useCombinedFormat ? "{0} {1} {2} {3} \"{4} {5} {6}\" {7} {8} \"{9}\" \"{10}\"" : "{0} {1} {2} {3} \"{4} {5} {6}\" {7} {8}"; - if (m_useCombinedFormat && m_logCookies) - logstr += " \"{11}\""; - - m_logFormatString = logstr; - - } - - /// - /// Gets the log line in the combined log format. - /// - /// The combined log line. - /// The http context. - /// The exception. - /// Timestamp for when the request started. - /// Duration of the request processing. - public string GetCombinedLogLine(IHttpContext context, Exception ex, DateTime started, TimeSpan duration) - { - string remoteAddr; - - if (context.Request.RemoteEndPoint is System.Net.IPEndPoint) - remoteAddr = ((System.Net.IPEndPoint)context.Request.RemoteEndPoint).Address.ToString(); - else - remoteAddr = context.Request.RemoteEndPoint.ToString(); - - string referer = null; - string cookies = null; - string useragent = null; - - if (m_useCombinedFormat) - { - referer = context.Request.Headers["Referer"]; - useragent = context.Request.Headers["User-Agent"]; - - if (string.IsNullOrWhiteSpace(referer)) - referer = "-"; - if (string.IsNullOrWhiteSpace(useragent)) - useragent = "-"; - - if (m_logCookies) - { - cookies = context.Request.Headers["Cookie"]; - if (string.IsNullOrWhiteSpace(cookies)) - cookies = "-"; - } - - } - - var statuscode = context.Response == null ? HttpStatusCode.InternalServerError : context.Response.StatusCode; - var streamlength = context.Response == null ? -1 : context.Response.GetResponseStream().Length; - - return string.Format( - m_logFormatString, - remoteAddr, - "-", - "-", - string.Format("[{0} {1}]", started.ToString("dd/MMM/yyyy:HH:mm:ss", CultureInfo.InvariantCulture), TIME_ZONE_SPECIFIER), - context.Request.Method, context.Request.Path + context.Request.RawQueryString ?? string.Empty, context.Request.HttpVersion, - (int)statuscode, - streamlength, - referer, - useragent, - cookies - ); - } - - /// - /// Dispose the specified isDisposing. - /// - /// If set to true is disposing. - protected virtual void Dispose(bool isDisposing) - { - if (m_closeOnDispose && m_stream != null) - try {m_stream.Dispose(); } - - catch { } - finally { m_stream = null; } - } - - #region IDisposable implementation - - /// - /// Releases all resource used by the object. - /// - /// Call when you are finished using the . The - /// method leaves the in an unusable state. After - /// calling , you must release all references to the so - /// the garbage collector can reclaim the memory that the was occupying. - public void Dispose() - { - Dispose(true); - } - - #endregion - - #region ILogger implementation - - /// - /// Logs the request to the stream. - /// - /// The awaitable task. - /// The http context. - /// The exception. - /// Timestamp for when the request started. - /// Duration of the request processing. - public virtual Task LogRequestCompletedAsync(IHttpContext context, Exception ex, DateTime started, TimeSpan duration) - { - return Task.Run(async () => { - if (m_stream == null) - throw new ObjectDisposedException(this.GetType().FullName); - - var logmsg = GetCombinedLogLine(context, ex, started, duration); - - using (await m_lock.LockAsync()) - { - await m_stream.WriteLineAsync(logmsg); - await m_stream.FlushAsync(); - } - }); - } - - #endregion - } + { + /// + /// The stream to write to + /// + protected StreamWriter m_stream; + /// + /// The lock used to provide exclusive access to the stream + /// + protected readonly AsyncLock m_lock = new AsyncLock(); + /// + /// Trueif the stream should be closed when the logger is disposed + /// + protected readonly bool m_closeOnDispose; + /// + /// True if the logging should be in combined format, false otherwise + /// + protected readonly bool m_useCombinedFormat; + /// + /// True if the logging should contain cookies in the combined format, false otherwise + /// + protected readonly bool m_logCookies; + /// + /// The log format string + /// + protected readonly string m_logFormatString; + + /// + /// Cached instance of the timezone for use in the log output + /// + private static readonly string TIME_ZONE_SPECIFIER = new DateTime().ToString("zzz").Replace(":", ""); + + + /// + /// Initializes a new instance of the class. + /// + /// The file to write log data into. + /// True if the logging should be in combined format, false otherwise. + /// True if the logging should contain cookies in the combined format, false otherwise. + public CLFLogger(string filename, bool useCombinedFormat = true, bool logCookies = false) + : this(File.Open(filename, FileMode.Append, FileAccess.Write, FileShare.Read), useCombinedFormat, logCookies, true) + { + } + + /// + /// Initializes a new instance of the class. + /// + /// The stream to write to. + /// True if the logging should be in combined format, false otherwise. + /// True if the logging should contain cookies in the combined format, false otherwise. + /// Trueif the stream should be closed when the logger is disposed. + public CLFLogger(Stream destination, bool useCombinedFormat = true, bool logCookies = false, bool closeOnDispose = false) + { + m_stream = new StreamWriter(destination); + m_closeOnDispose = closeOnDispose; + m_useCombinedFormat = useCombinedFormat; + m_logCookies = logCookies; + + var logstr = m_useCombinedFormat ? "{0} {1} {2} {3} \"{4} {5} {6}\" {7} {8} \"{9}\" \"{10}\"" : "{0} {1} {2} {3} \"{4} {5} {6}\" {7} {8}"; + if (m_useCombinedFormat && m_logCookies) + logstr += " \"{11}\""; + + m_logFormatString = logstr; + + } + + /// + /// Gets the log line in the combined log format. + /// + /// The combined log line. + /// The http context. + /// The exception. + /// Timestamp for when the request started. + /// Duration of the request processing. + public string GetCombinedLogLine(IHttpContext context, Exception ex, DateTime started, TimeSpan duration) + { + string remoteAddr; + + if (context.Request.RemoteEndPoint is System.Net.IPEndPoint) + remoteAddr = ((System.Net.IPEndPoint)context.Request.RemoteEndPoint).Address.ToString(); + else + remoteAddr = context.Request.RemoteEndPoint.ToString(); + + string referer = null; + string cookies = null; + string useragent = null; + + if (m_useCombinedFormat) + { + referer = context.Request.Headers["Referer"]; + useragent = context.Request.Headers["User-Agent"]; + + if (string.IsNullOrWhiteSpace(referer)) + referer = "-"; + if (string.IsNullOrWhiteSpace(useragent)) + useragent = "-"; + + if (m_logCookies) + { + cookies = context.Request.Headers["Cookie"]; + if (string.IsNullOrWhiteSpace(cookies)) + cookies = "-"; + } + + } + + var statuscode = context.Response == null ? HttpStatusCode.InternalServerError : context.Response.StatusCode; + var streamlength = context.Response == null ? -1 : context.Response.GetResponseStream().Length; + + return string.Format( + m_logFormatString, + remoteAddr, + "-", + "-", + string.Format("[{0} {1}]", started.ToString("dd/MMM/yyyy:HH:mm:ss", CultureInfo.InvariantCulture), TIME_ZONE_SPECIFIER), + context.Request.Method, context.Request.Path + context.Request.RawQueryString ?? string.Empty, context.Request.HttpVersion, + (int)statuscode, + streamlength, + referer, + useragent, + cookies + ); + } + + /// + /// Dispose the specified isDisposing. + /// + /// If set to true is disposing. + protected virtual void Dispose(bool isDisposing) + { + if (m_closeOnDispose && m_stream != null) + try { m_stream.Dispose(); } + + catch { } + finally { m_stream = null; } + } + + #region IDisposable implementation + + /// + /// Releases all resource used by the object. + /// + /// Call when you are finished using the . The + /// method leaves the in an unusable state. After + /// calling , you must release all references to the so + /// the garbage collector can reclaim the memory that the was occupying. + public void Dispose() + { + Dispose(true); + } + + #endregion + + #region ILogger implementation + + /// + /// Logs the request to the stream. + /// + /// The awaitable task. + /// The http context. + /// The exception. + /// Timestamp for when the request started. + /// Duration of the request processing. + public virtual Task LogRequestCompletedAsync(IHttpContext context, Exception ex, DateTime started, TimeSpan duration) + { + return Task.Run(async () => + { + if (m_stream == null) + throw new ObjectDisposedException(this.GetType().FullName); + + var logmsg = GetCombinedLogLine(context, ex, started, duration); + + using (await m_lock.LockAsync()) + { + await m_stream.WriteLineAsync(logmsg); + await m_stream.FlushAsync(); + } + }); + } + + #endregion + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Logging/FunctionLogger.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Logging/FunctionLogger.cs index a531b6253..ab3169c89 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Logging/FunctionLogger.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Logging/FunctionLogger.cs @@ -7,36 +7,36 @@ namespace Ceen.Httpd.Logging /// Helper class for providing a logging method by a function delegate /// internal class FunctionLogger : ILogger - { - /// - /// The logging function - /// - private readonly LogDelegate m_func; - /// - /// Initializes a new instance of the class. - /// - /// The logging function. - public FunctionLogger(LogDelegate func) - { - m_func = func; - } + { + /// + /// The logging function + /// + private readonly LogDelegate m_func; + /// + /// Initializes a new instance of the class. + /// + /// The logging function. + public FunctionLogger(LogDelegate func) + { + m_func = func; + } - #region ILogger implementation + #region ILogger implementation - /// - /// Logs the request by calling the function. - /// - /// The awaitable task. - /// The http context. - /// The exception. - /// Timestamp for when the request started. - /// Duration of the request processing. - public Task LogRequestCompletedAsync(IHttpContext context, Exception ex, DateTime started, TimeSpan duration) - { - return m_func(context, ex, started, duration); - } + /// + /// Logs the request by calling the function. + /// + /// The awaitable task. + /// The http context. + /// The exception. + /// Timestamp for when the request started. + /// Duration of the request processing. + public Task LogRequestCompletedAsync(IHttpContext context, Exception ex, DateTime started, TimeSpan duration) + { + return m_func(context, ex, started, duration); + } - #endregion - } + #endregion + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Logging/Log4netCLFLogger.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Logging/Log4netCLFLogger.cs index d97e16136..dbe24eb2b 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Logging/Log4netCLFLogger.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Logging/Log4netCLFLogger.cs @@ -12,91 +12,91 @@ namespace Ceen.Httpd.Logging /// Implementation of a logger that writes messages in the combined log format to log4net /// internal class Log4netCLFLogger : CLFLogger - { - /// - /// The log instance - /// - private readonly object m_log; - /// - /// The info method for the logger - /// - private readonly System.Reflection.MethodInfo m_info; - /// - /// The error method for the logger - /// - private readonly System.Reflection.MethodInfo m_error; + { + /// + /// The log instance + /// + private readonly object m_log; + /// + /// The info method for the logger + /// + private readonly System.Reflection.MethodInfo m_info; + /// + /// The error method for the logger + /// + private readonly System.Reflection.MethodInfo m_error; - /// - /// Initializes a new instance of the class. - /// - public Log4netCLFLogger() - : this(typeof(Log4netCLFLogger).FullName) - { - } + /// + /// Initializes a new instance of the class. + /// + public Log4netCLFLogger() + : this(typeof(Log4netCLFLogger).FullName) + { + } - /// - /// Initializes a new instance of the class. - /// - /// The typename of the type to report the logger for - public Log4netCLFLogger(string logreporttype) - : base(new MemoryStream(), true, false) - { - var targettype = - Type.GetType(logreporttype, false) - ?? - AppDomain.CurrentDomain.GetAssemblies() - .Select(x => x.GetType(logreporttype)) - .FirstOrDefault(x => x != null); - - if (targettype == null) - throw new Exception($"Failed to load target type: {logreporttype}"); + /// + /// Initializes a new instance of the class. + /// + /// The typename of the type to report the logger for + public Log4netCLFLogger(string logreporttype) + : base(new MemoryStream(), true, false) + { + var targettype = + Type.GetType(logreporttype, false) + ?? + AppDomain.CurrentDomain.GetAssemblies() + .Select(x => x.GetType(logreporttype)) + .FirstOrDefault(x => x != null); - var type = Type.GetType("log4net.ILog, log4net, Culture=neutral"); - if (type == null) - { - m_log = null; - m_info = null; - m_error = null; - } - else - { - m_info = type.GetMethod("Info", new Type[] { typeof(object) }); - m_error = type.GetMethod("Error", new Type[] { typeof(object), typeof(Exception) }); - var logman = Type.GetType("log4net.LogManager, log4net, Culture=neutral"); - if (logman == null) - m_log = null; - else - { - var logmethod = logman.GetMethod("GetLogger", new Type[] { typeof(Type) }); - if (logmethod == null) - m_log = null; - else - m_log = logmethod.Invoke(null, new object[] { targettype }); - } - } + if (targettype == null) + throw new Exception($"Failed to load target type: {logreporttype}"); - if (m_log == null || m_info == null || m_error == null) - throw new Exception("Unable to load Log4net assembly"); - } + var type = Type.GetType("log4net.ILog, log4net, Culture=neutral"); + if (type == null) + { + m_log = null; + m_info = null; + m_error = null; + } + else + { + m_info = type.GetMethod("Info", new Type[] { typeof(object) }); + m_error = type.GetMethod("Error", new Type[] { typeof(object), typeof(Exception) }); + var logman = Type.GetType("log4net.LogManager, log4net, Culture=neutral"); + if (logman == null) + m_log = null; + else + { + var logmethod = logman.GetMethod("GetLogger", new Type[] { typeof(Type) }); + if (logmethod == null) + m_log = null; + else + m_log = logmethod.Invoke(null, new object[] { targettype }); + } + } - /// - /// Logs the request to log4net. - /// - /// The awaitable task. - /// The http context. - /// The exception. - /// Timestamp for when the request started. - /// Duration of the request processing. - public override Task LogRequestCompletedAsync(IHttpContext context, Exception ex, DateTime started, TimeSpan duration) - { - return Task.Run(() => - { - var line = GetCombinedLogLine(context, ex, started, duration); - if (ex == null) - m_info.Invoke(m_log, new object[] { line }); - else - m_error.Invoke(m_log, new object[] { line, ex }); - }); - } - } + if (m_log == null || m_info == null || m_error == null) + throw new Exception("Unable to load Log4net assembly"); + } + + /// + /// Logs the request to log4net. + /// + /// The awaitable task. + /// The http context. + /// The exception. + /// Timestamp for when the request started. + /// Duration of the request processing. + public override Task LogRequestCompletedAsync(IHttpContext context, Exception ex, DateTime started, TimeSpan duration) + { + return Task.Run(() => + { + var line = GetCombinedLogLine(context, ex, started, duration); + if (ex == null) + m_info.Invoke(m_log, new object[] { line }); + else + m_error.Invoke(m_log, new object[] { line, ex }); + }); + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Logging/LogHelpers.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Logging/LogHelpers.cs index 7f6e9688f..7e078b6d0 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Logging/LogHelpers.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Logging/LogHelpers.cs @@ -7,48 +7,48 @@ namespace Ceen.Httpd.Logging /// Outputs Common Log Format to STDOUT /// internal sealed class CLFStdOut : CLFLogger - { - /// - /// Initializes a new instance of the class. - /// - public CLFStdOut() - : base(Console.OpenStandardOutput()) - { - } - } + { + /// + /// Initializes a new instance of the class. + /// + public CLFStdOut() + : base(Console.OpenStandardOutput()) + { + } + } /// /// Outputs Common Log Format to STDERR /// internal sealed class CLFStdErr : CLFLogger - { - /// - /// Initializes a new instance of the class. - /// - public CLFStdErr() - : base(Console.OpenStandardError()) - { - } - } + { + /// + /// Initializes a new instance of the class. + /// + public CLFStdErr() + : base(Console.OpenStandardError()) + { + } + } /// /// Logger that outputs exception messages to stdout /// internal sealed class StdErrErrors : IMessageLogger - { - /// - /// A static cached instance of the StdErr stream - /// - private static readonly System.IO.StreamWriter _stderr; + { + /// + /// A static cached instance of the StdErr stream + /// + private static readonly System.IO.StreamWriter _stderr; - /// - /// Static initializer - /// - static StdErrErrors() - { - _stderr = new System.IO.StreamWriter(Console.OpenStandardError(), System.Text.Encoding.UTF8, 1024, true); - _stderr.AutoFlush = true; - } + /// + /// Static initializer + /// + static StdErrErrors() + { + _stderr = new System.IO.StreamWriter(Console.OpenStandardError(), System.Text.Encoding.UTF8, 1024, true); + _stderr.AutoFlush = true; + } /// /// Logs a message @@ -63,7 +63,7 @@ public Task LogMessageAsync(IHttpContext context, Exception ex, LogLevel logleve { if (ex != null) _stderr.WriteLine(ex); - return Task.FromResult(true); + return Task.FromResult(true); } /// @@ -86,7 +86,7 @@ public Task LogRequestCompletedAsync(IHttpContext context, Exception ex, DateTim /// Logger that outputs exception messages to stdout /// internal sealed class StdOutErrors : IMessageLogger - { + { /// /// Logs a message /// diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Logging/SyslogLogger.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Logging/SyslogLogger.cs index 28cd9d2c1..d2d018051 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Logging/SyslogLogger.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Logging/SyslogLogger.cs @@ -10,103 +10,103 @@ namespace Ceen.Httpd.Logging /// Implementation of a syslogger, using SyslogNet.Client by reflection /// internal class SyslogLogger : CLFLogger - { - /// - /// The serializer instance - /// - private readonly object m_serializer; - /// - /// The sender instance - /// - private readonly object m_sender; - /// - /// The message type used to construct messages - /// - private readonly Type m_message_t; - /// - /// The send method to invoke - /// - private readonly MethodInfo m_sendMethod; - /// - /// The logging facility to use - /// - private readonly object m_facility; - /// - /// The logging severity level - /// - private readonly object m_severity; - /// - /// The name to use as the log source - /// - private readonly string m_logsource; + { + /// + /// The serializer instance + /// + private readonly object m_serializer; + /// + /// The sender instance + /// + private readonly object m_sender; + /// + /// The message type used to construct messages + /// + private readonly Type m_message_t; + /// + /// The send method to invoke + /// + private readonly MethodInfo m_sendMethod; + /// + /// The logging facility to use + /// + private readonly object m_facility; + /// + /// The logging severity level + /// + private readonly object m_severity; + /// + /// The name to use as the log source + /// + private readonly string m_logsource; - /// - /// Initializes a new instance of the class. - /// - public SyslogLogger() - : this("SystemDaemons", "Informational", "ceenhttpd") - { - } + /// + /// Initializes a new instance of the class. + /// + public SyslogLogger() + : this("SystemDaemons", "Informational", "ceenhttpd") + { + } - /// - /// Initializes a new instance of the class. - /// - /// The log facility to use. - /// The log severity to use. - /// The log source name to use. - public SyslogLogger(string facility, string severity, string logsource) - : base(new MemoryStream(), true, false) - { - // Don't use the base stream - m_stream.Dispose(); - m_stream = null; + /// + /// Initializes a new instance of the class. + /// + /// The log facility to use. + /// The log severity to use. + /// The log source name to use. + public SyslogLogger(string facility, string severity, string logsource) + : base(new MemoryStream(), true, false) + { + // Don't use the base stream + m_stream.Dispose(); + m_stream = null; - // Fire up the reflection - var serializer_t = Type.GetType("SyslogNet.Client.Serialization.SyslogLocalMessageSerializer, SyslogNet.Client"); - var sender_t = Type.GetType("SyslogNet.Client.Transport.SyslogLocalSender, SyslogNet.Client"); - m_message_t = Type.GetType("SyslogNet.Client.SyslogMessage, SyslogNet.Client"); - var iserializer_t = Type.GetType("SyslogNet.Client.Serialization.ISyslogMessageSerializer, SyslogNet.Client"); + // Fire up the reflection + var serializer_t = Type.GetType("SyslogNet.Client.Serialization.SyslogLocalMessageSerializer, SyslogNet.Client"); + var sender_t = Type.GetType("SyslogNet.Client.Transport.SyslogLocalSender, SyslogNet.Client"); + m_message_t = Type.GetType("SyslogNet.Client.SyslogMessage, SyslogNet.Client"); + var iserializer_t = Type.GetType("SyslogNet.Client.Serialization.ISyslogMessageSerializer, SyslogNet.Client"); - var facility_t = Type.GetType("SyslogNet.Client.Facility, SyslogNet.Client"); - var severity_t = Type.GetType("SyslogNet.Client.Severity, SyslogNet.Client"); + var facility_t = Type.GetType("SyslogNet.Client.Facility, SyslogNet.Client"); + var severity_t = Type.GetType("SyslogNet.Client.Severity, SyslogNet.Client"); - if (new[] { serializer_t, sender_t, m_message_t, iserializer_t, facility_t, severity_t }.Any(x => x == null)) - throw new Exception("Unable to load SyslogNet.Client assembly, please add a reference to SyslogNet.Client version 0.3.2 or newer"); + if (new[] { serializer_t, sender_t, m_message_t, iserializer_t, facility_t, severity_t }.Any(x => x == null)) + throw new Exception("Unable to load SyslogNet.Client assembly, please add a reference to SyslogNet.Client version 0.3.2 or newer"); - m_sendMethod = sender_t.GetMethod("Send", new Type[] { m_message_t, iserializer_t }); - m_serializer = Activator.CreateInstance(serializer_t); - m_sender = Activator.CreateInstance(sender_t); + m_sendMethod = sender_t.GetMethod("Send", new Type[] { m_message_t, iserializer_t }); + m_serializer = Activator.CreateInstance(serializer_t); + m_sender = Activator.CreateInstance(sender_t); - if (new object[] { m_sendMethod, m_serializer, m_sender }.Any(x => x == null)) - throw new Exception("Failed to set up syslog interface, maybe the SyslogNet.Client library has changed since 0.3.2?"); + if (new object[] { m_sendMethod, m_serializer, m_sender }.Any(x => x == null)) + throw new Exception("Failed to set up syslog interface, maybe the SyslogNet.Client library has changed since 0.3.2?"); - m_facility = Enum.Parse(facility_t, facility, true); - m_severity = Enum.Parse(severity_t, severity, true); - m_logsource = logsource; - } + m_facility = Enum.Parse(facility_t, facility, true); + m_severity = Enum.Parse(severity_t, severity, true); + m_logsource = logsource; + } - /// - /// Logs the request to syslog. - /// - /// The awaitable task. - /// The http context. - /// The exception. - /// Timestamp for when the request started. - /// Duration of the request processing. - public override Task LogRequestCompletedAsync(IHttpContext context, Exception ex, DateTime started, TimeSpan duration) - { - return Task.Run(() => - { - var msg = Activator.CreateInstance(m_message_t, new object[] - { - m_facility, - m_severity, - m_logsource, - GetCombinedLogLine(context, ex, started, duration) - }); + /// + /// Logs the request to syslog. + /// + /// The awaitable task. + /// The http context. + /// The exception. + /// Timestamp for when the request started. + /// Duration of the request processing. + public override Task LogRequestCompletedAsync(IHttpContext context, Exception ex, DateTime started, TimeSpan duration) + { + return Task.Run(() => + { + var msg = Activator.CreateInstance(m_message_t, new object[] + { + m_facility, + m_severity, + m_logsource, + GetCombinedLogLine(context, ex, started, duration) + }); - m_sendMethod.Invoke(m_sender, new object[] { msg, m_serializer }); - }); - } - } + m_sendMethod.Invoke(m_sender, new object[] { msg, m_serializer }); + }); + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/MultipartItem.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/MultipartItem.cs index 83fa17c9a..9500186b7 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/MultipartItem.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/MultipartItem.cs @@ -8,50 +8,50 @@ namespace Ceen.Httpd /// Interface for a multipart item /// internal class MultipartItem : IMultipartItem - { - /// - /// The headers associated with the item - /// - /// The headers. - public IDictionary Headers { get; private set; } + { + /// + /// The headers associated with the item + /// + /// The headers. + public IDictionary Headers { get; private set; } - /// - /// Gets or sets the form name. - /// - /// The name. - public string Name { get; set; } - /// - /// Gets or sets the filename. - /// - /// The filename. - public string Filename { get; set; } - /// - /// Gets the Content-Type header value. - /// - /// The type of the content. - public string ContentType { get { return Headers["Content-Type"]; } } - /// - /// The data for this entry - /// - /// The data. - public Stream Data { get; set; } + /// + /// Gets or sets the form name. + /// + /// The name. + public string Name { get; set; } + /// + /// Gets or sets the filename. + /// + /// The filename. + public string Filename { get; set; } + /// + /// Gets the Content-Type header value. + /// + /// The type of the content. + public string ContentType { get { return Headers["Content-Type"]; } } + /// + /// The data for this entry + /// + /// The data. + public Stream Data { get; set; } - /// - /// Initializes a new instance of the class. - /// - public MultipartItem() - { - this.Headers = new Dictionary(StringComparer.OrdinalIgnoreCase).WithDefaultValue(null); - } + /// + /// Initializes a new instance of the class. + /// + public MultipartItem() + { + this.Headers = new Dictionary(StringComparer.OrdinalIgnoreCase).WithDefaultValue(null); + } - /// - /// Initializes a new instance of the class. - /// - /// The headers present on the multipart entry. - public MultipartItem(IDictionary headers) - { - this.Headers = headers; - } - } + /// + /// Initializes a new instance of the class. + /// + /// The headers present on the multipart entry. + public MultipartItem(IDictionary headers) + { + this.Headers = headers; + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/ResponseCookie.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/ResponseCookie.cs index 2cc0323fe..50a0cea43 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/ResponseCookie.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/ResponseCookie.cs @@ -8,165 +8,165 @@ namespace Ceen.Httpd /// Representation of a response cookie /// internal class ResponseCookie : IResponseCookie - { - /// - /// List of settings attached to the cookie - /// - /// The settings. - public IDictionary Settings { get; private set; } + { + /// + /// List of settings attached to the cookie + /// + /// The settings. + public IDictionary Settings { get; private set; } - /// - /// The name of the cookie - /// - /// The name. - public string Name { get; set; } - /// - /// The value of the cookie - /// - /// The value. - public string Value { get; set; } + /// + /// The name of the cookie + /// + /// The name. + public string Name { get; set; } + /// + /// The value of the cookie + /// + /// The value. + public string Value { get; set; } - /// - /// Gets or sets the cookie path - /// - /// The path. - public string Path - { - get { return Settings["Path"]; } - set - { - if (value == null) - Settings.Remove("Path"); - else - Settings["Path"] = value; - } - } + /// + /// Gets or sets the cookie path + /// + /// The path. + public string Path + { + get { return Settings["Path"]; } + set + { + if (value == null) + Settings.Remove("Path"); + else + Settings["Path"] = value; + } + } - /// - /// Gets or sets the cookie domain - /// - /// The path. - public string Domain - { - get { return Settings["Domain"]; } - set - { - if (value == null) - Settings.Remove("Domain"); - else - Settings["Domain"] = value; - } - } + /// + /// Gets or sets the cookie domain + /// + /// The path. + public string Domain + { + get { return Settings["Domain"]; } + set + { + if (value == null) + Settings.Remove("Domain"); + else + Settings["Domain"] = value; + } + } - /// - /// Gets or sets the cookie expiration date - /// - /// The path. - public DateTime? Expires - { - get - { - if (Settings["Expires"] == null) - return null; + /// + /// Gets or sets the cookie expiration date + /// + /// The path. + public DateTime? Expires + { + get + { + if (Settings["Expires"] == null) + return null; - DateTime res; - if (DateTime.TryParseExact(Settings["Expires"], "R", CultureInfo.InvariantCulture, DateTimeStyles.None, out res)) - return res; - - return null; - } - set - { - if (value == null) - Settings.Remove("Expires"); - else - Settings["Expires"] = value.Value.ToString("R", CultureInfo.InvariantCulture); - } - } + DateTime res; + if (DateTime.TryParseExact(Settings["Expires"], "R", CultureInfo.InvariantCulture, DateTimeStyles.None, out res)) + return res; - /// - /// Gets or sets the cookie max age. - /// Zero or negative values means un-set - /// - /// The max age. - public long MaxAge - { - get - { - long res; - if (!long.TryParse(Settings["Max-Age"], out res)) - res = -1; - return res; - } - set - { - if (value <= 0) - Settings.Remove("Max-Age"); - else - Settings["Max-Age"] = value.ToString(); - } - } + return null; + } + set + { + if (value == null) + Settings.Remove("Expires"); + else + Settings["Expires"] = value.Value.ToString("R", CultureInfo.InvariantCulture); + } + } - /// - /// Gets or sets the cookie secure flag - /// - /// The path. - public bool Secure - { - get { return Settings["Secure"] != null; } - set - { - if (!value) - Settings.Remove("Secure"); - else - Settings["Secure"] = string.Empty; - } - } + /// + /// Gets or sets the cookie max age. + /// Zero or negative values means un-set + /// + /// The max age. + public long MaxAge + { + get + { + long res; + if (!long.TryParse(Settings["Max-Age"], out res)) + res = -1; + return res; + } + set + { + if (value <= 0) + Settings.Remove("Max-Age"); + else + Settings["Max-Age"] = value.ToString(); + } + } - /// - /// Gets or sets the cookie HttpOnly flag - /// - /// The path. - public bool HttpOnly - { - get { return Settings["HttpOnly"] != null; } - set - { - if (!value) - Settings.Remove("HttpOnly"); - else - Settings["HttpOnly"] = string.Empty; - } - } + /// + /// Gets or sets the cookie secure flag + /// + /// The path. + public bool Secure + { + get { return Settings["Secure"] != null; } + set + { + if (!value) + Settings.Remove("Secure"); + else + Settings["Secure"] = string.Empty; + } + } - /// - /// Gets or sets the cookie SameSite attribute. - /// Expected values are "None&Quot;, "Strict", or "Lax". - /// - /// The samesite value - public string SameSite - { - get { return Settings["SameSite"]; } - set - { - if (value == null) - Settings.Remove("SameSite"); - else - Settings["SameSite"] = value; - } - } + /// + /// Gets or sets the cookie HttpOnly flag + /// + /// The path. + public bool HttpOnly + { + get { return Settings["HttpOnly"] != null; } + set + { + if (!value) + Settings.Remove("HttpOnly"); + else + Settings["HttpOnly"] = string.Empty; + } + } - /// - /// Initializes a new instance of the class. - /// - /// The cookie name. - /// The cookie value. - public ResponseCookie(string name, string value) - { - Name = name; - Value = value; - Settings = new Dictionary(StringComparer.OrdinalIgnoreCase).WithDefaultValue(null); - } - } + /// + /// Gets or sets the cookie SameSite attribute. + /// Expected values are "None&Quot;, "Strict", or "Lax". + /// + /// The samesite value + public string SameSite + { + get { return Settings["SameSite"]; } + set + { + if (value == null) + Settings.Remove("SameSite"); + else + Settings["SameSite"] = value; + } + } + + /// + /// Initializes a new instance of the class. + /// + /// The cookie name. + /// The cookie value. + public ResponseCookie(string name, string value) + { + Name = name; + Value = value; + Settings = new Dictionary(StringComparer.OrdinalIgnoreCase).WithDefaultValue(null); + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/ResponseOutputStream.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/ResponseOutputStream.cs index 7031efee2..845a275fd 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/ResponseOutputStream.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/ResponseOutputStream.cs @@ -6,276 +6,276 @@ namespace Ceen.Httpd { - /// - /// Wrapper class for providing access to the output, - /// while allowing auto-setting and flushing of the headers - /// - internal class ResponseOutputStream : Stream - { - /// - /// The stream into which data should be written - /// - private Stream m_parent; - - /// - /// The response object that this stream is attached to - /// - private HttpResponse m_response; - - /// - /// The optionally buffered content - /// - private MemoryStream m_buffer = null; - - /// - /// A value indicating if a write should simply be sent to the underlying stream - /// - private bool m_passThrough = false; - - /// - /// The number of bytes written - /// - private long m_written = 0; - - /// - /// Flag for keeping track of the disposed state - /// - private bool m_isDisposed = false; - - /// - /// The maximum number of bytes to buffer before sending data without a Content-Length header - /// - private const int MAX_RESPONSE_BUFFER = 5 * 1024 * 1024; - - /// - /// Initializes a new instance of the class. - /// - /// The stream where data is written to. - /// The response instance that this stream is attached to. - public ResponseOutputStream(Stream parent, HttpResponse response) - { - m_parent = parent; - m_response = response; - } - - /// - /// Sets the Content-Length header and writes data to the stream. - /// - /// The awaitable task. - /// If set to true overwrite the Content-Length header. - /// The cancellation token. - internal async Task SetLengthAndFlushAsync(bool forceLength, CancellationToken cancellationToken = default(CancellationToken)) - { - if (!m_response.HasSentHeaders) - { - if (m_response.ContentLength < 0 || forceLength) - m_response.ContentLength = m_buffer == null ? 0 : m_buffer.Length; - await m_response.FlushHeadersAsync(); - } - - if (m_buffer != null) - { - m_buffer.Position = 0; - await m_buffer.CopyToAsync(m_parent, 8 * 1024, cancellationToken); - m_buffer = null; - } - } - - /// - /// Clears the internal buffer - /// - internal void Clear() - { - if (m_buffer != null) - { - m_written -= m_buffer.Length; - m_buffer = null; - } - } - - #region implemented abstract members of Stream - - /// - /// Flush the contents to the underlying stream. - /// - /// The async. - /// The cancellation token. - public override async Task FlushAsync(CancellationToken cancellationToken) - { - await SetLengthAndFlushAsync(false, cancellationToken); - await m_parent.FlushAsync(cancellationToken); - } - - /// - /// Flush this instance. - /// - public override void Flush() - { - SyncAwaiter.WaitSync(() => FlushAsync(CancellationToken.None)); - } - - /// - /// Seek the specified offset and origin. - /// - /// Offset. - /// Origin. - public override long Seek(long offset, SeekOrigin origin) - { - throw new InvalidOperationException(); - } - - /// - /// Sets the length. - /// - /// Value. - public override void SetLength(long value) - { - throw new InvalidOperationException(); - } - - /// - /// Read data from the stream into the buffer, given offset and count. - /// - /// The buffer to read into. - /// The offset into the buffer where data is written. - /// The number of bytes to read. - public override int Read(byte[] buffer, int offset, int count) - { - throw new InvalidOperationException(); - } - - /// - /// Writes data from the stream into the buffer, given offset and count. - /// - /// The awaitable task. - /// The buffer to write into. - /// The offset into the buffer where data is read from. - /// The number of bytes to write. - /// Cancellation token. - public override async Task WriteAsync(byte[] buffer, int offset, int count, CancellationToken cancellationToken) - { - if (m_isDisposed) - throw new ObjectDisposedException("ResponseOutputStream"); - - if (!m_passThrough) - { - if (m_response.HasSentHeaders || m_response.ContentLength >= 0 || m_buffer?.Length + count > MAX_RESPONSE_BUFFER) - { - m_passThrough = true; - } - else - { - if (m_buffer == null) - m_buffer = new MemoryStream(); - - await m_buffer.WriteAsync(buffer, offset, count, cancellationToken); - m_written += count; - return; - } - - // If we get here, we dump what we have - await SetLengthAndFlushAsync(false, cancellationToken); - } - - await m_parent.WriteAsync(buffer, offset, count, cancellationToken); - m_written += count; - } - - /// - /// Writes data from the stream into the buffer, given offset and count. - /// - /// The buffer to write into. - /// The offset into the buffer where data is read from. - /// The number of bytes to write. - public override void Write(byte[] buffer, int offset, int count) - { + /// + /// Wrapper class for providing access to the output, + /// while allowing auto-setting and flushing of the headers + /// + internal class ResponseOutputStream : Stream + { + /// + /// The stream into which data should be written + /// + private Stream m_parent; + + /// + /// The response object that this stream is attached to + /// + private HttpResponse m_response; + + /// + /// The optionally buffered content + /// + private MemoryStream m_buffer = null; + + /// + /// A value indicating if a write should simply be sent to the underlying stream + /// + private bool m_passThrough = false; + + /// + /// The number of bytes written + /// + private long m_written = 0; + + /// + /// Flag for keeping track of the disposed state + /// + private bool m_isDisposed = false; + + /// + /// The maximum number of bytes to buffer before sending data without a Content-Length header + /// + private const int MAX_RESPONSE_BUFFER = 5 * 1024 * 1024; + + /// + /// Initializes a new instance of the class. + /// + /// The stream where data is written to. + /// The response instance that this stream is attached to. + public ResponseOutputStream(Stream parent, HttpResponse response) + { + m_parent = parent; + m_response = response; + } + + /// + /// Sets the Content-Length header and writes data to the stream. + /// + /// The awaitable task. + /// If set to true overwrite the Content-Length header. + /// The cancellation token. + internal async Task SetLengthAndFlushAsync(bool forceLength, CancellationToken cancellationToken = default(CancellationToken)) + { + if (!m_response.HasSentHeaders) + { + if (m_response.ContentLength < 0 || forceLength) + m_response.ContentLength = m_buffer == null ? 0 : m_buffer.Length; + await m_response.FlushHeadersAsync(); + } + + if (m_buffer != null) + { + m_buffer.Position = 0; + await m_buffer.CopyToAsync(m_parent, 8 * 1024, cancellationToken); + m_buffer = null; + } + } + + /// + /// Clears the internal buffer + /// + internal void Clear() + { + if (m_buffer != null) + { + m_written -= m_buffer.Length; + m_buffer = null; + } + } + + #region implemented abstract members of Stream + + /// + /// Flush the contents to the underlying stream. + /// + /// The async. + /// The cancellation token. + public override async Task FlushAsync(CancellationToken cancellationToken) + { + await SetLengthAndFlushAsync(false, cancellationToken); + await m_parent.FlushAsync(cancellationToken); + } + + /// + /// Flush this instance. + /// + public override void Flush() + { + SyncAwaiter.WaitSync(() => FlushAsync(CancellationToken.None)); + } + + /// + /// Seek the specified offset and origin. + /// + /// Offset. + /// Origin. + public override long Seek(long offset, SeekOrigin origin) + { + throw new InvalidOperationException(); + } + + /// + /// Sets the length. + /// + /// Value. + public override void SetLength(long value) + { + throw new InvalidOperationException(); + } + + /// + /// Read data from the stream into the buffer, given offset and count. + /// + /// The buffer to read into. + /// The offset into the buffer where data is written. + /// The number of bytes to read. + public override int Read(byte[] buffer, int offset, int count) + { + throw new InvalidOperationException(); + } + + /// + /// Writes data from the stream into the buffer, given offset and count. + /// + /// The awaitable task. + /// The buffer to write into. + /// The offset into the buffer where data is read from. + /// The number of bytes to write. + /// Cancellation token. + public override async Task WriteAsync(byte[] buffer, int offset, int count, CancellationToken cancellationToken) + { + if (m_isDisposed) + throw new ObjectDisposedException("ResponseOutputStream"); + + if (!m_passThrough) + { + if (m_response.HasSentHeaders || m_response.ContentLength >= 0 || m_buffer?.Length + count > MAX_RESPONSE_BUFFER) + { + m_passThrough = true; + } + else + { + if (m_buffer == null) + m_buffer = new MemoryStream(); + + await m_buffer.WriteAsync(buffer, offset, count, cancellationToken); + m_written += count; + return; + } + + // If we get here, we dump what we have + await SetLengthAndFlushAsync(false, cancellationToken); + } + + await m_parent.WriteAsync(buffer, offset, count, cancellationToken); + m_written += count; + } + + /// + /// Writes data from the stream into the buffer, given offset and count. + /// + /// The buffer to write into. + /// The offset into the buffer where data is read from. + /// The number of bytes to write. + public override void Write(byte[] buffer, int offset, int count) + { SyncAwaiter.WaitSync(() => WriteAsync(buffer, offset, count)); - } - - /// - /// Gets a value indicating whether this instance can be read. - /// - /// true if this instance can read; otherwise, false. - public override bool CanRead => false; - - /// - /// Gets a value indicating whether this instance can seek. - /// - /// true if this instance can seek; otherwise, false. - public override bool CanSeek => false; - - /// - /// Gets a value indicating whether this instance can be written. - /// - /// true if this instance can write; otherwise, false. - public override bool CanWrite => m_parent.CanWrite; - - /// - /// Gets the length of the stream. - /// - /// The length. - public override long Length => m_written; - - /// - /// Gets or sets the position. - /// - /// The position. - public override long Position - { - get => m_written; - set => throw new NotImplementedException(); - } - - /// - /// Dispose the specified disposing. - /// - /// If set to true disposing. - protected override void Dispose(bool disposing) - { + } + + /// + /// Gets a value indicating whether this instance can be read. + /// + /// true if this instance can read; otherwise, false. + public override bool CanRead => false; + + /// + /// Gets a value indicating whether this instance can seek. + /// + /// true if this instance can seek; otherwise, false. + public override bool CanSeek => false; + + /// + /// Gets a value indicating whether this instance can be written. + /// + /// true if this instance can write; otherwise, false. + public override bool CanWrite => m_parent.CanWrite; + + /// + /// Gets the length of the stream. + /// + /// The length. + public override long Length => m_written; + + /// + /// Gets or sets the position. + /// + /// The position. + public override long Position + { + get => m_written; + set => throw new NotImplementedException(); + } + + /// + /// Dispose the specified disposing. + /// + /// If set to true disposing. + protected override void Dispose(bool disposing) + { if (disposing) - { + { Flush(); m_isDisposed = true; } - } - - /// - /// Asyncronously dispose resources held by the stream - /// - /// An awaitable task - protected virtual async ValueTask DisposeAsyncCore() - { - if (!m_isDisposed) - { - await FlushAsync(); - m_isDisposed = true; - } - } - - - /// - /// Unbuffers the contents of this stream and puts it into the target stream - /// - /// The stream to unbuffer to - public void Unbuffer(Stream target) - { - if (target == null) - throw new ArgumentNullException(nameof(target)); - - if (m_passThrough) - throw new InvalidOperationException("Cannot unbuffer when the stream is no longer buffering"); - - // Copy the current buffer reference - var buf = m_buffer; - - // Mark this instance as not buffering - Clear(); - - // Copy to the target, which may start a new buffer on this instance - if (buf != null) - buf.CopyTo(target); - } - - #endregion - } + } + + /// + /// Asyncronously dispose resources held by the stream + /// + /// An awaitable task + protected virtual async ValueTask DisposeAsyncCore() + { + if (!m_isDisposed) + { + await FlushAsync(); + m_isDisposed = true; + } + } + + + /// + /// Unbuffers the contents of this stream and puts it into the target stream + /// + /// The stream to unbuffer to + public void Unbuffer(Stream target) + { + if (target == null) + throw new ArgumentNullException(nameof(target)); + + if (m_passThrough) + throw new InvalidOperationException("Cannot unbuffer when the stream is no longer buffering"); + + // Copy the current buffer reference + var buf = m_buffer; + + // Mark this instance as not buffering + Clear(); + + // Copy to the target, which may start a new buffer on this instance + if (buf != null) + buf.CopyTo(target); + } + + #endregion + } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Router.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Router.cs index 3b7f3bc61..6070bfdce 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Router.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/Router.cs @@ -11,95 +11,96 @@ namespace Ceen.Httpd /// Implementation of a simple regexp based router /// internal class Router : IRouter - { - /// - /// Regex for mathcing wildcard/globbing characters - /// - private static readonly Regex WILDCARD_MATCHER = new Regex("\\*|\\?|[^\\*\\?]+"); - - /// - /// List of rules - /// - public IList> Rules { get; set; } - - /// - /// Creates a new router - /// - public Router() - : this(new KeyValuePair[0]) - { - } - - /// - /// Initializes a new instance of the class. - /// - /// The list of routes to use. - public Router(params KeyValuePair[] items) - : this(items.AsEnumerable()) - { - } - /// - /// Initializes a new instance of the class. - /// - /// The routing rules. - public Router(IEnumerable> rules) - { - Rules = rules.Select(x => new KeyValuePair(ToRegex(x.Key), x.Value)).ToList(); - } - - /// - /// Parses a string and determines if it is a regular expression or not - /// - /// The parsed regular expression. - /// The string to parse. - public static Regex ToRegex(string value) - { - if (string.IsNullOrWhiteSpace(value)) - return null; - - if (value.StartsWith("[", StringComparison.Ordinal) && value.EndsWith("]", StringComparison.Ordinal)) - return new Regex(value.Substring(1, value.Length - 2)); - else - return WildcardExpandToRegex(value); - } - - /// - /// Expands a wildcard expression to a regular expression - /// - /// The regular expression. - /// The wildcard expression. - public static Regex WildcardExpandToRegex(string value) - { - return new Regex(WILDCARD_MATCHER.Replace(value, (match) => { - if (match.Value == "*") - return ".*"; - else if (match.Value == "?") - return "."; - else - return Regex.Escape(match.Value); - })); - } - - - /// - /// Add the specified route and handler. - /// - /// The route to match. - /// The handler to use. - public void Add(string route, IHttpModule handler) - { - Rules.Add(new KeyValuePair(ToRegex(route), handler)); - } - - /// - /// Add the specified route and handler. - /// - /// The route to match. - /// The handler to use. - public void Add(Regex route, IHttpModule handler) - { - Rules.Add(new KeyValuePair(route, handler)); - } + { + /// + /// Regex for mathcing wildcard/globbing characters + /// + private static readonly Regex WILDCARD_MATCHER = new Regex("\\*|\\?|[^\\*\\?]+"); + + /// + /// List of rules + /// + public IList> Rules { get; set; } + + /// + /// Creates a new router + /// + public Router() + : this(new KeyValuePair[0]) + { + } + + /// + /// Initializes a new instance of the class. + /// + /// The list of routes to use. + public Router(params KeyValuePair[] items) + : this(items.AsEnumerable()) + { + } + /// + /// Initializes a new instance of the class. + /// + /// The routing rules. + public Router(IEnumerable> rules) + { + Rules = rules.Select(x => new KeyValuePair(ToRegex(x.Key), x.Value)).ToList(); + } + + /// + /// Parses a string and determines if it is a regular expression or not + /// + /// The parsed regular expression. + /// The string to parse. + public static Regex ToRegex(string value) + { + if (string.IsNullOrWhiteSpace(value)) + return null; + + if (value.StartsWith("[", StringComparison.Ordinal) && value.EndsWith("]", StringComparison.Ordinal)) + return new Regex(value.Substring(1, value.Length - 2)); + else + return WildcardExpandToRegex(value); + } + + /// + /// Expands a wildcard expression to a regular expression + /// + /// The regular expression. + /// The wildcard expression. + public static Regex WildcardExpandToRegex(string value) + { + return new Regex(WILDCARD_MATCHER.Replace(value, (match) => + { + if (match.Value == "*") + return ".*"; + else if (match.Value == "?") + return "."; + else + return Regex.Escape(match.Value); + })); + } + + + /// + /// Add the specified route and handler. + /// + /// The route to match. + /// The handler to use. + public void Add(string route, IHttpModule handler) + { + Rules.Add(new KeyValuePair(ToRegex(route), handler)); + } + + /// + /// Add the specified route and handler. + /// + /// The route to match. + /// The handler to use. + public void Add(Regex route, IHttpModule handler) + { + Rules.Add(new KeyValuePair(route, handler)); + } /// /// Process the specified request. @@ -108,26 +109,26 @@ public void Add(Regex route, IHttpModule handler) /// The token indicating to stop handling. /// True if the processing was handled, false otherwise public async Task Process(IHttpContext context, CancellationToken cancellationToken) - { - foreach (var rule in Rules) - { - if (rule.Key != null) - { - var m = rule.Key.Match(context.Request.Path); - if (!m.Success || m.Length != context.Request.Path.Length) - continue; - } - - context.Request.RequireHandler(rule.Value.GetType().GetCustomAttributes(typeof(RequireHandlerAttribute), true).OfType()); - - if (await rule.Value.HandleAsync(context, cancellationToken)) - return true; - - context.Request.PushHandlerOnStack(rule.Value); - } - - return false; - } - } + { + foreach (var rule in Rules) + { + if (rule.Key != null) + { + var m = rule.Key.Match(context.Request.Path); + if (!m.Success || m.Length != context.Request.Path.Length) + continue; + } + + context.Request.RequireHandler(rule.Value.GetType().GetCustomAttributes(typeof(RequireHandlerAttribute), true).OfType()); + + if (await rule.Value.HandleAsync(context, cancellationToken)) + return true; + + context.Request.PushHandlerOnStack(rule.Value); + } + + return false; + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/ServerConfig.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/ServerConfig.cs index 1b69ce023..591962b2a 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/ServerConfig.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/ServerConfig.cs @@ -12,96 +12,96 @@ namespace Ceen.Httpd /// Configuration of a server instance /// internal class ServerConfig : ILoadedModuleInfo - { - /// - /// The socket backlog. - /// - public int SocketBacklog { get; set; } = 5; - /// - /// The maximum size of the request line. - /// - public int MaxRequestLineSize { get; set; } = 8 * 1024; - /// - /// The maximum size of the request header. - /// - public int MaxRequestHeaderSize { get; set; } = 64 * 1024; - /// - /// The maximum number of active requests. - /// - public int MaxActiveRequests { get; set; } = 500000; - /// - /// The maximum number of internal redirects - /// - public int MaxInternalRedirects { get; set; } = 5; - - /// - /// The maximum size of a POST request with url encoded data. - /// This is also the maximum size allowed for automatically - /// decoding multipart form data. - /// - public int MaxUrlEncodedFormSize { get; set; } = 5 * 1024 * 1024; - - /// - /// Allow automatic parsing of multipart form data - /// - public bool AutoParseMultipartFormData { get; set; } = true; - - /// - /// The maximum size of a POST request - /// - public long MaxPostSize { get; set; } = 100 * 1024 * 1024; - - /// - /// A flag indicating if the X-HTTP-Method-Override header is supported - /// - public bool AllowHttpMethodOverride { get; set; } = true; - - /// - /// A flag indicating if requests with HTTP/1.0 are allowed - /// - public bool AllowLegacyHttp { get; set; } = false; - - /// - /// A value indicating the name of the header, - /// the proxy uses to communicate the source IP of the request. - /// Commonly this is set to "X-Real-IP" or "X-Forwarded-For" - /// Leave blank to disable. - /// - public string AllowedSourceIPHeaderValue { get; set; } = null; - - /// - /// The request idle timeout in seconds. - /// - public int RequestIdleTimeoutSeconds { get; set; } = 5; - /// - /// The request header read timeout in seconds. - /// - public int RequestHeaderReadTimeoutSeconds { get; set; } = 10; - /// - /// The maximum number of requests to server with a single connection. - /// - public int KeepAliveMaxRequests { get; set; } = 30; - /// - /// The keep-alive timeout in seconds - /// - public int KeepAliveTimeoutSeconds { get; set; } = 10; + { + /// + /// The socket backlog. + /// + public int SocketBacklog { get; set; } = 5; + /// + /// The maximum size of the request line. + /// + public int MaxRequestLineSize { get; set; } = 8 * 1024; + /// + /// The maximum size of the request header. + /// + public int MaxRequestHeaderSize { get; set; } = 64 * 1024; + /// + /// The maximum number of active requests. + /// + public int MaxActiveRequests { get; set; } = 500000; + /// + /// The maximum number of internal redirects + /// + public int MaxInternalRedirects { get; set; } = 5; + + /// + /// The maximum size of a POST request with url encoded data. + /// This is also the maximum size allowed for automatically + /// decoding multipart form data. + /// + public int MaxUrlEncodedFormSize { get; set; } = 5 * 1024 * 1024; + + /// + /// Allow automatic parsing of multipart form data + /// + public bool AutoParseMultipartFormData { get; set; } = true; + + /// + /// The maximum size of a POST request + /// + public long MaxPostSize { get; set; } = 100 * 1024 * 1024; + + /// + /// A flag indicating if the X-HTTP-Method-Override header is supported + /// + public bool AllowHttpMethodOverride { get; set; } = true; + + /// + /// A flag indicating if requests with HTTP/1.0 are allowed + /// + public bool AllowLegacyHttp { get; set; } = false; + + /// + /// A value indicating the name of the header, + /// the proxy uses to communicate the source IP of the request. + /// Commonly this is set to "X-Real-IP" or "X-Forwarded-For" + /// Leave blank to disable. + /// + public string AllowedSourceIPHeaderValue { get; set; } = null; + + /// + /// The request idle timeout in seconds. + /// + public int RequestIdleTimeoutSeconds { get; set; } = 5; + /// + /// The request header read timeout in seconds. + /// + public int RequestHeaderReadTimeoutSeconds { get; set; } = 10; + /// + /// The maximum number of requests to server with a single connection. + /// + public int KeepAliveMaxRequests { get; set; } = 30; + /// + /// The keep-alive timeout in seconds + /// + public int KeepAliveTimeoutSeconds { get; set; } = 10; /// /// The maximum number of seconds a process may be running /// /// The max processing time seconds. public int MaxProcessingTimeSeconds { get; set; } = 30; - /// - /// The router instance to use for handling requests - /// - public IRouter Router { get; set; } - /// - /// The logger instances to use - /// - public IList Loggers { get; set; } - /// - /// The loaded module instance - /// - public IList Modules { get; set; } + /// + /// The router instance to use for handling requests + /// + public IRouter Router { get; set; } + /// + /// The logger instances to use + /// + public IList Loggers { get; set; } + /// + /// The loaded module instance + /// + public IList Modules { get; set; } /// /// The loaded post-processor instances /// @@ -111,185 +111,185 @@ internal class ServerConfig : ILoadedModuleInfo /// public Action AddDefaultResponseHeaders { get; set; } - /// - /// Gets or sets the default name of the server reported in response headers. - /// - /// The default name of the server. - public string DefaultServerName { get; set; } - - /// - /// The server certificate if used for serving SSL requests - /// - public X509Certificate SSLCertificate { get; set; } - /// - /// True if a client SSL certificate should be requested - /// - public bool SSLRequireClientCert { get; set; } = false; - /// - /// List the allowed SSL versions - /// - public SslProtocols SSLEnabledProtocols { get; set; } = SslProtocols.Tls12; - /// - /// Value indicating if SSL certificates are checked against a revocation list - /// - public bool SSLCheckCertificateRevocation { get; set; } = true; - - /// - /// A callback handler for debugging the internal server state - /// - public DebugLogDelegate DebugLogHandler; - - /// - /// The storage creator - /// - public IStorageCreator Storage { get; set; } - - /// - /// The loader context for this instance - /// - public IDisposable LoaderContext; - - /// - /// Static initializer for the class. - /// - static ServerConfig() - { - } - - /// - /// Initializes a new instance of the class. - /// - public ServerConfig() - { - var version = typeof(ServerConfig).Assembly.GetName().Version; - DefaultServerName = string.Format("ceenhttpd/{0}.{1}", version.Major, version.Minor); - - AddDefaultResponseHeaders = DefaultHeaders; - } - - /// - /// Loads a certificate instance - /// - /// The path to the file with the certificate. - /// The certificate password. - public void LoadCertificate(string path, string password) - { - this.SSLCertificate = new X509Certificate2(path, password ?? ""); - } - - /// - /// Adds default headers to the output. - /// - /// The response to update. - public void DefaultHeaders(IHttpResponse response) - { - response.AddHeader("Date", DateTime.UtcNow.ToString("R", CultureInfo.InvariantCulture)); - - if (!string.IsNullOrWhiteSpace(DefaultServerName)) - response.AddHeader("Server", DefaultServerName); - } - - /// - /// Adds a logger instance to the server - /// - /// The server configuration. - /// The logger module to add. - public ServerConfig AddLogger(LogDelegate logger) - { - return AddLogger(new Logging.FunctionLogger(logger)); - } - - /// - /// Adds a logger instance to the server - /// - /// The server configuration. - /// The logger module to add. - public ServerConfig AddLogger(ILogger logger) - { - if (logger == null) - throw new ArgumentNullException(nameof(logger)); - if (Loggers == null) - Loggers = new List(); - - Loggers.Add(logger); - return this; - } - - /// - /// Adds a route to this configuration - /// - /// The server configuration. - /// The handler function that will execute the operation. - public ServerConfig AddRoute(HttpHandlerDelegate handler) - { - if (handler == null) - throw new ArgumentNullException(nameof(handler)); - return AddRoute(null, new Handler.FunctionHandler(handler)); - } - - /// - /// Adds a route to this configuration - /// - /// The server configuration. - /// The handler function that will execute the operation. - public ServerConfig AddRoute(IHttpModule handler) - { - if (handler == null) - throw new ArgumentNullException(nameof(handler)); - return AddRoute(null, handler); - } - - /// - /// Adds a route to this configuration - /// - /// The server configuration. - /// The expression used to pre-filter requests before invoking the handler. - /// The handler function that will execute the operation. - public ServerConfig AddRoute(string route, HttpHandlerDelegate handler) - { - if (handler == null) - throw new ArgumentNullException(nameof(handler)); - return AddRoute(route, new Handler.FunctionHandler(handler)); - } - - /// - /// Adds a route to this configuration - /// - /// The server configuration. - /// The expression used to pre-filter requests before invoking the handler. - /// The handler module that will execute the operation. - public ServerConfig AddRoute(string route, IHttpModule handler) - { - if (handler == null) - throw new ArgumentNullException(nameof(handler)); - - Router rt; - if (this.Router == null) - this.Router = rt = new Router(); - else if (this.Router is Router) - rt = this.Router as Router; - else - throw new Exception($"Cannot use the AddRoute method unless the {nameof(Router)} is an instance of {typeof(Router).FullName}"); - - rt.Add(route, handler); - return this; - } - - /// - /// Adds a module instance to the server - /// - /// The server configuration. - /// The module to add. - public ServerConfig AddModule(IModule module) - { - if (module == null) - throw new ArgumentNullException(nameof(module)); - if (Modules == null) - Modules = new List(); - - Modules.Add(module); - return this; - } + /// + /// Gets or sets the default name of the server reported in response headers. + /// + /// The default name of the server. + public string DefaultServerName { get; set; } + + /// + /// The server certificate if used for serving SSL requests + /// + public X509Certificate SSLCertificate { get; set; } + /// + /// True if a client SSL certificate should be requested + /// + public bool SSLRequireClientCert { get; set; } = false; + /// + /// List the allowed SSL versions + /// + public SslProtocols SSLEnabledProtocols { get; set; } = SslProtocols.Tls12; + /// + /// Value indicating if SSL certificates are checked against a revocation list + /// + public bool SSLCheckCertificateRevocation { get; set; } = true; + + /// + /// A callback handler for debugging the internal server state + /// + public DebugLogDelegate DebugLogHandler; + + /// + /// The storage creator + /// + public IStorageCreator Storage { get; set; } + + /// + /// The loader context for this instance + /// + public IDisposable LoaderContext; + + /// + /// Static initializer for the class. + /// + static ServerConfig() + { + } + + /// + /// Initializes a new instance of the class. + /// + public ServerConfig() + { + var version = typeof(ServerConfig).Assembly.GetName().Version; + DefaultServerName = string.Format("ceenhttpd/{0}.{1}", version.Major, version.Minor); + + AddDefaultResponseHeaders = DefaultHeaders; + } + + /// + /// Loads a certificate instance + /// + /// The path to the file with the certificate. + /// The certificate password. + public void LoadCertificate(string path, string password) + { + this.SSLCertificate = new X509Certificate2(path, password ?? ""); + } + + /// + /// Adds default headers to the output. + /// + /// The response to update. + public void DefaultHeaders(IHttpResponse response) + { + response.AddHeader("Date", DateTime.UtcNow.ToString("R", CultureInfo.InvariantCulture)); + + if (!string.IsNullOrWhiteSpace(DefaultServerName)) + response.AddHeader("Server", DefaultServerName); + } + + /// + /// Adds a logger instance to the server + /// + /// The server configuration. + /// The logger module to add. + public ServerConfig AddLogger(LogDelegate logger) + { + return AddLogger(new Logging.FunctionLogger(logger)); + } + + /// + /// Adds a logger instance to the server + /// + /// The server configuration. + /// The logger module to add. + public ServerConfig AddLogger(ILogger logger) + { + if (logger == null) + throw new ArgumentNullException(nameof(logger)); + if (Loggers == null) + Loggers = new List(); + + Loggers.Add(logger); + return this; + } + + /// + /// Adds a route to this configuration + /// + /// The server configuration. + /// The handler function that will execute the operation. + public ServerConfig AddRoute(HttpHandlerDelegate handler) + { + if (handler == null) + throw new ArgumentNullException(nameof(handler)); + return AddRoute(null, new Handler.FunctionHandler(handler)); + } + + /// + /// Adds a route to this configuration + /// + /// The server configuration. + /// The handler function that will execute the operation. + public ServerConfig AddRoute(IHttpModule handler) + { + if (handler == null) + throw new ArgumentNullException(nameof(handler)); + return AddRoute(null, handler); + } + + /// + /// Adds a route to this configuration + /// + /// The server configuration. + /// The expression used to pre-filter requests before invoking the handler. + /// The handler function that will execute the operation. + public ServerConfig AddRoute(string route, HttpHandlerDelegate handler) + { + if (handler == null) + throw new ArgumentNullException(nameof(handler)); + return AddRoute(route, new Handler.FunctionHandler(handler)); + } + + /// + /// Adds a route to this configuration + /// + /// The server configuration. + /// The expression used to pre-filter requests before invoking the handler. + /// The handler module that will execute the operation. + public ServerConfig AddRoute(string route, IHttpModule handler) + { + if (handler == null) + throw new ArgumentNullException(nameof(handler)); + + Router rt; + if (this.Router == null) + this.Router = rt = new Router(); + else if (this.Router is Router) + rt = this.Router as Router; + else + throw new Exception($"Cannot use the AddRoute method unless the {nameof(Router)} is an instance of {typeof(Router).FullName}"); + + rt.Add(route, handler); + return this; + } + + /// + /// Adds a module instance to the server + /// + /// The server configuration. + /// The module to add. + public ServerConfig AddModule(IModule module) + { + if (module == null) + throw new ArgumentNullException(nameof(module)); + if (Modules == null) + Modules = new List(); + + Modules.Add(module); + return this; + } /// /// Adds a post-processor instance to the server @@ -307,48 +307,48 @@ public ServerConfig AddPostProcessor(IPostProcessor postprocessor) return this; } - /// - /// Calls all shutdown modules - /// - /// A combined task - public async Task ShutdownAsync() - { - var res = Ceen.Context - .GetItemsOfType(this) - .Select(x => x.ShutdownAsync()) - .ToArray(); + /// + /// Calls all shutdown modules + /// + /// A combined task + public async Task ShutdownAsync() + { + var res = Ceen.Context + .GetItemsOfType(this) + .Select(x => x.ShutdownAsync()) + .ToArray(); + + if (res.Length != 0) + await Task.WhenAll(res); - if (res.Length != 0) - await Task.WhenAll(res); - - if (LoaderContext != null) - LoaderContext.Dispose(); - } + if (LoaderContext != null) + LoaderContext.Dispose(); + } /// /// The handlers loaded by the router /// - IEnumerable> ILoadedModuleInfo.Handlers - => (Router as Router)?.Rules.Select(x => new KeyValuePair(x.Key?.ToString(), x.Value)); + IEnumerable> ILoadedModuleInfo.Handlers + => (Router as Router)?.Rules.Select(x => new KeyValuePair(x.Key?.ToString(), x.Value)); /// /// The logger instances /// - IEnumerable ILoadedModuleInfo.Loggers - => Loggers; + IEnumerable ILoadedModuleInfo.Loggers + => Loggers; /// /// The loaded modules /// - IEnumerable ILoadedModuleInfo.Modules - => Modules; + IEnumerable ILoadedModuleInfo.Modules + => Modules; /// /// The loaded post-processors /// - IEnumerable ILoadedModuleInfo.PostProcessors - => PostProcessors; + IEnumerable ILoadedModuleInfo.PostProcessors + => PostProcessors; } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/StorageImplementation.cs b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/StorageImplementation.cs index 893501028..1816d4d53 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Httpd/StorageImplementation.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Httpd/StorageImplementation.cs @@ -7,279 +7,279 @@ namespace Ceen.Httpd { - /// - /// AppDomain wrapper for accessing an IStorageEntry in another domain - /// - internal class StorageEntryWrapper : IStorageEntry - { - /// - /// The remote instance of the StorageCreator - /// - private readonly object m_wrapped; - - /// - /// The instance as a dictionary - /// - private readonly IDictionary m_dict; - - /// - /// The Expires property - /// - private readonly System.Reflection.PropertyInfo m_expires; - - /// - /// The Name property - /// - private readonly System.Reflection.PropertyInfo m_name; - - /// - /// The indexer property - /// - private readonly System.Reflection.PropertyInfo m_index; - - /// - /// Initializes a new instance of the class. - /// - /// The owner to wrap. - public StorageEntryWrapper(object owner) - { - m_wrapped = owner; - m_dict = (IDictionary)owner; - m_expires = m_wrapped.GetType().GetProperty(nameof(Expires)); - m_name = m_wrapped.GetType().GetProperty(nameof(Name)); - - var iface = m_wrapped.GetType().GetInterfaces().FirstOrDefault(x => x.FullName == typeof(IStorageEntry).FullName); - if (iface == null) - throw new Exception($"The given type ${m_wrapped.GetType()} does not implement {typeof(IStorageEntry)}"); - - m_index = typeof(IDictionary).GetProperties().FirstOrDefault(x => x.GetIndexParameters().Length == 1); - - if (new[] { m_wrapped, m_expires, m_name, m_index }.Any(x => x == null)) - throw new Exception($"Something changed in {typeof(IStorageEntry)}"); - } - - /// - /// Gets the element with the specified key, or null. - /// Set to null to delete the item. - /// - /// The item key. - public string this[string key] - { - get - { - return (string)m_index.GetValue(m_wrapped, new object[] { key }); - } - - set - { - m_index.SetValue(m_wrapped, value, new object[] { key }); - } - } - - /// - /// Gets or sets the time the dictionary expires - /// - public DateTime Expires - { - get - { - return (DateTime)m_expires.GetValue(m_wrapped, null); - } - set - { - m_expires.SetValue(m_wrapped, value, null); - } - } - - /// - /// Gets the name of the storage element - /// - public string Name - { - get - { - return (string)m_name.GetValue(m_wrapped, null); - } - } - - /// - ///Gets the number of elements in the collection - /// - public int Count { get { return m_dict.Count; } } - - /// - /// Gets a value indicating whether this instance is read only. - /// - public bool IsReadOnly { get { return m_dict.IsReadOnly; } } - - /// - /// Gets the keys for this collection - /// - public ICollection Keys { get { return m_dict.Keys; } } - - /// - /// Gets the values for this collection - /// - public ICollection Values { get { return m_dict.Values; } } - - /// - /// Adds an item to the collection - /// - /// The item to add. - public void Add(KeyValuePair item) - { - m_dict.Add(item); - } - - /// - /// Adds an item to the collection - /// - /// The key to use. - /// The value to use. - public void Add(string key, string value) - { - m_dict.Add(key, value); - } - - /// - /// Removes all elements from this collection - /// - public void Clear() - { - m_dict.Clear(); - } - - /// - /// Returns a value indicating if the given item was found in the collection - /// - /// The item to look for. - public bool Contains(KeyValuePair item) - { - return m_dict.Contains(item); - } - - /// - /// Returns a value indicating if the given item was found in the collection - /// - /// true, if key was found, false otherwise. - /// The key to look for. - public bool ContainsKey(string key) - { - return m_dict.ContainsKey(key); - } - - /// - /// Copies the elements to an array - /// - /// The target array. - /// The target array index. - public void CopyTo(KeyValuePair[] array, int arrayIndex) - { - m_dict.CopyTo(array, arrayIndex); - } - - /// - /// Gets the enumerator. - /// - /// The enumerator. - public IEnumerator> GetEnumerator() - { - return m_dict.GetEnumerator(); - } - - /// - /// Remove the specified item. - /// - /// The item to remove. - public bool Remove(KeyValuePair item) - { - return m_dict.Remove(item); - } - - /// - /// Remove the item with the specified key. - /// - /// The key to look for. - public bool Remove(string key) - { - return m_dict.Remove(key); - } - - /// - /// Tries the get value for the given key. - /// - /// true, if get value was found, false otherwise. - /// The key to look for. - /// The resulting value. - public bool TryGetValue(string key, out string value) - { - return m_dict.TryGetValue(key, out value); - } - - /// - /// Gets the enumerator. - /// - /// The enumerator. - IEnumerator IEnumerable.GetEnumerator() - { - return m_dict.GetEnumerator(); - } - } + /// + /// AppDomain wrapper for accessing an IStorageEntry in another domain + /// + internal class StorageEntryWrapper : IStorageEntry + { + /// + /// The remote instance of the StorageCreator + /// + private readonly object m_wrapped; + + /// + /// The instance as a dictionary + /// + private readonly IDictionary m_dict; + + /// + /// The Expires property + /// + private readonly System.Reflection.PropertyInfo m_expires; + + /// + /// The Name property + /// + private readonly System.Reflection.PropertyInfo m_name; + + /// + /// The indexer property + /// + private readonly System.Reflection.PropertyInfo m_index; + + /// + /// Initializes a new instance of the class. + /// + /// The owner to wrap. + public StorageEntryWrapper(object owner) + { + m_wrapped = owner; + m_dict = (IDictionary)owner; + m_expires = m_wrapped.GetType().GetProperty(nameof(Expires)); + m_name = m_wrapped.GetType().GetProperty(nameof(Name)); + + var iface = m_wrapped.GetType().GetInterfaces().FirstOrDefault(x => x.FullName == typeof(IStorageEntry).FullName); + if (iface == null) + throw new Exception($"The given type ${m_wrapped.GetType()} does not implement {typeof(IStorageEntry)}"); + + m_index = typeof(IDictionary).GetProperties().FirstOrDefault(x => x.GetIndexParameters().Length == 1); + + if (new[] { m_wrapped, m_expires, m_name, m_index }.Any(x => x == null)) + throw new Exception($"Something changed in {typeof(IStorageEntry)}"); + } + + /// + /// Gets the element with the specified key, or null. + /// Set to null to delete the item. + /// + /// The item key. + public string this[string key] + { + get + { + return (string)m_index.GetValue(m_wrapped, new object[] { key }); + } + + set + { + m_index.SetValue(m_wrapped, value, new object[] { key }); + } + } + + /// + /// Gets or sets the time the dictionary expires + /// + public DateTime Expires + { + get + { + return (DateTime)m_expires.GetValue(m_wrapped, null); + } + set + { + m_expires.SetValue(m_wrapped, value, null); + } + } + + /// + /// Gets the name of the storage element + /// + public string Name + { + get + { + return (string)m_name.GetValue(m_wrapped, null); + } + } + + /// + ///Gets the number of elements in the collection + /// + public int Count { get { return m_dict.Count; } } + + /// + /// Gets a value indicating whether this instance is read only. + /// + public bool IsReadOnly { get { return m_dict.IsReadOnly; } } + + /// + /// Gets the keys for this collection + /// + public ICollection Keys { get { return m_dict.Keys; } } + + /// + /// Gets the values for this collection + /// + public ICollection Values { get { return m_dict.Values; } } + + /// + /// Adds an item to the collection + /// + /// The item to add. + public void Add(KeyValuePair item) + { + m_dict.Add(item); + } + + /// + /// Adds an item to the collection + /// + /// The key to use. + /// The value to use. + public void Add(string key, string value) + { + m_dict.Add(key, value); + } + + /// + /// Removes all elements from this collection + /// + public void Clear() + { + m_dict.Clear(); + } + + /// + /// Returns a value indicating if the given item was found in the collection + /// + /// The item to look for. + public bool Contains(KeyValuePair item) + { + return m_dict.Contains(item); + } + + /// + /// Returns a value indicating if the given item was found in the collection + /// + /// true, if key was found, false otherwise. + /// The key to look for. + public bool ContainsKey(string key) + { + return m_dict.ContainsKey(key); + } + + /// + /// Copies the elements to an array + /// + /// The target array. + /// The target array index. + public void CopyTo(KeyValuePair[] array, int arrayIndex) + { + m_dict.CopyTo(array, arrayIndex); + } + + /// + /// Gets the enumerator. + /// + /// The enumerator. + public IEnumerator> GetEnumerator() + { + return m_dict.GetEnumerator(); + } + + /// + /// Remove the specified item. + /// + /// The item to remove. + public bool Remove(KeyValuePair item) + { + return m_dict.Remove(item); + } + + /// + /// Remove the item with the specified key. + /// + /// The key to look for. + public bool Remove(string key) + { + return m_dict.Remove(key); + } + + /// + /// Tries the get value for the given key. + /// + /// true, if get value was found, false otherwise. + /// The key to look for. + /// The resulting value. + public bool TryGetValue(string key, out string value) + { + return m_dict.TryGetValue(key, out value); + } + + /// + /// Gets the enumerator. + /// + /// The enumerator. + IEnumerator IEnumerable.GetEnumerator() + { + return m_dict.GetEnumerator(); + } + } /// /// Wrapper helper to invoke methods across the AppDomain boundary /// internal class StorageCreatorAccessor : IStorageCreator - { - /// - /// The remote instance of the StorageCreator - /// - private readonly object m_wrapped; - /// - /// The GetStorageAsync method - /// - private readonly System.Reflection.MethodInfo m_getStorageCallback; - - /// - /// Initializes a new instance of the class. - /// - /// The storage creator instance from the other AppDomain. - public StorageCreatorAccessor(object owner) - { - m_wrapped = owner; - - m_getStorageCallback = m_wrapped.GetType().GetMethod(nameof(MemoryStorageCreator.GetStorageCallback)); - - if (new[] { m_wrapped, m_getStorageCallback }.Any(x => x == null)) - throw new Exception($"Something changed in {typeof(MemoryStorageCreator)}"); - } - - /// - /// Gets or creates a storage module with the given name - /// - /// The storage module or null. - /// The name of the module to get. - /// The session key of the module, or null. - /// The module time-to-live, zero or less means no expiration. - /// Automatically create storage if not found - public async Task GetStorageAsync(string name, string key, int ttl, bool autocreate) - { - var appdomaintask = new AppDomainTask(); - m_getStorageCallback.Invoke(m_wrapped, new object[] { name, key, ttl, autocreate, appdomaintask }); - - var res = await appdomaintask.ResultAsync(); - if (res == null) - return null; - - return new StorageEntryWrapper(res); - } - } - - /// - /// A storage entry that uses a defaultable dictionary for storage - /// - internal class MemoryStorageEntry : MarshalByRefObject, IStorageEntry - { + { + /// + /// The remote instance of the StorageCreator + /// + private readonly object m_wrapped; + /// + /// The GetStorageAsync method + /// + private readonly System.Reflection.MethodInfo m_getStorageCallback; + + /// + /// Initializes a new instance of the class. + /// + /// The storage creator instance from the other AppDomain. + public StorageCreatorAccessor(object owner) + { + m_wrapped = owner; + + m_getStorageCallback = m_wrapped.GetType().GetMethod(nameof(MemoryStorageCreator.GetStorageCallback)); + + if (new[] { m_wrapped, m_getStorageCallback }.Any(x => x == null)) + throw new Exception($"Something changed in {typeof(MemoryStorageCreator)}"); + } + + /// + /// Gets or creates a storage module with the given name + /// + /// The storage module or null. + /// The name of the module to get. + /// The session key of the module, or null. + /// The module time-to-live, zero or less means no expiration. + /// Automatically create storage if not found + public async Task GetStorageAsync(string name, string key, int ttl, bool autocreate) + { + var appdomaintask = new AppDomainTask(); + m_getStorageCallback.Invoke(m_wrapped, new object[] { name, key, ttl, autocreate, appdomaintask }); + + var res = await appdomaintask.ResultAsync(); + if (res == null) + return null; + + return new StorageEntryWrapper(res); + } + } + + /// + /// A storage entry that uses a defaultable dictionary for storage + /// + internal class MemoryStorageEntry : MarshalByRefObject, IStorageEntry + { /// /// The storage entry /// @@ -290,347 +290,347 @@ internal class MemoryStorageEntry : MarshalByRefObject, IStorageEntry /// /// The storage element name. public MemoryStorageEntry(string name) - { - this.Name = name; - } - - /// - /// Gets or sets the and element with the specified key. - /// - /// The key to look for. - public string this[string key] - { - get { return m_dict[key]; } - set { m_dict[key] = value; } - } - - /// - /// Gets or sets the time when the storage entry expires - /// - /// The expires. - public DateTime Expires { get; set; } - - /// - /// Gets the name of this storage entry - /// - public string Name { get; private set; } - - /// - ///Gets the number of elements in the collection - /// - public int Count { get { return m_dict.Count; } } - - /// - /// Gets a value indicating whether this instance is read only. - /// - public bool IsReadOnly { get { return m_dict.IsReadOnly; } } - - /// - /// Gets the keys for this collection - /// - public ICollection Keys { get { return m_dict.Keys; } } - - /// - /// Gets the values for this collection - /// - public ICollection Values { get { return m_dict.Values; } } - - /// - /// Adds an item to the collection - /// - /// The item to add. - public void Add(KeyValuePair item) - { - m_dict.Add(item); - } - - /// - /// Adds an item to the collection - /// - /// The key to use. - /// The value to use. - public void Add(string key, string value) - { - m_dict.Add(key, value); - } - - /// - /// Removes all elements from this collection - /// - public void Clear() - { - m_dict.Clear(); - } - - /// - /// Returns a value indicating if the given item was found in the collection - /// - /// The item to look for. - public bool Contains(KeyValuePair item) - { - return m_dict.Contains(item); - } - - /// - /// Returns a value indicating if the given item was found in the collection - /// - /// true, if key was found, false otherwise. - /// The key to look for. - public bool ContainsKey(string key) - { - return m_dict.ContainsKey(key); - } - - /// - /// Copies the elements to an array - /// - /// The target array. - /// The target array index. - public void CopyTo(KeyValuePair[] array, int arrayIndex) - { - m_dict.CopyTo(array, arrayIndex); - } - - /// - /// Gets the enumerator. - /// - /// The enumerator. - public IEnumerator> GetEnumerator() - { - return m_dict.GetEnumerator(); - } - - /// - /// Remove the specified item. - /// - /// The item to remove. - public bool Remove(KeyValuePair item) - { - return m_dict.Remove(item); - } - - /// - /// Remove the item with the specified key. - /// - /// The key to look for. - public bool Remove(string key) - { - return m_dict.Remove(key); - } - - /// - /// Tries the get value for the given key. - /// - /// true, if get value was found, false otherwise. - /// The key to look for. - /// The resulting value. - public bool TryGetValue(string key, out string value) - { - return m_dict.TryGetValue(key, out value); - } - - /// - /// Gets the enumerator. - /// - /// The enumerator. - IEnumerator IEnumerable.GetEnumerator() - { - return m_dict.GetEnumerator(); - } - } + { + this.Name = name; + } + + /// + /// Gets or sets the and element with the specified key. + /// + /// The key to look for. + public string this[string key] + { + get { return m_dict[key]; } + set { m_dict[key] = value; } + } + + /// + /// Gets or sets the time when the storage entry expires + /// + /// The expires. + public DateTime Expires { get; set; } + + /// + /// Gets the name of this storage entry + /// + public string Name { get; private set; } + + /// + ///Gets the number of elements in the collection + /// + public int Count { get { return m_dict.Count; } } + + /// + /// Gets a value indicating whether this instance is read only. + /// + public bool IsReadOnly { get { return m_dict.IsReadOnly; } } + + /// + /// Gets the keys for this collection + /// + public ICollection Keys { get { return m_dict.Keys; } } + + /// + /// Gets the values for this collection + /// + public ICollection Values { get { return m_dict.Values; } } + + /// + /// Adds an item to the collection + /// + /// The item to add. + public void Add(KeyValuePair item) + { + m_dict.Add(item); + } + + /// + /// Adds an item to the collection + /// + /// The key to use. + /// The value to use. + public void Add(string key, string value) + { + m_dict.Add(key, value); + } + + /// + /// Removes all elements from this collection + /// + public void Clear() + { + m_dict.Clear(); + } + + /// + /// Returns a value indicating if the given item was found in the collection + /// + /// The item to look for. + public bool Contains(KeyValuePair item) + { + return m_dict.Contains(item); + } + + /// + /// Returns a value indicating if the given item was found in the collection + /// + /// true, if key was found, false otherwise. + /// The key to look for. + public bool ContainsKey(string key) + { + return m_dict.ContainsKey(key); + } + + /// + /// Copies the elements to an array + /// + /// The target array. + /// The target array index. + public void CopyTo(KeyValuePair[] array, int arrayIndex) + { + m_dict.CopyTo(array, arrayIndex); + } + + /// + /// Gets the enumerator. + /// + /// The enumerator. + public IEnumerator> GetEnumerator() + { + return m_dict.GetEnumerator(); + } + + /// + /// Remove the specified item. + /// + /// The item to remove. + public bool Remove(KeyValuePair item) + { + return m_dict.Remove(item); + } + + /// + /// Remove the item with the specified key. + /// + /// The key to look for. + public bool Remove(string key) + { + return m_dict.Remove(key); + } + + /// + /// Tries the get value for the given key. + /// + /// true, if get value was found, false otherwise. + /// The key to look for. + /// The resulting value. + public bool TryGetValue(string key, out string value) + { + return m_dict.TryGetValue(key, out value); + } + + /// + /// Gets the enumerator. + /// + /// The enumerator. + IEnumerator IEnumerable.GetEnumerator() + { + return m_dict.GetEnumerator(); + } + } /// /// A storage creator instance that uses simple in-memory dictionaries /// internal class MemoryStorageCreator : MarshalByRefObject, IStorageCreator, IDisposable - { - /// - /// Synchronization lock - /// - private readonly AsyncLock m_lock = new AsyncLock(); - - /// - /// The storage item - /// - private readonly Dictionary> m_storage = new Dictionary>(); - - /// - /// Gets or sets an external creator, used to supply custom storage. - /// Parameters are (name, key, ttl) - /// - public Func> ExternalCreator { get; set; } - - /// - /// Gets or sets the expiration check interval. - /// - public TimeSpan ExpireCheckInterval - { - get { return m_expirationHandler.Interval; } - set { m_expirationHandler.Interval = value; } - } - - /// - /// Gets or sets the high water mark, where expires are triggered. - /// - public long HighWaterMark { get; set; } = 10000; - - /// - /// The expiration handler. - /// - private PeriodicTask m_expirationHandler; - - /// - /// The minimum high water mark - /// - private readonly long m_minhighwater; - - /// - /// The number of items created - /// - private long m_createcount; - - /// - /// Initializes a new instance of the class. - /// - public MemoryStorageCreator() - { - m_minhighwater = HighWaterMark; - m_expirationHandler = new PeriodicTask(DoExpireAsync, TimeSpan.FromMinutes(10)); - } - - /// - /// Perform the actual expiration - /// - private async Task DoExpireAsync(bool forced) - { - var count = 0L; - using (await m_lock.LockAsync()) - { - foreach (var kp in m_storage) - { - var expiredkeys = kp.Value - .Where(x => x.Value.Expires.Ticks > 0 && DateTime.Now > x.Value.Expires) - .Select(x => x.Key) - .ToList(); - foreach (var key in expiredkeys) - kp.Value.Remove(key); - - count += kp.Value.Count; - } - - m_createcount = count; - - if (count * 1.1 > HighWaterMark) - HighWaterMark = HighWaterMark * 2; - else if (count < HighWaterMark / 4) - HighWaterMark = Math.Max(m_minhighwater, HighWaterMark / 2); - } - - return count; - } - - - /// - /// Gets or creates a storage module with the given name - /// - /// The storage module or null. - /// The name of the module to get. - /// The session key of the module, or null. - /// The module time-to-live, zero or less means no expiration. - /// Automatically create storage if not found - /// The callback handler - public void GetStorageCallback(string name, string key, int ttl, bool autocreate, AppDomainTask handler) - { - AppDomainTask.HandleTask(GetStorageAsync(name, key, ttl, autocreate), handler); - } - - /// - /// Gets or creates a storage module with the given name - /// - /// The storage module or null. - /// The name of the module to get. - /// The session key of the module, or null. - /// The module time-to-live, zero or less means no expiration. - /// Automatically create storage if not found - public async Task GetStorageAsync(string name, string key, int ttl, bool autocreate) - { - // Copy ref to avoid race when setting a new creator - var ec = ExternalCreator; - - IStorageEntry res = null; - key = key ?? string.Empty; - - using (await m_lock.LockAsync()) - { - Dictionary dict; - if (!m_storage.TryGetValue(name, out dict)) - dict = m_storage[name] = new Dictionary(); - - if (!dict.TryGetValue(key, out res)) - { - if (!autocreate) - return null; - - if (ec != null) - res = await ec(name, key, ttl); - - if (res == null) - res = new MemoryStorageEntry(name); - - dict[key] = res; - m_createcount++; - } - else if (res.Expires.Ticks > 0 && DateTime.Now > res.Expires) - { - dict.Remove(key); - if (!autocreate) - { - m_createcount--; - return null; - } - - res = null; - if (ec != null) - res = await ec(name, key, ttl); - - if (res == null) - res = new MemoryStorageEntry(name); - - dict[key] = res; - } - - if (ttl > 0) - res.Expires = DateTime.Now.AddSeconds(ttl); - - if (m_createcount > HighWaterMark) - m_expirationHandler.RunNow(); - - return res; - } - } - - /// - /// Releases all resource used by the object. - /// - /// Call when you are finished using the . The - /// method leaves the in an unusable state. - /// After calling , you must release all references to the - /// so the garbage collector can reclaim the memory that the - /// was occupying. - public void Dispose() - { - if (m_expirationHandler != null) - m_expirationHandler.Dispose(); - } - - /// - /// Releases unmanaged resources and performs other cleanup operations before the - /// is reclaimed by garbage collection. - /// - ~MemoryStorageCreator() - { - Dispose(); - GC.SuppressFinalize(this); - } - } + { + /// + /// Synchronization lock + /// + private readonly AsyncLock m_lock = new AsyncLock(); + + /// + /// The storage item + /// + private readonly Dictionary> m_storage = new Dictionary>(); + + /// + /// Gets or sets an external creator, used to supply custom storage. + /// Parameters are (name, key, ttl) + /// + public Func> ExternalCreator { get; set; } + + /// + /// Gets or sets the expiration check interval. + /// + public TimeSpan ExpireCheckInterval + { + get { return m_expirationHandler.Interval; } + set { m_expirationHandler.Interval = value; } + } + + /// + /// Gets or sets the high water mark, where expires are triggered. + /// + public long HighWaterMark { get; set; } = 10000; + + /// + /// The expiration handler. + /// + private PeriodicTask m_expirationHandler; + + /// + /// The minimum high water mark + /// + private readonly long m_minhighwater; + + /// + /// The number of items created + /// + private long m_createcount; + + /// + /// Initializes a new instance of the class. + /// + public MemoryStorageCreator() + { + m_minhighwater = HighWaterMark; + m_expirationHandler = new PeriodicTask(DoExpireAsync, TimeSpan.FromMinutes(10)); + } + + /// + /// Perform the actual expiration + /// + private async Task DoExpireAsync(bool forced) + { + var count = 0L; + using (await m_lock.LockAsync()) + { + foreach (var kp in m_storage) + { + var expiredkeys = kp.Value + .Where(x => x.Value.Expires.Ticks > 0 && DateTime.Now > x.Value.Expires) + .Select(x => x.Key) + .ToList(); + foreach (var key in expiredkeys) + kp.Value.Remove(key); + + count += kp.Value.Count; + } + + m_createcount = count; + + if (count * 1.1 > HighWaterMark) + HighWaterMark = HighWaterMark * 2; + else if (count < HighWaterMark / 4) + HighWaterMark = Math.Max(m_minhighwater, HighWaterMark / 2); + } + + return count; + } + + + /// + /// Gets or creates a storage module with the given name + /// + /// The storage module or null. + /// The name of the module to get. + /// The session key of the module, or null. + /// The module time-to-live, zero or less means no expiration. + /// Automatically create storage if not found + /// The callback handler + public void GetStorageCallback(string name, string key, int ttl, bool autocreate, AppDomainTask handler) + { + AppDomainTask.HandleTask(GetStorageAsync(name, key, ttl, autocreate), handler); + } + + /// + /// Gets or creates a storage module with the given name + /// + /// The storage module or null. + /// The name of the module to get. + /// The session key of the module, or null. + /// The module time-to-live, zero or less means no expiration. + /// Automatically create storage if not found + public async Task GetStorageAsync(string name, string key, int ttl, bool autocreate) + { + // Copy ref to avoid race when setting a new creator + var ec = ExternalCreator; + + IStorageEntry res = null; + key = key ?? string.Empty; + + using (await m_lock.LockAsync()) + { + Dictionary dict; + if (!m_storage.TryGetValue(name, out dict)) + dict = m_storage[name] = new Dictionary(); + + if (!dict.TryGetValue(key, out res)) + { + if (!autocreate) + return null; + + if (ec != null) + res = await ec(name, key, ttl); + + if (res == null) + res = new MemoryStorageEntry(name); + + dict[key] = res; + m_createcount++; + } + else if (res.Expires.Ticks > 0 && DateTime.Now > res.Expires) + { + dict.Remove(key); + if (!autocreate) + { + m_createcount--; + return null; + } + + res = null; + if (ec != null) + res = await ec(name, key, ttl); + + if (res == null) + res = new MemoryStorageEntry(name); + + dict[key] = res; + } + + if (ttl > 0) + res.Expires = DateTime.Now.AddSeconds(ttl); + + if (m_createcount > HighWaterMark) + m_expirationHandler.RunNow(); + + return res; + } + } + + /// + /// Releases all resource used by the object. + /// + /// Call when you are finished using the . The + /// method leaves the in an unusable state. + /// After calling , you must release all references to the + /// so the garbage collector can reclaim the memory that the + /// was occupying. + public void Dispose() + { + if (m_expirationHandler != null) + m_expirationHandler.Dispose(); + } + + /// + /// Releases unmanaged resources and performs other cleanup operations before the + /// is reclaimed by garbage collection. + /// + ~MemoryStorageCreator() + { + Dispose(); + GC.SuppressFinalize(this); + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Mvc/Attributes.cs b/libraries/MTConnect.NET-HTTP/Ceen/Mvc/Attributes.cs index 92405dbb3..938e60877 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Mvc/Attributes.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Mvc/Attributes.cs @@ -4,182 +4,182 @@ namespace Ceen.Mvc { - /// - /// Attribute for renaming an elements route - /// - [AttributeUsage(AttributeTargets.Class | AttributeTargets.Method, Inherited = true, AllowMultiple = true)] + /// + /// Attribute for renaming an elements route + /// + [AttributeUsage(AttributeTargets.Class | AttributeTargets.Method, Inherited = true, AllowMultiple = true)] internal class RouteAttribute : Attribute - { - /// - /// Gets or sets the route. - /// - /// The route. - public string Route { get; set; } - - /// - /// Initializes a new instance of the class. - /// - /// The route expression to use. - public RouteAttribute(string route) - { - Route = route; - } - } - - /// - /// Attribute for renaming an elements route - /// - [AttributeUsage(AttributeTargets.Class | AttributeTargets.Method | AttributeTargets.Parameter | AttributeTargets.Interface, Inherited = false, AllowMultiple = false)] - internal class NameAttribute : Attribute - { - /// - /// Gets or sets the name this routing entry uses - /// - /// The path. - public string Name { get; set; } - - /// - /// Initializes a new instance of the class. - /// - /// The name to use - public NameAttribute(string name) - { - Name = name; - } - } - - /// - /// Flags that describe the allowed sources for arguments - /// - [Flags] + { + /// + /// Gets or sets the route. + /// + /// The route. + public string Route { get; set; } + + /// + /// Initializes a new instance of the class. + /// + /// The route expression to use. + public RouteAttribute(string route) + { + Route = route; + } + } + + /// + /// Attribute for renaming an elements route + /// + [AttributeUsage(AttributeTargets.Class | AttributeTargets.Method | AttributeTargets.Parameter | AttributeTargets.Interface, Inherited = false, AllowMultiple = false)] + internal class NameAttribute : Attribute + { + /// + /// Gets or sets the name this routing entry uses + /// + /// The path. + public string Name { get; set; } + + /// + /// Initializes a new instance of the class. + /// + /// The name to use + public NameAttribute(string name) + { + Name = name; + } + } + + /// + /// Flags that describe the allowed sources for arguments + /// + [Flags] internal enum ParameterSource - { - None = 0x0, - Url = 0x1, - Query = 0x2, - Form = 0x4, - Header = 0x8, + { + None = 0x0, + Url = 0x1, + Query = 0x2, + Form = 0x4, + Header = 0x8, Body = 0xF, - Default = Url | Query | Form | Body, - Request = Query | Form, - Any = Url | Query | Form | Request | Header | Body - } + Default = Url | Query | Form | Body, + Request = Query | Form, + Any = Url | Query | Form | Request | Header | Body + } - [AttributeUsage(AttributeTargets.Parameter, AllowMultiple = false)] + [AttributeUsage(AttributeTargets.Parameter, AllowMultiple = false)] internal class ParameterAttribute : Attribute - { - /// - /// Gets or sets the allowed sources for the entry - /// - /// The source. - public ParameterSource Source { get; set; } + { + /// + /// Gets or sets the allowed sources for the entry + /// + /// The source. + public ParameterSource Source { get; set; } /// /// Gets or sets the name of the entry, defaults to the name or the method argument /// /// The name. public string Name { get; set; } - /// - /// Gets or sets a value indicating whether this argument is required. - /// - public bool Required { get; set; } - - /// - /// Initializes a new instance of the class. - /// - /// Sets the allowed sources. - /// A flag indicating if the parameter is required. - public ParameterAttribute(ParameterSource source = ParameterSource.Default, bool required = true, string name = null) - { - Source = source; - Required = required; + /// + /// Gets or sets a value indicating whether this argument is required. + /// + public bool Required { get; set; } + + /// + /// Initializes a new instance of the class. + /// + /// Sets the allowed sources. + /// A flag indicating if the parameter is required. + public ParameterAttribute(ParameterSource source = ParameterSource.Default, bool required = true, string name = null) + { + Source = source; + Required = required; Name = name; - } - } + } + } - /// - /// Base http verb filter attribute - /// - [AttributeUsage(AttributeTargets.Method, AllowMultiple = true)] + /// + /// Base http verb filter attribute + /// + [AttributeUsage(AttributeTargets.Method, AllowMultiple = true)] internal class HttpVerbFilterAttribute : Attribute - { - /// - /// Gets or sets the verb this filter represents. - /// - /// The verb. - public string Verb { get; set; } - - /// - /// Initializes a new instance of the class. - /// - /// The verb to assign. - public HttpVerbFilterAttribute(string verb) - { - this.Verb = verb; - } - } + { + /// + /// Gets or sets the verb this filter represents. + /// + /// The verb. + public string Verb { get; set; } + + /// + /// Initializes a new instance of the class. + /// + /// The verb to assign. + public HttpVerbFilterAttribute(string verb) + { + this.Verb = verb; + } + } /// /// Http GET verb filter attribute. /// internal class HttpGetAttribute : HttpVerbFilterAttribute - { - public HttpGetAttribute() : base("GET") { } - } + { + public HttpGetAttribute() : base("GET") { } + } /// /// Http POST verb filter attribute. /// internal class HttpPostAttribute : HttpVerbFilterAttribute - { - public HttpPostAttribute() : base("POST") { } - } + { + public HttpPostAttribute() : base("POST") { } + } /// /// Http PUT verb filter attribute. /// internal class HttpPutAttribute : HttpVerbFilterAttribute - { - public HttpPutAttribute() : base("PUT") { } - } + { + public HttpPutAttribute() : base("PUT") { } + } /// /// Http DELETE verb filter attribute. /// internal class HttpDeleteAttribute : HttpVerbFilterAttribute - { - public HttpDeleteAttribute() : base("DELETE") { } - } + { + public HttpDeleteAttribute() : base("DELETE") { } + } /// /// Http HEAD verb filter attribute. /// internal class HttpHeadAttribute : HttpVerbFilterAttribute - { - public HttpHeadAttribute() : base("HEAD") { } - } + { + public HttpHeadAttribute() : base("HEAD") { } + } /// /// Http PATCH verb filter attribute. /// internal class HttpPatchAttribute : HttpVerbFilterAttribute - { - public HttpPatchAttribute() : base("PATCH") { } - } + { + public HttpPatchAttribute() : base("PATCH") { } + } /// /// Http MKCOL verb filter attribute. /// internal class HttpMkColAttribute : HttpVerbFilterAttribute - { - public HttpMkColAttribute() : base("MKCOL") { } - } + { + public HttpMkColAttribute() : base("MKCOL") { } + } /// /// Http PROPFIND verb filter attribute. /// internal class HttpPropFindAttribute : HttpVerbFilterAttribute - { - public HttpPropFindAttribute() : base("PROPFIND") { } - } + { + public HttpPropFindAttribute() : base("PROPFIND") { } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Mvc/Controller.cs b/libraries/MTConnect.NET-HTTP/Ceen/Mvc/Controller.cs index a3b725eba..c3d7857ac 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Mvc/Controller.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Mvc/Controller.cs @@ -13,8 +13,8 @@ namespace Ceen.Mvc /// Use this interface and place a RouteAttribute on it /// internal interface IControllerPrefix - { - } + { + } /// /// Interface for allowing a controller to reconfigure the static parts @@ -22,11 +22,11 @@ internal interface IControllerPrefix /// internal interface IIDynamicConfiguredController { - /// - /// Change a statically parsed route at runtime - /// - /// The route to change - /// The patched route + /// + /// Change a statically parsed route at runtime + /// + /// The route to change + /// The patched route PartialParsedRoute PatchRoute(PartialParsedRoute x); } @@ -34,121 +34,121 @@ internal interface IIDynamicConfiguredController /// Implementation of support methods in a controller /// internal abstract class Controller - { - /// - /// Returns the result as JSON encoded with UTF-8 - /// - /// The data object to serialize. - /// Set to true to emit non-cacheable headers. - protected IResult Json(object data, bool disablecaching = true) - { - return new LambdaResult(ctx => - { - if (disablecaching) - ctx.Response.SetNonCacheable(); - return ctx.Response.WriteAllJsonAsync(JsonSerializer.Serialize(data)); - }); - } - /// - /// Returns a text string as the result - /// - /// The string to return. - /// The encoding to use, defaults to UTF-8. - /// The content type to use, defaults to "text/plain". - /// Set to true to emit non-cacheable headers. - protected IResult Text(string data, System.Text.Encoding encoding = null, string contenttype = "text/plain", bool disablecaching = true) - { - encoding = encoding ?? System.Text.Encoding.UTF8; - - return new LambdaResult(ctx => - { - if (disablecaching) - ctx.Response.SetNonCacheable(); - - return ctx.Response.WriteAllAsync(data, encoding, string.Format("{0}; charset={1}", contenttype, encoding.BodyName)); - }); - } - - /// - /// Returns a html document as the result - /// - /// The html to return. - /// The encoding to use, defaults to UTF-8. - /// Set to true to emit non-cacheable headers. - protected IResult Html(string data, System.Text.Encoding encoding = null, bool disablecaching = true) - { - return Text(data, encoding, "text/html", disablecaching); - } - - /// - /// Sets the status for the request - /// - /// The status code. - /// An optional status message. - protected IResult Status(HttpStatusCode code, string message = null, bool disablecaching = true) - => new StatusCodeResult(code, message, disablecaching); - - /// - /// Sets the status for the request - /// - /// The status code. - /// An optional status message. - protected IResult Status(IStatusCodeResult code, string message = null, bool disablecaching = true) - => new StatusCodeResult(code.StatusCode, message ?? code.StatusMessage, disablecaching); - - /// - /// Sends a "400 - Bad request" response - /// - protected static readonly IStatusCodeResult BadRequest = new StatusCodeResult(HttpStatusCode.BadRequest); - - /// - /// Sends a "404 - Not found" response - /// - protected static readonly IStatusCodeResult NotFound = new StatusCodeResult(HttpStatusCode.NotFound); - - /// - /// Sends a "200 - OK" response - /// - protected static readonly IStatusCodeResult OK = new StatusCodeResult(HttpStatusCode.OK); - - /// - /// Sends a "403 - Forbidden" response - /// - protected static readonly IStatusCodeResult Forbidden = new StatusCodeResult(HttpStatusCode.Forbidden); - - /// - /// Sends a "204 - No Content" response - /// - protected static readonly IStatusCodeResult NoContent = new StatusCodeResult(HttpStatusCode.NoContent); - - /// - /// Sends a "302 - redirect" to the client - /// - /// URL. - protected IResult Redirect(string url) - { - return new LambdaResult(ctx => - { - ctx.Response.Redirect(url); - }); - } - - /// - /// Wraps a result method - /// - /// The function to use. - protected IResult Result(Func func) - { - return new LambdaResult(func); - } - - /// - /// Wraps a result method - /// - /// The function to use. - protected IResult Result(Action func) - { - return new LambdaResult(func); - } - } + { + /// + /// Returns the result as JSON encoded with UTF-8 + /// + /// The data object to serialize. + /// Set to true to emit non-cacheable headers. + protected IResult Json(object data, bool disablecaching = true) + { + return new LambdaResult(ctx => + { + if (disablecaching) + ctx.Response.SetNonCacheable(); + return ctx.Response.WriteAllJsonAsync(JsonSerializer.Serialize(data)); + }); + } + /// + /// Returns a text string as the result + /// + /// The string to return. + /// The encoding to use, defaults to UTF-8. + /// The content type to use, defaults to "text/plain". + /// Set to true to emit non-cacheable headers. + protected IResult Text(string data, System.Text.Encoding encoding = null, string contenttype = "text/plain", bool disablecaching = true) + { + encoding = encoding ?? System.Text.Encoding.UTF8; + + return new LambdaResult(ctx => + { + if (disablecaching) + ctx.Response.SetNonCacheable(); + + return ctx.Response.WriteAllAsync(data, encoding, string.Format("{0}; charset={1}", contenttype, encoding.BodyName)); + }); + } + + /// + /// Returns a html document as the result + /// + /// The html to return. + /// The encoding to use, defaults to UTF-8. + /// Set to true to emit non-cacheable headers. + protected IResult Html(string data, System.Text.Encoding encoding = null, bool disablecaching = true) + { + return Text(data, encoding, "text/html", disablecaching); + } + + /// + /// Sets the status for the request + /// + /// The status code. + /// An optional status message. + protected IResult Status(HttpStatusCode code, string message = null, bool disablecaching = true) + => new StatusCodeResult(code, message, disablecaching); + + /// + /// Sets the status for the request + /// + /// The status code. + /// An optional status message. + protected IResult Status(IStatusCodeResult code, string message = null, bool disablecaching = true) + => new StatusCodeResult(code.StatusCode, message ?? code.StatusMessage, disablecaching); + + /// + /// Sends a "400 - Bad request" response + /// + protected static readonly IStatusCodeResult BadRequest = new StatusCodeResult(HttpStatusCode.BadRequest); + + /// + /// Sends a "404 - Not found" response + /// + protected static readonly IStatusCodeResult NotFound = new StatusCodeResult(HttpStatusCode.NotFound); + + /// + /// Sends a "200 - OK" response + /// + protected static readonly IStatusCodeResult OK = new StatusCodeResult(HttpStatusCode.OK); + + /// + /// Sends a "403 - Forbidden" response + /// + protected static readonly IStatusCodeResult Forbidden = new StatusCodeResult(HttpStatusCode.Forbidden); + + /// + /// Sends a "204 - No Content" response + /// + protected static readonly IStatusCodeResult NoContent = new StatusCodeResult(HttpStatusCode.NoContent); + + /// + /// Sends a "302 - redirect" to the client + /// + /// URL. + protected IResult Redirect(string url) + { + return new LambdaResult(ctx => + { + ctx.Response.Redirect(url); + }); + } + + /// + /// Wraps a result method + /// + /// The function to use. + protected IResult Result(Func func) + { + return new LambdaResult(func); + } + + /// + /// Wraps a result method + /// + /// The function to use. + protected IResult Result(Action func) + { + return new LambdaResult(func); + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Mvc/ControllerRouter.cs b/libraries/MTConnect.NET-HTTP/Ceen/Mvc/ControllerRouter.cs index 0a83691d5..eaa969cfa 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Mvc/ControllerRouter.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Mvc/ControllerRouter.cs @@ -14,83 +14,83 @@ namespace Ceen /// Extension methods for the Mvc module /// internal static class MvcExtensionMethods - { - /// - /// Creates a route instance from an assembly - /// - /// The route. - /// The assembly to use. - /// An optional config. - /// The router - public static Ceen.Mvc.ControllerRouter ToRoute(this Assembly assembly, Ceen.Mvc.ControllerRouterConfig config = null) - { - return new Mvc.ControllerRouter(config ?? new Mvc.ControllerRouterConfig(), assembly); - } - - /// - /// Creates a route instance from a list of assemblies - /// - /// The route. - /// The assemblies to use. - /// An optional config. - /// The router - public static Ceen.Mvc.ControllerRouter ToRoute(this IEnumerable assemblies, Ceen.Mvc.ControllerRouterConfig config = null) - { - return new Mvc.ControllerRouter(config ?? new Mvc.ControllerRouterConfig(), assemblies); - } - - /// - /// Creates a route instance from a list of types - /// - /// The route. - /// The types to use. - /// An optional config. - /// The router - public static Ceen.Mvc.ControllerRouter ToRoute(this IEnumerable types, Ceen.Mvc.ControllerRouterConfig config = null) - { - return new Mvc.ControllerRouter(config ?? new Mvc.ControllerRouterConfig(), types); - } - - /// - /// Creates a route instance from a list of types - /// - /// The route. - /// The declared instances to use. - /// An optional config. - /// The router - public static Ceen.Mvc.ControllerRouter ToRoute(this IEnumerable instances, Ceen.Mvc.ControllerRouterConfig config = null) - => new Mvc.ControllerRouter( - config ?? new Mvc.ControllerRouterConfig(), - instances - ); - - /// - /// Creates a route instance from a list of routes - /// - /// The routes to use - /// The config to use - /// The router - public static Ceen.Mvc.ControllerRouter ToRoute(this IEnumerable routes, Ceen.Mvc.ControllerRouterConfig config = null) - => new Mvc.ControllerRouter( - config ?? new Mvc.ControllerRouterConfig(), - new Ceen.Mvc.ManualRoutingController( - routes - ) - ); - - /// - /// Creates a route instance for a manual routing controller - /// - /// The manual routing controller - /// The config to use - /// The controller - public static Ceen.Mvc.ControllerRouter ToRoute(this Ceen.Mvc.ManualRoutingController self, Ceen.Mvc.ControllerRouterConfig config = null) - => new Mvc.ControllerRouter( - config ?? new Mvc.ControllerRouterConfig(), - self - ); - - } + { + /// + /// Creates a route instance from an assembly + /// + /// The route. + /// The assembly to use. + /// An optional config. + /// The router + public static Ceen.Mvc.ControllerRouter ToRoute(this Assembly assembly, Ceen.Mvc.ControllerRouterConfig config = null) + { + return new Mvc.ControllerRouter(config ?? new Mvc.ControllerRouterConfig(), assembly); + } + + /// + /// Creates a route instance from a list of assemblies + /// + /// The route. + /// The assemblies to use. + /// An optional config. + /// The router + public static Ceen.Mvc.ControllerRouter ToRoute(this IEnumerable assemblies, Ceen.Mvc.ControllerRouterConfig config = null) + { + return new Mvc.ControllerRouter(config ?? new Mvc.ControllerRouterConfig(), assemblies); + } + + /// + /// Creates a route instance from a list of types + /// + /// The route. + /// The types to use. + /// An optional config. + /// The router + public static Ceen.Mvc.ControllerRouter ToRoute(this IEnumerable types, Ceen.Mvc.ControllerRouterConfig config = null) + { + return new Mvc.ControllerRouter(config ?? new Mvc.ControllerRouterConfig(), types); + } + + /// + /// Creates a route instance from a list of types + /// + /// The route. + /// The declared instances to use. + /// An optional config. + /// The router + public static Ceen.Mvc.ControllerRouter ToRoute(this IEnumerable instances, Ceen.Mvc.ControllerRouterConfig config = null) + => new Mvc.ControllerRouter( + config ?? new Mvc.ControllerRouterConfig(), + instances + ); + + /// + /// Creates a route instance from a list of routes + /// + /// The routes to use + /// The config to use + /// The router + public static Ceen.Mvc.ControllerRouter ToRoute(this IEnumerable routes, Ceen.Mvc.ControllerRouterConfig config = null) + => new Mvc.ControllerRouter( + config ?? new Mvc.ControllerRouterConfig(), + new Ceen.Mvc.ManualRoutingController( + routes + ) + ); + + /// + /// Creates a route instance for a manual routing controller + /// + /// The manual routing controller + /// The config to use + /// The controller + public static Ceen.Mvc.ControllerRouter ToRoute(this Ceen.Mvc.ManualRoutingController self, Ceen.Mvc.ControllerRouterConfig config = null) + => new Mvc.ControllerRouter( + config ?? new Mvc.ControllerRouterConfig(), + self + ); + + } } namespace Ceen.Mvc @@ -99,625 +99,625 @@ namespace Ceen.Mvc /// Some common Linq methods /// internal static class LinqHelpers - { - /// - /// Builds a dictionary where the identical key values overwrite instead of throwing exceptions - /// - /// The dictionary. - /// The list to build from. - /// The function to extract the key. - /// An optional target dictionary - /// The key type parameter. - /// The value type parameter. - public static Dictionary ToSafeDictionary(this IEnumerable self, Func keyselector, Dictionary target = null) - { - var res = target ?? new Dictionary(); - foreach (var x in self) - res[keyselector(x)] = x; - return res; - } - - /// - /// Builds a dictionary where the identical key values overwrite instead of throwing exceptions - /// - /// The dictionary. - /// The list to build from. - /// The function to extract the key. - /// The function to extract the value. - /// An optional target dictionary - /// The key type parameter. - /// The value type parameter. - /// The source type parameter. - public static Dictionary ToSafeDictionary(this IEnumerable self, Func keyselector, Func valueselector, Dictionary target) - { - var res = target ?? new Dictionary(); - foreach (var x in self) - res[keyselector(x)] = valueselector(x); - return res; - } - - /// - /// Returns distinct items, by sorting the list and removing duplicate values - /// - /// The list to filter. - /// The function to extract the compare parameter. - /// An optional key comparer. - /// The value type parameter. - /// The distinct value type parameter. - public static IEnumerable Distinct(this IEnumerable self, Func comparevalue, IComparer comparer = null) - { - var prev = default(TKey); - var first = true; - var cmp = comparer ?? Comparer.Default; - - foreach (var item in self.OrderBy(x => comparevalue(x))) - { - var k = comparevalue(item); - if (first || cmp.Compare(prev, k) != 0) - { - first = false; - prev = k; - yield return item; - } - } - } - - /// - /// Gets the covering parent interfaces for a given type - /// - /// The parent interfaces. - /// The type to examine. - /// An filter to limit the results to a specific type - public static IEnumerable GetParentInterfaces(this Type self) - { - return GetParentInterfaces(self, typeof(TFilter)); - } - - /// - /// Gets the covering parent interfaces for a given type - /// - /// The parent interfaces. - /// The type to examine. - /// An optional filter to limit the results to a specific type. - public static IEnumerable GetParentInterfaces(this Type self, Type basetypefilter = null) - { - var all = self.GetInterfaces().AsEnumerable(); - if (basetypefilter != null) - all = all.Where(x => basetypefilter.IsAssignableFrom(x)); - - return all.Except(all.SelectMany(t => t.GetInterfaces())); - } - - /// - /// Gets a list of parent interfaces - /// - /// The sequence of parent interfaces. - /// The type to start with. - /// An filter to limit the results to a specific type - public static IEnumerable GetParentInterfaceSequence(this Type self) - { - return GetParentInterfaceSequence(self, typeof(TFilter)); - } - - /// - /// Gets a list of parent interfaces - /// - /// The sequence of parent interfaces. - /// The type to start with. - /// An optional filter to limit the results to a specific type. - public static IEnumerable GetParentInterfaceSequence(this Type self, Type basetypefilter = null) - { - var cur = self; - while (cur != null) - { - yield return cur; - - var parents = cur.GetParentInterfaces(basetypefilter); - - if (parents.Count() > 1) - throw new Exception($"Error building prefix map, the type {cur.FullName} (from {self.FullName} has multiple parents"); - cur = parents.FirstOrDefault(); - - if (cur == basetypefilter) - basetypefilter = null; - } - } - - /// - /// Searches the type inheritance tree until it finds the desired attribute. - /// This approach allows a derived class to override attributes, but defaults to inheriting. - /// - /// The type to examine - /// The attribute type to find - /// The attributes found - public static IEnumerable SearchCustomAttributes(this Type self) - where T : Attribute - { - if (self == null) - throw new ArgumentNullException(nameof(self)); - - do - { - var res = self.GetCustomAttributes(typeof(T), false); - if (res != null && res.Length > 0) - return res.Cast(); - - self = self.BaseType; - } while(self != null); - - return new T[0]; - } - - /// - /// Searches the type inheritance tree until it finds the desired attribute. - /// This approach allows a derived class to override attributes, but defaults to inheriting. - /// - /// The type to examine - /// The attribute type to find - /// The attributes found - public static IEnumerable SearchCustomAttributes(this MethodInfo self) - where T : Attribute - { - if (self == null) - throw new ArgumentNullException(nameof(self)); - - do - { - var res = self.GetCustomAttributes(typeof(T), false); - if (res != null && res.Length > 0) - return res.Cast(); - - var next = self.GetBaseDefinition(); - if (self == next) - break; - self = next; - } while(self != null); - - return new T[0]; - } - - /// - /// Gets the name of an item - /// - /// The item name. - /// The type to get the name for. - /// The configuration to use - public static string GetItemName(this Type self, ControllerRouterConfig config) - { - var nameattr = self.SearchCustomAttributes().Cast().FirstOrDefault(); - // Extract an assigned name - if (nameattr != null) - return nameattr.Name; - - var name = self.Name; - if (typeof(Controller).IsAssignableFrom(self) && self.IsClass) - { - if (config.ControllerSuffixRemovals != null) - foreach (var rm in config.ControllerSuffixRemovals) - while (!string.IsNullOrWhiteSpace(rm) && name.EndsWith(rm, StringComparison.InvariantCultureIgnoreCase)) - name = name.Substring(0, name.Length - rm.Length); - if (config.ControllerPrefixRemovals != null) - foreach (var rm in config.ControllerPrefixRemovals) - while (!string.IsNullOrWhiteSpace(rm) && name.StartsWith(rm, StringComparison.InvariantCultureIgnoreCase)) - name = name.Substring(rm.Length); - } - else if (typeof(IControllerPrefix).IsAssignableFrom(self) && self.IsInterface) - { - if (config.InterfaceSuffixRemovals != null) - foreach (var rm in config.InterfaceSuffixRemovals) - while (!string.IsNullOrWhiteSpace(rm) && name.EndsWith(rm, StringComparison.InvariantCultureIgnoreCase)) - name = name.Substring(0, name.Length - rm.Length); - if (config.InterfacePrefixRemovals != null) - foreach (var rm in config.InterfacePrefixRemovals) - while (!string.IsNullOrWhiteSpace(rm) && name.StartsWith(rm, StringComparison.InvariantCultureIgnoreCase)) - name = name.Substring(rm.Length); - } - - if (config.LowerCaseNames) - name = name.ToLowerInvariant(); - - return name; - } - - /// - /// Gets the name of an item - /// - /// The item name. - /// The type to get the name for. - /// The configuration to use - public static string GetItemName(this MethodInfo self, ControllerRouterConfig config) - { - var nameattr = self.SearchCustomAttributes().Cast().FirstOrDefault(); - // Extract an assigned name - if (nameattr != null) - return nameattr.Name; - - var name = self.Name; - if (config.LowerCaseNames) - name = name.ToLowerInvariant(); - - return name; - } - } + { + /// + /// Builds a dictionary where the identical key values overwrite instead of throwing exceptions + /// + /// The dictionary. + /// The list to build from. + /// The function to extract the key. + /// An optional target dictionary + /// The key type parameter. + /// The value type parameter. + public static Dictionary ToSafeDictionary(this IEnumerable self, Func keyselector, Dictionary target = null) + { + var res = target ?? new Dictionary(); + foreach (var x in self) + res[keyselector(x)] = x; + return res; + } + + /// + /// Builds a dictionary where the identical key values overwrite instead of throwing exceptions + /// + /// The dictionary. + /// The list to build from. + /// The function to extract the key. + /// The function to extract the value. + /// An optional target dictionary + /// The key type parameter. + /// The value type parameter. + /// The source type parameter. + public static Dictionary ToSafeDictionary(this IEnumerable self, Func keyselector, Func valueselector, Dictionary target) + { + var res = target ?? new Dictionary(); + foreach (var x in self) + res[keyselector(x)] = valueselector(x); + return res; + } + + /// + /// Returns distinct items, by sorting the list and removing duplicate values + /// + /// The list to filter. + /// The function to extract the compare parameter. + /// An optional key comparer. + /// The value type parameter. + /// The distinct value type parameter. + public static IEnumerable Distinct(this IEnumerable self, Func comparevalue, IComparer comparer = null) + { + var prev = default(TKey); + var first = true; + var cmp = comparer ?? Comparer.Default; + + foreach (var item in self.OrderBy(x => comparevalue(x))) + { + var k = comparevalue(item); + if (first || cmp.Compare(prev, k) != 0) + { + first = false; + prev = k; + yield return item; + } + } + } + + /// + /// Gets the covering parent interfaces for a given type + /// + /// The parent interfaces. + /// The type to examine. + /// An filter to limit the results to a specific type + public static IEnumerable GetParentInterfaces(this Type self) + { + return GetParentInterfaces(self, typeof(TFilter)); + } + + /// + /// Gets the covering parent interfaces for a given type + /// + /// The parent interfaces. + /// The type to examine. + /// An optional filter to limit the results to a specific type. + public static IEnumerable GetParentInterfaces(this Type self, Type basetypefilter = null) + { + var all = self.GetInterfaces().AsEnumerable(); + if (basetypefilter != null) + all = all.Where(x => basetypefilter.IsAssignableFrom(x)); + + return all.Except(all.SelectMany(t => t.GetInterfaces())); + } + + /// + /// Gets a list of parent interfaces + /// + /// The sequence of parent interfaces. + /// The type to start with. + /// An filter to limit the results to a specific type + public static IEnumerable GetParentInterfaceSequence(this Type self) + { + return GetParentInterfaceSequence(self, typeof(TFilter)); + } + + /// + /// Gets a list of parent interfaces + /// + /// The sequence of parent interfaces. + /// The type to start with. + /// An optional filter to limit the results to a specific type. + public static IEnumerable GetParentInterfaceSequence(this Type self, Type basetypefilter = null) + { + var cur = self; + while (cur != null) + { + yield return cur; + + var parents = cur.GetParentInterfaces(basetypefilter); + + if (parents.Count() > 1) + throw new Exception($"Error building prefix map, the type {cur.FullName} (from {self.FullName} has multiple parents"); + cur = parents.FirstOrDefault(); + + if (cur == basetypefilter) + basetypefilter = null; + } + } + + /// + /// Searches the type inheritance tree until it finds the desired attribute. + /// This approach allows a derived class to override attributes, but defaults to inheriting. + /// + /// The type to examine + /// The attribute type to find + /// The attributes found + public static IEnumerable SearchCustomAttributes(this Type self) + where T : Attribute + { + if (self == null) + throw new ArgumentNullException(nameof(self)); + + do + { + var res = self.GetCustomAttributes(typeof(T), false); + if (res != null && res.Length > 0) + return res.Cast(); + + self = self.BaseType; + } while (self != null); + + return new T[0]; + } + + /// + /// Searches the type inheritance tree until it finds the desired attribute. + /// This approach allows a derived class to override attributes, but defaults to inheriting. + /// + /// The type to examine + /// The attribute type to find + /// The attributes found + public static IEnumerable SearchCustomAttributes(this MethodInfo self) + where T : Attribute + { + if (self == null) + throw new ArgumentNullException(nameof(self)); + + do + { + var res = self.GetCustomAttributes(typeof(T), false); + if (res != null && res.Length > 0) + return res.Cast(); + + var next = self.GetBaseDefinition(); + if (self == next) + break; + self = next; + } while (self != null); + + return new T[0]; + } + + /// + /// Gets the name of an item + /// + /// The item name. + /// The type to get the name for. + /// The configuration to use + public static string GetItemName(this Type self, ControllerRouterConfig config) + { + var nameattr = self.SearchCustomAttributes().Cast().FirstOrDefault(); + // Extract an assigned name + if (nameattr != null) + return nameattr.Name; + + var name = self.Name; + if (typeof(Controller).IsAssignableFrom(self) && self.IsClass) + { + if (config.ControllerSuffixRemovals != null) + foreach (var rm in config.ControllerSuffixRemovals) + while (!string.IsNullOrWhiteSpace(rm) && name.EndsWith(rm, StringComparison.InvariantCultureIgnoreCase)) + name = name.Substring(0, name.Length - rm.Length); + if (config.ControllerPrefixRemovals != null) + foreach (var rm in config.ControllerPrefixRemovals) + while (!string.IsNullOrWhiteSpace(rm) && name.StartsWith(rm, StringComparison.InvariantCultureIgnoreCase)) + name = name.Substring(rm.Length); + } + else if (typeof(IControllerPrefix).IsAssignableFrom(self) && self.IsInterface) + { + if (config.InterfaceSuffixRemovals != null) + foreach (var rm in config.InterfaceSuffixRemovals) + while (!string.IsNullOrWhiteSpace(rm) && name.EndsWith(rm, StringComparison.InvariantCultureIgnoreCase)) + name = name.Substring(0, name.Length - rm.Length); + if (config.InterfacePrefixRemovals != null) + foreach (var rm in config.InterfacePrefixRemovals) + while (!string.IsNullOrWhiteSpace(rm) && name.StartsWith(rm, StringComparison.InvariantCultureIgnoreCase)) + name = name.Substring(rm.Length); + } + + if (config.LowerCaseNames) + name = name.ToLowerInvariant(); + + return name; + } + + /// + /// Gets the name of an item + /// + /// The item name. + /// The type to get the name for. + /// The configuration to use + public static string GetItemName(this MethodInfo self, ControllerRouterConfig config) + { + var nameattr = self.SearchCustomAttributes().Cast().FirstOrDefault(); + // Extract an assigned name + if (nameattr != null) + return nameattr.Name; + + var name = self.Name; + if (config.LowerCaseNames) + name = name.ToLowerInvariant(); + + return name; + } + } /// /// Represents the parsed route before binding any variables /// internal class PartialParsedRoute - { - /// - /// The controller instance to use - /// - public Controller Controller; - /// - /// The path fragment on the controller - /// - public string ControllerPath; - /// - /// The path fragment on the interface - /// - public string InterfacePath; - /// - /// The path fragment on the method - /// - public string MethodPath; - /// - /// The method to invoke - /// - public MethodInfo Method; - /// - /// The verbs accepted by the method - /// - public string[] Verbs; - } + { + /// + /// The controller instance to use + /// + public Controller Controller; + /// + /// The path fragment on the controller + /// + public string ControllerPath; + /// + /// The path fragment on the interface + /// + public string InterfacePath; + /// + /// The path fragment on the method + /// + public string MethodPath; + /// + /// The method to invoke + /// + public MethodInfo Method; + /// + /// The verbs accepted by the method + /// + public string[] Verbs; + } /// /// Router that can route to a set of controllers /// internal class ControllerRouter : IRouter, IHttpModule - { - /// - /// The template used to locate controllers - /// - private readonly ControllerRouterConfig m_config; - - /// - /// The route parser - /// - private readonly RouteParser m_routeparser; - - /// - /// Initializes a new instance of the class. - /// - /// The configuration to use - /// The assembly to scan for controllers. - public ControllerRouter(ControllerRouterConfig config, Assembly assembly) - : this(config, assembly == null ? new Assembly[0] : new [] { assembly }) - { - } - - /// - /// Initializes a new instance of the class. - /// - /// The configuration to use - /// The assemblies to scan for controllers. - public ControllerRouter(ControllerRouterConfig config, IEnumerable assemblies) - : this(config, assemblies.SelectMany(x => x.GetTypes()).Where(x => x != null && typeof(Controller).IsAssignableFrom(x) && !x.IsAbstract && !x.IsGenericTypeDefinition)) - { - } - - /// - /// Initializes a new instance of the class. - /// - /// The configuration to use - /// The types to use, must all derive from . - public ControllerRouter(ControllerRouterConfig config, params Type[] types) - : this(config, (types ?? new Type[0]).AsEnumerable()) - { - } - - /// - /// Initializes a new instance of the class. - /// - /// The configuration to use - /// The types to use, must all derive from . - public ControllerRouter(ControllerRouterConfig config, IEnumerable types) - { - if (types == null) - throw new ArgumentNullException($"{types}"); - if (config == null) - throw new ArgumentNullException($"{config}"); - - // Make sure the caller cannot edit the config afterwards - m_config = config.Clone(); - - var variables = new RouteParser(m_config.Template, !m_config.CaseSensitive, null).Variables; - - if (variables.Count(x => x.Key == m_config.ControllerGroupName) != 1) - throw new ArgumentException($"The template must contain exactly 1 named group called {m_config.ControllerGroupName}"); - if (variables.Count(x => x.Key == m_config.ActionGroupName) != 1) - throw new ArgumentException($"The template must contain exactly 1 named group called {m_config.ActionGroupName}"); - - types = types.Where(x => x != null).Distinct().ToArray(); - if (types.Count() == 0) - throw new ArgumentException($"Attempted to load routes from an assembly, or set of types with no routes", nameof(types)); - - var wrong = types.FirstOrDefault(x => !typeof(Controller).IsAssignableFrom(x)); - if (wrong != null) - throw new ArgumentException($"The type \"{wrong.FullName}\" does not derive from {typeof(Controller).FullName}"); + { + /// + /// The template used to locate controllers + /// + private readonly ControllerRouterConfig m_config; + + /// + /// The route parser + /// + private readonly RouteParser m_routeparser; + + /// + /// Initializes a new instance of the class. + /// + /// The configuration to use + /// The assembly to scan for controllers. + public ControllerRouter(ControllerRouterConfig config, Assembly assembly) + : this(config, assembly == null ? new Assembly[0] : new[] { assembly }) + { + } + + /// + /// Initializes a new instance of the class. + /// + /// The configuration to use + /// The assemblies to scan for controllers. + public ControllerRouter(ControllerRouterConfig config, IEnumerable assemblies) + : this(config, assemblies.SelectMany(x => x.GetTypes()).Where(x => x != null && typeof(Controller).IsAssignableFrom(x) && !x.IsAbstract && !x.IsGenericTypeDefinition)) + { + } + + /// + /// Initializes a new instance of the class. + /// + /// The configuration to use + /// The types to use, must all derive from . + public ControllerRouter(ControllerRouterConfig config, params Type[] types) + : this(config, (types ?? new Type[0]).AsEnumerable()) + { + } + + /// + /// Initializes a new instance of the class. + /// + /// The configuration to use + /// The types to use, must all derive from . + public ControllerRouter(ControllerRouterConfig config, IEnumerable types) + { + if (types == null) + throw new ArgumentNullException($"{types}"); + if (config == null) + throw new ArgumentNullException($"{config}"); + + // Make sure the caller cannot edit the config afterwards + m_config = config.Clone(); + + var variables = new RouteParser(m_config.Template, !m_config.CaseSensitive, null).Variables; + + if (variables.Count(x => x.Key == m_config.ControllerGroupName) != 1) + throw new ArgumentException($"The template must contain exactly 1 named group called {m_config.ControllerGroupName}"); + if (variables.Count(x => x.Key == m_config.ActionGroupName) != 1) + throw new ArgumentException($"The template must contain exactly 1 named group called {m_config.ActionGroupName}"); + + types = types.Where(x => x != null).Distinct().ToArray(); + if (types.Count() == 0) + throw new ArgumentException($"Attempted to load routes from an assembly, or set of types with no routes", nameof(types)); + + var wrong = types.FirstOrDefault(x => !typeof(Controller).IsAssignableFrom(x)); + if (wrong != null) + throw new ArgumentException($"The type \"{wrong.FullName}\" does not derive from {typeof(Controller).FullName}"); wrong = types.FirstOrDefault(x => x.IsAbstract || x.IsGenericTypeDefinition); if (wrong != null) throw new ArgumentException($"The type \"{wrong.FullName}\" cannot be instantiated"); m_routeparser = BuildParse(types.Select(x => (Controller)Activator.CreateInstance(x)).ToArray(), m_config); - } - - /// - /// Initializes a new instance of the class. - /// - /// The configuration to use - /// The instances to use. - public ControllerRouter(ControllerRouterConfig config, params Controller[] instances) - : this(config, (instances ?? new Controller[0]).AsEnumerable()) - { - } - - - /// - /// Initializes a new instance of the class. - /// - /// The configuration to use - /// The instances to use. - public ControllerRouter(ControllerRouterConfig config, IEnumerable instances) - { - if (instances == null || instances.Any(x => x == null)) - throw new ArgumentNullException($"{instances}"); - if (config == null) - throw new ArgumentNullException($"{config}"); - - // Make sure the caller cannot edit the config afterwards - m_config = config.Clone(); - - var variables = new RouteParser(m_config.Template, !m_config.CaseSensitive, null).Variables; - - if (variables.Count(x => x.Key == m_config.ControllerGroupName) != 1) - throw new ArgumentException($"The template must contain exactly 1 named group called {m_config.ControllerGroupName}"); - if (variables.Count(x => x.Key == m_config.ActionGroupName) != 1) - throw new ArgumentException($"The template must contain exactly 1 named group called {m_config.ActionGroupName}"); - - if (instances.Count() == 0) - throw new ArgumentException($"No instances were added as routes", nameof(instances)); - - var duplicates = instances.GroupBy(x => x.GetType()).Where(x => x.Count() > 1); - if (duplicates.Any()) - throw new ArgumentException($"The type \"{duplicates.First().Key}\" has {duplicates.First().Count()} instances"); + } + + /// + /// Initializes a new instance of the class. + /// + /// The configuration to use + /// The instances to use. + public ControllerRouter(ControllerRouterConfig config, params Controller[] instances) + : this(config, (instances ?? new Controller[0]).AsEnumerable()) + { + } + + + /// + /// Initializes a new instance of the class. + /// + /// The configuration to use + /// The instances to use. + public ControllerRouter(ControllerRouterConfig config, IEnumerable instances) + { + if (instances == null || instances.Any(x => x == null)) + throw new ArgumentNullException($"{instances}"); + if (config == null) + throw new ArgumentNullException($"{config}"); + + // Make sure the caller cannot edit the config afterwards + m_config = config.Clone(); + + var variables = new RouteParser(m_config.Template, !m_config.CaseSensitive, null).Variables; + + if (variables.Count(x => x.Key == m_config.ControllerGroupName) != 1) + throw new ArgumentException($"The template must contain exactly 1 named group called {m_config.ControllerGroupName}"); + if (variables.Count(x => x.Key == m_config.ActionGroupName) != 1) + throw new ArgumentException($"The template must contain exactly 1 named group called {m_config.ActionGroupName}"); + + if (instances.Count() == 0) + throw new ArgumentException($"No instances were added as routes", nameof(instances)); + + var duplicates = instances.GroupBy(x => x.GetType()).Where(x => x.Count() > 1); + if (duplicates.Any()) + throw new ArgumentException($"The type \"{duplicates.First().Key}\" has {duplicates.First().Count()} instances"); m_routeparser = BuildParse(instances, m_config); - } - - /// - /// Creates partial routes for all controllers in the sequence - /// - /// The controllers to create partial routes for - /// The configuration to use - /// The partial routes - public static PartialParsedRoute[] ParseControllers(IEnumerable controllers, ControllerRouterConfig config) - { - var controller_routes = controllers - .Where(x => !(x is ManualRoutingController)) - .SelectMany(x => - { - string name; - var nameattr = x.GetType().SearchCustomAttributes().Cast().FirstOrDefault(); - // Extract controller name - if (nameattr != null) - name = nameattr.Name; - else - { - name = x.GetType().Name; - if (config.ControllerSuffixRemovals != null) - foreach (var rm in config.ControllerSuffixRemovals) - while (!string.IsNullOrWhiteSpace(rm) && name.EndsWith(rm, StringComparison.InvariantCultureIgnoreCase)) - name = name.Substring(0, name.Length - rm.Length); - - if (config.LowerCaseNames) - name = name.ToLowerInvariant(); - } - - var routes = x.GetType().SearchCustomAttributes().Cast().Select(y => y.Route); - - // Add default route, if there are no route attributes - if (routes.Count() == 0) - routes = new[] { string.Empty }; - - return routes.Distinct().Select(y => new - { - Controller = x, - ControllerRoute = y - }); - } - ).ToArray(); - - var interface_expanded_routes = - controller_routes.SelectMany(x => - { - var interfaces = x.Controller.GetType().GetParentInterfaces(); - var interfacenames = interfaces - .Select(y => x.Controller.GetType().GetParentInterfaceSequence(y).Reverse().Where(z => z != x.Controller.GetType() && z != typeof(IControllerPrefix))) - .Select(y => string.Join("/", y.Select(z => z.GetItemName(config)))); - - if (interfacenames.Count() == 0) - interfacenames = new[] { string.Empty }; - - return interfacenames.Distinct().Select(y => new - { - Controller = x.Controller, - ControllerRoute = x.ControllerRoute, - InterfacePath = (y ?? string.Empty) - }); + } + + /// + /// Creates partial routes for all controllers in the sequence + /// + /// The controllers to create partial routes for + /// The configuration to use + /// The partial routes + public static PartialParsedRoute[] ParseControllers(IEnumerable controllers, ControllerRouterConfig config) + { + var controller_routes = controllers + .Where(x => !(x is ManualRoutingController)) + .SelectMany(x => + { + string name; + var nameattr = x.GetType().SearchCustomAttributes().Cast().FirstOrDefault(); + // Extract controller name + if (nameattr != null) + name = nameattr.Name; + else + { + name = x.GetType().Name; + if (config.ControllerSuffixRemovals != null) + foreach (var rm in config.ControllerSuffixRemovals) + while (!string.IsNullOrWhiteSpace(rm) && name.EndsWith(rm, StringComparison.InvariantCultureIgnoreCase)) + name = name.Substring(0, name.Length - rm.Length); + + if (config.LowerCaseNames) + name = name.ToLowerInvariant(); + } + + var routes = x.GetType().SearchCustomAttributes().Cast().Select(y => y.Route); + + // Add default route, if there are no route attributes + if (routes.Count() == 0) + routes = new[] { string.Empty }; + + return routes.Distinct().Select(y => new + { + Controller = x, + ControllerRoute = y + }); + } + ).ToArray(); + + var interface_expanded_routes = + controller_routes.SelectMany(x => + { + var interfaces = x.Controller.GetType().GetParentInterfaces(); + var interfacenames = interfaces + .Select(y => x.Controller.GetType().GetParentInterfaceSequence(y).Reverse().Where(z => z != x.Controller.GetType() && z != typeof(IControllerPrefix))) + .Select(y => string.Join("/", y.Select(z => z.GetItemName(config)))); + + if (interfacenames.Count() == 0) + interfacenames = new[] { string.Empty }; + + return interfacenames.Distinct().Select(y => new + { + Controller = x.Controller, + ControllerRoute = x.ControllerRoute, + InterfacePath = (y ?? string.Empty) + }); } ).ToArray(); - var target_method_routes = - interface_expanded_routes.SelectMany(x => - { - return - x.Controller.GetType() - .GetMethods(BindingFlags.Public | BindingFlags.Instance) - // Only target the methods that return something useful - .Where(y => - y.ReturnType == typeof(void) - || typeof(IResult).IsAssignableFrom(y.ReturnType) - || typeof(Task).IsAssignableFrom(y.ReturnType) - ) - // Remove properties and others - .Where(y => !y.IsSpecialName) - .Select(y => new - { - Controller = x.Controller, - ControllerRoute = x.ControllerRoute, - InterfacePath = x.InterfacePath, - Method = y - }); - } + var target_method_routes = + interface_expanded_routes.SelectMany(x => + { + return + x.Controller.GetType() + .GetMethods(BindingFlags.Public | BindingFlags.Instance) + // Only target the methods that return something useful + .Where(y => + y.ReturnType == typeof(void) + || typeof(IResult).IsAssignableFrom(y.ReturnType) + || typeof(Task).IsAssignableFrom(y.ReturnType) + ) + // Remove properties and others + .Where(y => !y.IsSpecialName) + .Select(y => new + { + Controller = x.Controller, + ControllerRoute = x.ControllerRoute, + InterfacePath = x.InterfacePath, + Method = y + }); + } ).ToArray(); - return - target_method_routes.SelectMany(x => - { - var routes = x.Method.SearchCustomAttributes().Cast().Select(y => y.Route); - - // Add default route, if there are no route attributes - if (routes.Count() == 0) - routes = new[] { string.Empty }; - - // Get any accepted verbs - var verbs = x.Method.SearchCustomAttributes().Cast().Select(b => b.Verb.ToUpperInvariant()).ToArray(); - - return routes.Select(y => new PartialParsedRoute() - { - Controller = x.Controller, - ControllerPath = x.ControllerRoute, - InterfacePath = x.InterfacePath, - Method = x.Method, - MethodPath = y, - Verbs = verbs - }); - } - ) - .ToArray(); - } - - private static RouteParser BuildParse(IEnumerable controllers, ControllerRouterConfig config) - { - var target_routes = - ParseControllers(controllers, config) - - // Attach custom controller routes - .Concat( - controllers.OfType().SelectMany(x => x.Routes) - ) - .ToArray(); - - // Now we have the cartesian product of all route/controller/action pairs, then build the target strings - var tmp = new RouteParser(config.Template, !config.CaseSensitive, null); - var defaultcontrollername = tmp.GetDefaultValue(config.ControllerGroupName); - var defaultactionname = tmp.GetDefaultValue(config.ActionGroupName); - - var target_strings = - target_routes.SelectMany(x => - { - // Provide a hook point for the dynamic routing option - if (x.Controller is IIDynamicConfiguredController idc) - x = idc.PatchRoute(x); - - var entry = new RouteEntry(x.Controller, x.Method, x.Verbs, null); - - var path = new RouteParser("/", !config.CaseSensitive, entry); - - if (!string.IsNullOrWhiteSpace(x.InterfacePath)) - { - if (x.InterfacePath.StartsWith("/", StringComparison.Ordinal)) - path = new RouteParser(x.InterfacePath, !config.CaseSensitive, entry); - else - path = path.Append(x.InterfacePath, !config.CaseSensitive, entry); - } - - var ct = string.IsNullOrWhiteSpace(x.ControllerPath) ? config.Template : x.ControllerPath; - - if (!string.IsNullOrWhiteSpace(ct)) - { - if (ct.StartsWith("/", StringComparison.Ordinal)) - path = new RouteParser(ct, !config.CaseSensitive, entry); - else - { - if (!path.Path.EndsWith("/", StringComparison.Ordinal)) - ct = "/" + ct; - path = path.Append(ct, !config.CaseSensitive, entry); - } - } - - var mt = x.MethodPath; - if (!string.IsNullOrWhiteSpace(mt)) - { - if (mt.StartsWith("/", StringComparison.Ordinal)) - path = new RouteParser(mt, !config.CaseSensitive, entry); - else - { - path = path.Bind(config.ActionGroupName, string.Empty, !config.CaseSensitive, true); - if (!path.Path.EndsWith("/", StringComparison.Ordinal)) - mt = "/" + mt; - - path = path.Append(mt, !config.CaseSensitive, entry); - } - } - - var controllername = x.Controller.GetType().GetItemName(config); - var actionname = x.Method.GetItemName(config); - - var controllernames = new List(); - var actionnames = new List(); - - if (!config.HideDefaultController || controllername != defaultcontrollername) - controllernames.Add(controllername); - if (!config.HideDefaultAction || actionname != defaultactionname) - actionnames.Add(actionname); - if (!string.IsNullOrEmpty(defaultcontrollername) && controllername == defaultcontrollername) - controllernames.Add(string.Empty); - if (!string.IsNullOrEmpty(defaultactionname) && actionname == defaultactionname) - actionnames.Add(string.Empty); - - // Cartesian product with controller and action names bound - return controllernames - .SelectMany(y => actionnames.Select( - z => path - .Bind(config.ControllerGroupName, y, !config.CaseSensitive, true) - .Bind(config.ActionGroupName, z, !config.CaseSensitive, true) - .PrunePath() - .ReplaceTarget(x.Controller, x.Method, x.Verbs) - ) - ); - } - ) + return + target_method_routes.SelectMany(x => + { + var routes = x.Method.SearchCustomAttributes().Cast().Select(y => y.Route); + + // Add default route, if there are no route attributes + if (routes.Count() == 0) + routes = new[] { string.Empty }; + + // Get any accepted verbs + var verbs = x.Method.SearchCustomAttributes().Cast().Select(b => b.Verb.ToUpperInvariant()).ToArray(); + + return routes.Select(y => new PartialParsedRoute() + { + Controller = x.Controller, + ControllerPath = x.ControllerRoute, + InterfacePath = x.InterfacePath, + Method = x.Method, + MethodPath = y, + Verbs = verbs + }); + } + ) + .ToArray(); + } + + private static RouteParser BuildParse(IEnumerable controllers, ControllerRouterConfig config) + { + var target_routes = + ParseControllers(controllers, config) + + // Attach custom controller routes + .Concat( + controllers.OfType().SelectMany(x => x.Routes) + ) + .ToArray(); + + // Now we have the cartesian product of all route/controller/action pairs, then build the target strings + var tmp = new RouteParser(config.Template, !config.CaseSensitive, null); + var defaultcontrollername = tmp.GetDefaultValue(config.ControllerGroupName); + var defaultactionname = tmp.GetDefaultValue(config.ActionGroupName); + + var target_strings = + target_routes.SelectMany(x => + { + // Provide a hook point for the dynamic routing option + if (x.Controller is IIDynamicConfiguredController idc) + x = idc.PatchRoute(x); + + var entry = new RouteEntry(x.Controller, x.Method, x.Verbs, null); + + var path = new RouteParser("/", !config.CaseSensitive, entry); + + if (!string.IsNullOrWhiteSpace(x.InterfacePath)) + { + if (x.InterfacePath.StartsWith("/", StringComparison.Ordinal)) + path = new RouteParser(x.InterfacePath, !config.CaseSensitive, entry); + else + path = path.Append(x.InterfacePath, !config.CaseSensitive, entry); + } + + var ct = string.IsNullOrWhiteSpace(x.ControllerPath) ? config.Template : x.ControllerPath; + + if (!string.IsNullOrWhiteSpace(ct)) + { + if (ct.StartsWith("/", StringComparison.Ordinal)) + path = new RouteParser(ct, !config.CaseSensitive, entry); + else + { + if (!path.Path.EndsWith("/", StringComparison.Ordinal)) + ct = "/" + ct; + path = path.Append(ct, !config.CaseSensitive, entry); + } + } + + var mt = x.MethodPath; + if (!string.IsNullOrWhiteSpace(mt)) + { + if (mt.StartsWith("/", StringComparison.Ordinal)) + path = new RouteParser(mt, !config.CaseSensitive, entry); + else + { + path = path.Bind(config.ActionGroupName, string.Empty, !config.CaseSensitive, true); + if (!path.Path.EndsWith("/", StringComparison.Ordinal)) + mt = "/" + mt; + + path = path.Append(mt, !config.CaseSensitive, entry); + } + } + + var controllername = x.Controller.GetType().GetItemName(config); + var actionname = x.Method.GetItemName(config); + + var controllernames = new List(); + var actionnames = new List(); + + if (!config.HideDefaultController || controllername != defaultcontrollername) + controllernames.Add(controllername); + if (!config.HideDefaultAction || actionname != defaultactionname) + actionnames.Add(actionname); + if (!string.IsNullOrEmpty(defaultcontrollername) && controllername == defaultcontrollername) + controllernames.Add(string.Empty); + if (!string.IsNullOrEmpty(defaultactionname) && actionname == defaultactionname) + actionnames.Add(string.Empty); + + // Cartesian product with controller and action names bound + return controllernames + .SelectMany(y => actionnames.Select( + z => path + .Bind(config.ControllerGroupName, y, !config.CaseSensitive, true) + .Bind(config.ActionGroupName, z, !config.CaseSensitive, true) + .PrunePath() + .ReplaceTarget(x.Controller, x.Method, x.Verbs) + ) + ); + } + ) .Distinct(x => x.ToString()) - .ToArray(); + .ToArray(); - var merged = RouteParser.Merge(target_strings); + var merged = RouteParser.Merge(target_strings); - if (config.Debug) - { - Console.WriteLine("All target paths:"); - foreach (var x in target_strings) - Console.WriteLine(x); + if (config.Debug) + { + Console.WriteLine("All target paths:"); + foreach (var x in target_strings) + Console.WriteLine(x); - Console.WriteLine("Map structure:"); - Console.WriteLine(merged.ToString()); - } + Console.WriteLine("Map structure:"); + Console.WriteLine(merged.ToString()); + } - return merged; - } + return merged; + } /// /// Handles a request @@ -726,9 +726,9 @@ private static RouteParser BuildParse(IEnumerable controllers, Contr /// The exexcution context. /// The token indicating to stop handling. public Task HandleAsync(IHttpContext context, CancellationToken cancellationToken) - { - return Process(context, cancellationToken); - } + { + return Process(context, cancellationToken); + } /// /// Attempts to route the request to a controller instance. @@ -736,58 +736,58 @@ public Task HandleAsync(IHttpContext context, CancellationToken cancellati /// The exexcution context. /// The token indicating to stop handling. public async Task Process(IHttpContext context, CancellationToken cancellationToken) - { - var anymatches = false; - var test = m_routeparser - .MatchRequest(context.Request.Path) - .Where(x => { anymatches = true; return x.Key.AcceptsVerb(context.Request.Method); }) - .OrderBy(x => x.Value.Count) - .ToList(); - - // If we do not handle this entry, pass the request down the stack - if (!anymatches) - return false; - - // If we filtered all targets based on verb, - // we are handling the path, but the verb is not allowed - if (test.Count == 0) - { - context.Response.StatusCode = HttpStatusCode.MethodNotAllowed; - context.Response.StatusMessage = HttpStatusMessages.DefaultMessage(HttpStatusCode.MethodNotAllowed); - return true; - } - - var handler = test.First(); - await HandleWithMethod(context, handler.Key.Action, handler.Key.Controller, handler.Value); - return true; - } - - /// - /// Handles the actual method invocation, once a method has been selected - /// - /// The awaitable task. - /// The execution context. - /// The method to invoke. - /// The controller instance to use. - /// The parent url match - private async Task HandleWithMethod(IHttpContext context, MethodEntry method, Controller controller, Dictionary urlmatch) - { - // Make sure dependencies are met - if (controller != null) - context.Request.RequireHandler(controller.GetType().SearchCustomAttributes()); - context.Request.RequireHandler(method.Method.SearchCustomAttributes()); - - // Apply each argument in turn - var values = new object[method.ArgumentCount]; + { + var anymatches = false; + var test = m_routeparser + .MatchRequest(context.Request.Path) + .Where(x => { anymatches = true; return x.Key.AcceptsVerb(context.Request.Method); }) + .OrderBy(x => x.Value.Count) + .ToList(); + + // If we do not handle this entry, pass the request down the stack + if (!anymatches) + return false; + + // If we filtered all targets based on verb, + // we are handling the path, but the verb is not allowed + if (test.Count == 0) + { + context.Response.StatusCode = HttpStatusCode.MethodNotAllowed; + context.Response.StatusMessage = HttpStatusMessages.DefaultMessage(HttpStatusCode.MethodNotAllowed); + return true; + } + + var handler = test.First(); + await HandleWithMethod(context, handler.Key.Action, handler.Key.Controller, handler.Value); + return true; + } + + /// + /// Handles the actual method invocation, once a method has been selected + /// + /// The awaitable task. + /// The execution context. + /// The method to invoke. + /// The controller instance to use. + /// The parent url match + private async Task HandleWithMethod(IHttpContext context, MethodEntry method, Controller controller, Dictionary urlmatch) + { + // Make sure dependencies are met + if (controller != null) + context.Request.RequireHandler(controller.GetType().SearchCustomAttributes()); + context.Request.RequireHandler(method.Method.SearchCustomAttributes()); + + // Apply each argument in turn + var values = new object[method.ArgumentCount]; var hasreadbody = false; - foreach (var m in urlmatch) - context.Request.RequestState[m.Key] = m.Value; + foreach (var m in urlmatch) + context.Request.RequestState[m.Key] = m.Value; - for (var ix = 0; ix < values.Length; ix++) - { - var e = method.Parameters[ix]; - string val; + for (var ix = 0; ix < values.Length; ix++) + { + var e = method.Parameters[ix]; + string val; IMultipartItem file; if (typeof(IHttpContext).IsAssignableFrom(e.Parameter.ParameterType)) @@ -813,57 +813,57 @@ private async Task HandleWithMethod(IHttpContext context, MethodEntry method, Co var str = await RequestUtility.ReadAllAsStringAsync(context.Request.Body, RequestUtility.GetEncodingForContentType(context.Request.ContentType), context.Request.TimeoutCancellationToken); ApplyArgument(method.Method, e, str, values); } - else if (e.Required) - throw new HttpException(HttpStatusCode.BadRequest, $"Missing mandatory parameter {e.Name}"); - else if (e.Parameter.HasDefaultValue) - values[e.ArgumentIndex] = e.Parameter.DefaultValue; - else - values[e.ArgumentIndex] = e.Parameter.ParameterType.IsValueType ? Activator.CreateInstance(e.Parameter.ParameterType) : null; - - // Provide the bound variables to the processing module - if (!e.IsContextParameter) - context.Request.RequestState[e.Name] = values[e.ArgumentIndex]; - } - - var res = method.Method.Invoke(controller, values); - if (res == null) - return; - - if (res is IResult) - await((IResult)res).Execute(context); - else if (res is Task) - { - res = await(Task)res; - if (res as IResult != null) - await((IResult)res).Execute(context); - } - else if (res is Task) - await(Task)res; - } - - /// - /// Applies the argument to the value list. - /// - /// The argument entry. - /// The method to apply to. - /// The argument value. - /// The list of values to process. - private static void ApplyArgument(MethodInfo method, ParameterEntry entry, string value, object[] values) - { - var argtype = method.GetParameters()[entry.ArgumentIndex].ParameterType; - try - { - if (argtype.IsEnum) - values[entry.ArgumentIndex] = Enum.Parse(argtype, value, true); + else if (e.Required) + throw new HttpException(HttpStatusCode.BadRequest, $"Missing mandatory parameter {e.Name}"); + else if (e.Parameter.HasDefaultValue) + values[e.ArgumentIndex] = e.Parameter.DefaultValue; + else + values[e.ArgumentIndex] = e.Parameter.ParameterType.IsValueType ? Activator.CreateInstance(e.Parameter.ParameterType) : null; + + // Provide the bound variables to the processing module + if (!e.IsContextParameter) + context.Request.RequestState[e.Name] = values[e.ArgumentIndex]; + } + + var res = method.Method.Invoke(controller, values); + if (res == null) + return; + + if (res is IResult) + await ((IResult)res).Execute(context); + else if (res is Task) + { + res = await (Task)res; + if (res as IResult != null) + await ((IResult)res).Execute(context); + } + else if (res is Task) + await (Task)res; + } + + /// + /// Applies the argument to the value list. + /// + /// The argument entry. + /// The method to apply to. + /// The argument value. + /// The list of values to process. + private static void ApplyArgument(MethodInfo method, ParameterEntry entry, string value, object[] values) + { + var argtype = method.GetParameters()[entry.ArgumentIndex].ParameterType; + try + { + if (argtype.IsEnum) + values[entry.ArgumentIndex] = Enum.Parse(argtype, value, true); else if (argtype.IsPrimitive || argtype == typeof(string)) values[entry.ArgumentIndex] = Convert.ChangeType(value, argtype); else values[entry.ArgumentIndex] = JsonSerializer.Deserialize(value, argtype); - } - catch (Exception) - { - throw new HttpException(HttpStatusCode.BadRequest, $"The value \"{value}\" for {entry.Name} is not a valid {argtype.Name.ToLower()}"); - } - } - } + } + catch (Exception) + { + throw new HttpException(HttpStatusCode.BadRequest, $"The value \"{value}\" for {entry.Name} is not a valid {argtype.Name.ToLower()}"); + } + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Mvc/ControllerRouterConfig.cs b/libraries/MTConnect.NET-HTTP/Ceen/Mvc/ControllerRouterConfig.cs index 9918fdda5..fdd771c77 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Mvc/ControllerRouterConfig.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Mvc/ControllerRouterConfig.cs @@ -9,122 +9,122 @@ namespace Ceen.Mvc /// The configuration for a controller router /// internal class ControllerRouterConfig - { - /// - /// The default routing template - /// - public const string DEFAULT_ROUTING_TEMPLATE = @"{controller}/{action=index}"; - - /// - /// Gets or sets the name of the controller group in the template. - /// - public string ControllerGroupName { get; set; } = "controller"; - - /// - /// Gets or sets the name of the action group in the template. - /// - public string ActionGroupName { get; set; } = "action"; - - /// - /// The template used to locate controllers - /// - public string Template { get; set; } = DEFAULT_ROUTING_TEMPLATE; - - /// - /// Gets or sets a value indicating whether controller matches are case-sensitive. - /// - public bool CaseSensitive { get; set; } = false; - - /// - /// Gets or sets a value indicating whether controller treats all names as lower-case. - /// - public bool LowerCaseNames { get; set; } = true; - - /// - /// Gets a value indicating if the default controller, if any, cannot be adressed explicitly - /// - public bool HideDefaultController { get; set; } = true; - - /// - /// Gets a value indicating if the default action, if any, cannot be adressed explicitly - /// - public bool HideDefaultAction { get; set; } = true; - - /// - /// Gets or sets the suffixes to remove from the default controller names - /// - public string[] ControllerSuffixRemovals { get; set; } = new string[] { "Controller", "Handler" }; - - /// - /// Gets or sets the suffixes to remove from the default controller names - /// - public string[] ControllerPrefixRemovals { get; set; } = new string[] { }; - - /// - /// Gets or sets the suffixes to remove from the default interface names - /// - public string[] InterfaceSuffixRemovals { get; set; } = new string[] { }; - - /// - /// Gets or sets the suffixes to remove from the default interface names - /// - public string[] InterfacePrefixRemovals { get; set; } = new string[] { "I" }; - - /// - /// Gets or sets a value indicating whether this is emitting debug information. - /// - public bool Debug { get; set; } = false; - - /// - /// Initializes a new instance of the class. - /// - /// The default controller to use. - /// The default action to use. - public ControllerRouterConfig(Type defaultController = null, string defaultAction = "index", bool lowerCaseNames = true) - { - LowerCaseNames = lowerCaseNames; - - var sb = new StringBuilder(); - if (defaultController == null) - sb.Append($"{{{ControllerGroupName}}}"); - else - { - string name; - var attr = defaultController.GetCustomAttributes(typeof(NameAttribute), false).Cast().FirstOrDefault(); - if (attr != null) - name = attr.Name; - else - { - name = defaultController.Name; - if (ControllerSuffixRemovals != null) - foreach (var rm in ControllerSuffixRemovals) - while (!string.IsNullOrWhiteSpace(rm) && name.EndsWith(rm, StringComparison.InvariantCultureIgnoreCase)) - name = name.Substring(0, name.Length - rm.Length); - - if (LowerCaseNames) - name = name.ToLowerInvariant(); - } - - sb.Append($"{{{ControllerGroupName}={name}}}"); - } - - sb.Append("/"); - - if (string.IsNullOrWhiteSpace(defaultAction)) - sb.Append($"{{{ActionGroupName}}}"); - else - sb.Append($"{{{ActionGroupName}={defaultAction}}}"); - - Template = sb.ToString(); - } - - /// - /// Creates a copy of this instance - /// - internal ControllerRouterConfig Clone() - { - return (ControllerRouterConfig)this.MemberwiseClone(); - } - - } + { + /// + /// The default routing template + /// + public const string DEFAULT_ROUTING_TEMPLATE = @"{controller}/{action=index}"; + + /// + /// Gets or sets the name of the controller group in the template. + /// + public string ControllerGroupName { get; set; } = "controller"; + + /// + /// Gets or sets the name of the action group in the template. + /// + public string ActionGroupName { get; set; } = "action"; + + /// + /// The template used to locate controllers + /// + public string Template { get; set; } = DEFAULT_ROUTING_TEMPLATE; + + /// + /// Gets or sets a value indicating whether controller matches are case-sensitive. + /// + public bool CaseSensitive { get; set; } = false; + + /// + /// Gets or sets a value indicating whether controller treats all names as lower-case. + /// + public bool LowerCaseNames { get; set; } = true; + + /// + /// Gets a value indicating if the default controller, if any, cannot be adressed explicitly + /// + public bool HideDefaultController { get; set; } = true; + + /// + /// Gets a value indicating if the default action, if any, cannot be adressed explicitly + /// + public bool HideDefaultAction { get; set; } = true; + + /// + /// Gets or sets the suffixes to remove from the default controller names + /// + public string[] ControllerSuffixRemovals { get; set; } = new string[] { "Controller", "Handler" }; + + /// + /// Gets or sets the suffixes to remove from the default controller names + /// + public string[] ControllerPrefixRemovals { get; set; } = new string[] { }; + + /// + /// Gets or sets the suffixes to remove from the default interface names + /// + public string[] InterfaceSuffixRemovals { get; set; } = new string[] { }; + + /// + /// Gets or sets the suffixes to remove from the default interface names + /// + public string[] InterfacePrefixRemovals { get; set; } = new string[] { "I" }; + + /// + /// Gets or sets a value indicating whether this is emitting debug information. + /// + public bool Debug { get; set; } = false; + + /// + /// Initializes a new instance of the class. + /// + /// The default controller to use. + /// The default action to use. + public ControllerRouterConfig(Type defaultController = null, string defaultAction = "index", bool lowerCaseNames = true) + { + LowerCaseNames = lowerCaseNames; + + var sb = new StringBuilder(); + if (defaultController == null) + sb.Append($"{{{ControllerGroupName}}}"); + else + { + string name; + var attr = defaultController.GetCustomAttributes(typeof(NameAttribute), false).Cast().FirstOrDefault(); + if (attr != null) + name = attr.Name; + else + { + name = defaultController.Name; + if (ControllerSuffixRemovals != null) + foreach (var rm in ControllerSuffixRemovals) + while (!string.IsNullOrWhiteSpace(rm) && name.EndsWith(rm, StringComparison.InvariantCultureIgnoreCase)) + name = name.Substring(0, name.Length - rm.Length); + + if (LowerCaseNames) + name = name.ToLowerInvariant(); + } + + sb.Append($"{{{ControllerGroupName}={name}}}"); + } + + sb.Append("/"); + + if (string.IsNullOrWhiteSpace(defaultAction)) + sb.Append($"{{{ActionGroupName}}}"); + else + sb.Append($"{{{ActionGroupName}={defaultAction}}}"); + + Template = sb.ToString(); + } + + /// + /// Creates a copy of this instance + /// + internal ControllerRouterConfig Clone() + { + return (ControllerRouterConfig)this.MemberwiseClone(); + } + + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Mvc/LookupEntries.cs b/libraries/MTConnect.NET-HTTP/Ceen/Mvc/LookupEntries.cs index bcfa925a5..c7c53c7df 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Mvc/LookupEntries.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Mvc/LookupEntries.cs @@ -7,176 +7,176 @@ namespace Ceen.Mvc { - /// - /// Encapsulation of a method parameter - /// - internal struct ParameterEntry - { - /// - /// The index of the argument in the method - /// - public readonly int ArgumentIndex; - - /// - /// The name of the parameter - /// - public readonly string Name; - - /// - /// Indicating if the value is required - /// - public readonly bool Required; - - /// - /// The allowed sources for the parameter - /// - public readonly ParameterSource Source; - /// - /// The wrapped parameter - /// - public readonly ParameterInfo Parameter; - - /// - /// A flag indicating if this parameter gets a context-like argument - /// - public readonly bool IsContextParameter; - - /// - /// Initializes a new instance of the struct. - /// - /// The parameter to represent. - /// The argument index in the method. - /// The parameter name - /// The allowed parameter sources - /// A flag indicating if the parameter is required - public ParameterEntry(ParameterInfo par, string name, ParameterSource source, bool required, int index) - { - Parameter = par; - ArgumentIndex = index; - Name = name; - Source = source; - IsContextParameter = par.ParameterType == typeof(IHttpContext) || par.ParameterType == typeof(IHttpRequestInternal) || par.ParameterType == typeof(IHttpResponse); - Required = required; - } - } - - /// - /// Encapsulation for a method - /// - internal struct MethodEntry - { - /// - /// The wrapped method - /// - public readonly MethodInfo Method; - /// - /// The number of arguments - /// - public readonly int ArgumentCount; - /// - /// The list of method parameters - /// - public readonly ParameterEntry[] Parameters; - - /// - /// Initializes a new instance of the struct. - /// - /// The method to wrap. - /// The variables to include - public MethodEntry(MethodInfo method, IEnumerable> variables) - { - Method = method; - ArgumentCount = method.GetParameters().Length; - - var urlargs = (variables ?? new KeyValuePair[0]).ToLookup(x => x.Key, x => x.Value); - - var i = 0; - Parameters = Method - .GetParameters() - .Select(par => - { - var name_attr = par.GetCustomAttributes(typeof(NameAttribute), false).Cast().FirstOrDefault(); - var name = name_attr == null || string.IsNullOrWhiteSpace(name_attr.Name) ? par.Name : name_attr.Name; - - var par_attr = par.GetCustomAttributes(typeof(ParameterAttribute), false).Cast().FirstOrDefault(); - ParameterSource source; - bool optional; - - if (par_attr == null) - { - if (urlargs.Contains(name)) - { - source = ParameterSource.Url; - optional = urlargs[name].First(); - } - else - { - source = ParameterSource.Default; - optional = par.HasDefaultValue; - } - } - else - { - source = par_attr.Source; - optional = !par_attr.Required; + /// + /// Encapsulation of a method parameter + /// + internal struct ParameterEntry + { + /// + /// The index of the argument in the method + /// + public readonly int ArgumentIndex; + + /// + /// The name of the parameter + /// + public readonly string Name; + + /// + /// Indicating if the value is required + /// + public readonly bool Required; + + /// + /// The allowed sources for the parameter + /// + public readonly ParameterSource Source; + /// + /// The wrapped parameter + /// + public readonly ParameterInfo Parameter; + + /// + /// A flag indicating if this parameter gets a context-like argument + /// + public readonly bool IsContextParameter; + + /// + /// Initializes a new instance of the struct. + /// + /// The parameter to represent. + /// The argument index in the method. + /// The parameter name + /// The allowed parameter sources + /// A flag indicating if the parameter is required + public ParameterEntry(ParameterInfo par, string name, ParameterSource source, bool required, int index) + { + Parameter = par; + ArgumentIndex = index; + Name = name; + Source = source; + IsContextParameter = par.ParameterType == typeof(IHttpContext) || par.ParameterType == typeof(IHttpRequestInternal) || par.ParameterType == typeof(IHttpResponse); + Required = required; + } + } + + /// + /// Encapsulation for a method + /// + internal struct MethodEntry + { + /// + /// The wrapped method + /// + public readonly MethodInfo Method; + /// + /// The number of arguments + /// + public readonly int ArgumentCount; + /// + /// The list of method parameters + /// + public readonly ParameterEntry[] Parameters; + + /// + /// Initializes a new instance of the struct. + /// + /// The method to wrap. + /// The variables to include + public MethodEntry(MethodInfo method, IEnumerable> variables) + { + Method = method; + ArgumentCount = method.GetParameters().Length; + + var urlargs = (variables ?? new KeyValuePair[0]).ToLookup(x => x.Key, x => x.Value); + + var i = 0; + Parameters = Method + .GetParameters() + .Select(par => + { + var name_attr = par.GetCustomAttributes(typeof(NameAttribute), false).Cast().FirstOrDefault(); + var name = name_attr == null || string.IsNullOrWhiteSpace(name_attr.Name) ? par.Name : name_attr.Name; + + var par_attr = par.GetCustomAttributes(typeof(ParameterAttribute), false).Cast().FirstOrDefault(); + ParameterSource source; + bool optional; + + if (par_attr == null) + { + if (urlargs.Contains(name)) + { + source = ParameterSource.Url; + optional = urlargs[name].First(); + } + else + { + source = ParameterSource.Default; + optional = par.HasDefaultValue; + } + } + else + { + source = par_attr.Source; + optional = !par_attr.Required; if (!string.IsNullOrWhiteSpace(par_attr.Name)) name = par_attr.Name; - } - - var pe = new ParameterEntry(par, name, source, !optional, i); - - i++; - - return pe; - }) - .ToArray();; - } - - } - - internal class RouteEntry - { - /// - /// The controller for this entry - /// - public readonly Controller Controller; - /// - /// The method for this entry - /// - public readonly MethodEntry Action; - /// - /// The HTTP verbs for this method - /// - public readonly string[] Verbs; - /// - /// Gets a value indicating whether this accepts all verbs. - /// - /// true if accepts all verbs; otherwise, false. - public bool AcceptsAllVerbs { get { return Verbs == null || Verbs.Length == 0; } } - - /// - /// Checks if this route accepts the given verb - /// - /// true, if verb was accepted, false otherwise. - /// The verb to test. - public bool AcceptsVerb(string verb) - { - return AcceptsAllVerbs || Verbs.Contains(verb, StringComparer.Ordinal); - } - - /// - /// Initializes a new instance of the class. - /// - /// The controller for this entry. - /// The action for this entry. - /// The HTTP verbs. - /// The variables to include - public RouteEntry(Controller controller, MethodInfo action, string[] verbs, IEnumerable> variables) - { - Controller = controller; - Action = new MethodEntry(action, variables); - Verbs = verbs; - } - - } + } + + var pe = new ParameterEntry(par, name, source, !optional, i); + + i++; + + return pe; + }) + .ToArray(); ; + } + + } + + internal class RouteEntry + { + /// + /// The controller for this entry + /// + public readonly Controller Controller; + /// + /// The method for this entry + /// + public readonly MethodEntry Action; + /// + /// The HTTP verbs for this method + /// + public readonly string[] Verbs; + /// + /// Gets a value indicating whether this accepts all verbs. + /// + /// true if accepts all verbs; otherwise, false. + public bool AcceptsAllVerbs { get { return Verbs == null || Verbs.Length == 0; } } + + /// + /// Checks if this route accepts the given verb + /// + /// true, if verb was accepted, false otherwise. + /// The verb to test. + public bool AcceptsVerb(string verb) + { + return AcceptsAllVerbs || Verbs.Contains(verb, StringComparer.Ordinal); + } + + /// + /// Initializes a new instance of the class. + /// + /// The controller for this entry. + /// The action for this entry. + /// The HTTP verbs. + /// The variables to include + public RouteEntry(Controller controller, MethodInfo action, string[] verbs, IEnumerable> variables) + { + Controller = controller; + Action = new MethodEntry(action, variables); + Verbs = verbs; + } + + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Mvc/ManualRoutingController.cs b/libraries/MTConnect.NET-HTTP/Ceen/Mvc/ManualRoutingController.cs index 3994707de..4dac3763a 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Mvc/ManualRoutingController.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Mvc/ManualRoutingController.cs @@ -203,13 +203,13 @@ public ManualRoutingController Wire(Controller instance, string path, string met var delegatetype = System.Linq.Expressions.Expression.GetDelegateType( m.GetParameters().Select(x => x.ParameterType) - .Concat(new [] { m.ReturnType }) + .Concat(new[] { m.ReturnType }) .ToArray() ); // Clear this to avoid weird logic where Wire can reference an older WireWith Current = null; - return AddDelegateRoute(path, Delegate.CreateDelegate(delegatetype, instance, m, true)); + return AddDelegateRoute(path, Delegate.CreateDelegate(delegatetype, instance, m, true)); } /// @@ -283,8 +283,9 @@ public ManualRoutingController WireController(Controller instance, string prefix config = config ?? new ControllerRouterConfig(); // Extract all target methods, but remove their controller and interface fragments - foreach(var r in ControllerRouter.ParseControllers(new [] { instance }, config)) - AddRoute(new PartialParsedRoute() { + foreach (var r in ControllerRouter.ParseControllers(new[] { instance }, config)) + AddRoute(new PartialParsedRoute() + { InterfacePath = prefix, ControllerPath = controllerpath ?? $"{{{config.ActionGroupName}=index}}", Controller = r.Controller, diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Mvc/Results.cs b/libraries/MTConnect.NET-HTTP/Ceen/Mvc/Results.cs index 8a1e3e409..294792f7d 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Mvc/Results.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Mvc/Results.cs @@ -7,136 +7,136 @@ namespace Ceen.Mvc /// Interface for describing the result of an invocation. /// internal interface IResult - { - Task Execute(IHttpContext context); - } + { + Task Execute(IHttpContext context); + } /// /// Interface for representing a simple status response without content /// internal interface IStatusCodeResult : IResult - { - /// - /// Gets the status code. - /// - HttpStatusCode StatusCode { get; } + { + /// + /// Gets the status code. + /// + HttpStatusCode StatusCode { get; } - /// - /// Gets the status message. - /// - string StatusMessage { get; } - } + /// + /// Gets the status message. + /// + string StatusMessage { get; } + } /// /// Result wrapper for providing a status code result /// internal struct StatusCodeResult : IStatusCodeResult - { - /// - /// Gets the status code. - /// - /// The status code. - public HttpStatusCode StatusCode { get; private set; } + { + /// + /// Gets the status code. + /// + /// The status code. + public HttpStatusCode StatusCode { get; private set; } - /// - /// Gets the status message. - /// - public string StatusMessage { get; private set; } + /// + /// Gets the status message. + /// + public string StatusMessage { get; private set; } - /// - /// A flag indicating if caching of the result should be disabled - /// - /// - public bool DisableCaching { get; private set; } + /// + /// A flag indicating if caching of the result should be disabled + /// + /// + public bool DisableCaching { get; private set; } - /// - /// Initializes a new instance of the struct. - /// - /// The status code. - /// The status message. - public StatusCodeResult(HttpStatusCode code, string message = null, bool disableCaching = true) - { - StatusCode = code; - StatusMessage = message ?? HttpStatusMessages.DefaultMessage(code); - DisableCaching = disableCaching; - } + /// + /// Initializes a new instance of the struct. + /// + /// The status code. + /// The status message. + public StatusCodeResult(HttpStatusCode code, string message = null, bool disableCaching = true) + { + StatusCode = code; + StatusMessage = message ?? HttpStatusMessages.DefaultMessage(code); + DisableCaching = disableCaching; + } - /// - /// Execute the method with the specified context. - /// - /// The context to use. - public Task Execute(IHttpContext context) - { - if (DisableCaching) - context.Response.SetNonCacheable(); + /// + /// Execute the method with the specified context. + /// + /// The context to use. + public Task Execute(IHttpContext context) + { + if (DisableCaching) + context.Response.SetNonCacheable(); - context.Response.StatusCode = StatusCode; - context.Response.StatusMessage = StatusMessage; - return Task.FromResult(true); - } - } + context.Response.StatusCode = StatusCode; + context.Response.StatusMessage = StatusMessage; + return Task.FromResult(true); + } + } - /// - /// Result wrapper for providing an IResult from a function - /// - internal struct LambdaResult : IResult - { - /// - /// The function to invoke - /// - private readonly Func m_func; + /// + /// Result wrapper for providing an IResult from a function + /// + internal struct LambdaResult : IResult + { + /// + /// The function to invoke + /// + private readonly Func m_func; - /// - /// Initializes a new instance of the struct. - /// - /// The function to invoke. - public LambdaResult(Func func) - { - m_func = (x) => func(); - } + /// + /// Initializes a new instance of the struct. + /// + /// The function to invoke. + public LambdaResult(Func func) + { + m_func = (x) => func(); + } - /// - /// Initializes a new instance of the struct. - /// - /// The action to invoke. - public LambdaResult(Action func) - { - m_func = (x) => - { - func(); - return Task.FromResult(true); - }; - } + /// + /// Initializes a new instance of the struct. + /// + /// The action to invoke. + public LambdaResult(Action func) + { + m_func = (x) => + { + func(); + return Task.FromResult(true); + }; + } - /// - /// Initializes a new instance of the struct. - /// - /// The function to invoke. - public LambdaResult(Func func) - { - m_func = func; - } + /// + /// Initializes a new instance of the struct. + /// + /// The function to invoke. + public LambdaResult(Func func) + { + m_func = func; + } - /// - /// Initializes a new instance of the struct. - /// - /// The action to invoke. - public LambdaResult(Action func) - { - m_func = (ctx) => - { - func(ctx); - return Task.FromResult(true); - }; - } + /// + /// Initializes a new instance of the struct. + /// + /// The action to invoke. + public LambdaResult(Action func) + { + m_func = (ctx) => + { + func(ctx); + return Task.FromResult(true); + }; + } - /// - /// Execute the method with the specified context. - /// - /// The context to use. - public Task Execute(IHttpContext context) - { - return m_func(context); - } - } + /// + /// Execute the method with the specified context. + /// + /// The context to use. + public Task Execute(IHttpContext context) + { + return m_func(context); + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Ceen/Mvc/RouteParser.cs b/libraries/MTConnect.NET-HTTP/Ceen/Mvc/RouteParser.cs index 7bf382761..4116214ac 100644 --- a/libraries/MTConnect.NET-HTTP/Ceen/Mvc/RouteParser.cs +++ b/libraries/MTConnect.NET-HTTP/Ceen/Mvc/RouteParser.cs @@ -6,1031 +6,1031 @@ namespace Ceen.Mvc { - /// - /// Class for parsing route descriptions - /// - internal class RouteParser - { - /// - /// Common interface for fragments - /// - private interface IFragment - { - /// - /// Checks if the fragment matches - /// - /// The fragment to check. - /// The number of characters matched, negative numbers indicate no match - int Matches(string fragment); - - /// - /// Gets the children of this entry. - /// - IFragment[] Children { get; } - - /// - /// Returns a copy of the instance with the children entry set to the designated child - /// - /// The copy of this entry. - /// The children to attach. - IFragment AttachChildren(IFragment[] children); - } - - /// - /// Represents a literal token - /// - private struct Literal : IFragment - { - /// - /// The literal value for this fragment - /// - private readonly string m_value; - /// - /// The string comparer used for this instance - /// - private readonly StringComparison m_stringComparer; - /// - /// The list of child entries - /// - private readonly IFragment[] m_children; - - /// - /// Gets a value indicating whether this is case sensitive. - /// - public bool IsCaseSensitive { get { return m_stringComparer == StringComparison.OrdinalIgnoreCase; } } - /// - /// Gets the literal value. - /// - public string Value { get { return m_value; } } - /// - /// Gets the children. - /// - public IFragment[] Children { get { return m_children;} } - - /// - /// Initializes a new instance of the struct. - /// - /// The literal value to use. - /// If set to true, matches will be case insensitive. - /// The children associated with this entry. - public Literal(string value, bool caseinsensitive, IFragment[] children) - { - m_value = value; - m_stringComparer = caseinsensitive ? StringComparison.OrdinalIgnoreCase : StringComparison.Ordinal; - m_children = children; - } - - /// - /// Matches the fragment with the literal value. - /// - /// The fragment to match. - /// The number of charaters matched, negative numbers indicate no match - public int Matches(string fragment) - { - return fragment.StartsWith(m_value, m_stringComparer) ? m_value.Length : -1; - } - - /// - /// Returns a that represents the current . - /// - /// A that represents the current . - public override string ToString() - { - var v = m_value; - - if (this.Children != null) - v = string.Join("|", this.Children.Select(x => v + x.ToString())); - - return v; - } - - /// - /// Creates a clone of this entry, but assigned to new children - /// - /// The cloned copy. - /// The new children. - public IFragment AttachChildren(IFragment[] children) - { - return new Literal(m_value, m_stringComparer == StringComparison.OrdinalIgnoreCase, children); - } - } - - /// - /// A bound variable - /// - private struct BoundVariable : IFragment - { - /// - /// The name of the variable - /// - private readonly string m_name; - /// - /// The bound value for the variable - /// - private readonly string m_value; - /// - /// The string comparer used for this instance - /// - private readonly StringComparison m_stringComparer; - /// - /// The children. - /// - private readonly IFragment[] m_children; - - /// - /// Gets a value indicating whether this is case sensitive. - /// - public bool IsCaseSensitive { get { return m_stringComparer == StringComparison.OrdinalIgnoreCase; } } - /// - /// Gets the bound value. - /// - public string Value { get { return m_value; } } - /// - /// Gets the bound name - /// - public string Name { get { return m_name; } } - /// - /// Gets the children. - /// - public IFragment[] Children { get { return m_children; } } - - /// - /// Initializes a new instance of the struct. - /// - /// The name of the variable. - /// The bound value. - /// If set to true, comapres are performed case insensitive. - /// The children to assign. - public BoundVariable(string name, string value, bool caseinsensitive, IFragment[] children) - { - m_name = name; - m_value = value; - m_stringComparer = caseinsensitive ? StringComparison.OrdinalIgnoreCase : StringComparison.Ordinal; - m_children = children; - } - - /// - /// Checks if the fragment matches - /// - /// The fragment to check. - /// The number of characters matched, negative numbers indicate no match - public int Matches(string fragment) - { - return string.Equals(m_value, fragment, m_stringComparer) ? m_value.Length : -1; - } - - /// - /// Returns a that represents the current . - /// - /// A that represents the current . - public override string ToString() - { - var v = $"[{m_name}={m_value}]"; - - if (this.Children != null) - v = string.Join("|", this.Children.Select(x => v + x.ToString())); - - return v; - } - - /// - /// Returns a copy of the instance with the children entry set to the designated child - /// - /// The copy of this entry. - /// The children to attach. - public IFragment AttachChildren(IFragment[] children) - { - return new BoundVariable(m_name, m_value, m_stringComparer == StringComparison.OrdinalIgnoreCase, children); - } - } - - /// - /// Represents a variable - /// - private struct Variable : IFragment - { - /// - /// The variable name - /// - private readonly string m_name; - /// - /// The variable default value, if any - /// - private readonly string m_defaultvalue; - /// - /// A flag indicating if the variable is optional - /// - private readonly bool m_optional; - /// - /// A flag indicating if this variable slurps up the rest of the url - /// - private readonly bool m_slurp; - /// - /// Additional constraints for matching - /// - private readonly string m_constraint; - /// - /// A string delimiting the variable - /// - private readonly string m_delimiter; - /// - /// The assigned children. - /// - private readonly IFragment[] m_children; - - /// - /// Gets the children. - /// - public IFragment[] Children { get { return m_children; } } - - /// - /// Initializes a new instance of the struct. - /// - /// Name. - /// Defaultvalue. - /// If set to true optional. - /// Contraint. - /// If set to true slurp. - /// Children. - public Variable(string name, string defaultvalue, bool optional, string contraint, bool slurp, IFragment[] children) - { - m_name = name; - m_defaultvalue = defaultvalue; - m_optional = optional; - m_constraint = contraint; - m_slurp = slurp; - m_children = children; - if (children == null || m_children.Length == 0) - m_delimiter = "/"; - else - { - var firstliteral = m_children.Where(x => x is Literal).Select(x => ((Literal)x).Value).FirstOrDefault(); - if (string.IsNullOrWhiteSpace(firstliteral)) - m_delimiter = "/"; - else - m_delimiter = firstliteral.Substring(0); - } - } - - /// - /// Checks if the fragment matches - /// - /// The fragment to check. - /// The number of characters matched, negative numbers indicate no match - public int Matches(string fragment) - { - if (string.IsNullOrWhiteSpace(fragment)) - return m_optional ? 0 : -1; - - if (m_slurp) - return fragment.Length; - - var ix = fragment.IndexOf(m_delimiter, StringComparison.Ordinal); - return ix < 0 ? fragment.Length : ix; - } - - /// - /// Returns a that represents the current . - /// - /// A that represents the current . - public override string ToString() - { - var ext = string.IsNullOrWhiteSpace(m_defaultvalue) ? "" : "=" + m_defaultvalue; - var cst = string.IsNullOrWhiteSpace(m_constraint) ? "" : ":" + m_constraint; - var str = "{" + string.Format(string.Format("{0}{1}{2}{3}", m_slurp ? "*" : "", m_name, cst, ext)) + "}"; - - if (this.Children != null) - str = string.Join("|", this.Children.Select(x => str + x.ToString())); - - return str; - } - - /// - /// Gets the name of the variable. - /// - public string Name { get { return m_name; } } - /// - /// Gets a value indicating if the variable is optional - /// - public bool Optional { get { return m_optional; } } - /// - /// Gets the default value - /// - public string DefaultValue { get { return m_defaultvalue; } } - - /// - /// Returns a copy of the instance with the children entry set to the designated child - /// - /// The copy of this entry. - /// The children to attach. - public IFragment AttachChildren(IFragment[] children) - { - return new Variable(m_name, m_defaultvalue, m_optional, m_constraint, m_slurp, children); - } - } - - /// - /// Represents a terminator - /// - private struct Result : IFragment - { - /// - /// The target route this entry points to - /// - public readonly RouteEntry Route; - - /// - /// Initializes a new instance of the struct. - /// - /// The entry to represent. - public Result(RouteEntry entry) - { - Route = entry; - } - - /// - /// Checks if the fragment matches - /// - /// The fragment to check. - /// The number of characters matched, negative numbers indicate no match - public int Matches(string fragment) - { - return 0; - } - - /// - /// Returns a copy of the instance with the children entry set to the designated child - /// - /// The copy of this entry. - /// The children to attach. - public IFragment AttachChildren(IFragment[] children) - { - throw new Exception("Cannot attach children to a result node"); - } - - /// - /// Gets the children. - /// - public IFragment[] Children { get { return null; } } - - /// - /// Returns a that represents the current . - /// - /// A that represents the current . - public override string ToString() - { - return string.Format(" => {0}, {1}", Route.Controller == null ? Route.Action.Method.DeclaringType.FullName : Route.Controller.GetType().FullName, Route.Action.Method); - } - } - - /// - /// Represents a choice between different fragments - /// - private struct Choice : IFragment - { - /// - /// Teh children representing the choices - /// - private readonly IFragment[] m_children; - - /// - /// Gets the children. - /// - public IFragment[] Children { get { return m_children; } } - - /// - /// Initializes a new instance of the struct. - /// - /// The choices to use. - public Choice(IFragment[] choices) - { - if (choices == null || choices.Length == 0) - throw new ArgumentNullException(nameof(choices)); - m_children = choices; - } - - /// - /// Checks if the fragment matches - /// - /// The fragment to check. - /// The number of characters matched, negative numbers indicate no match - public int Matches(string fragment) - { - return 0; - } - - /// - /// Returns a that represents the current . - /// - /// A that represents the current . - public override string ToString() - { - return string.Join("|", m_children.Select(x => x.ToString())); - } - - /// - /// Returns a copy of the instance with the children entry set to the designated child - /// - /// The copy of this entry. - /// The children to attach. - public IFragment AttachChildren(IFragment[] children) - { - throw new InvalidOperationException($"Cannot set child on a choice"); - } - } - - /// - /// The regluar expression that matches variables - /// - private static readonly Regex CURLY_MATCH = new Regex(@"((?[^\}]+)\}(?!\})"); - - /// - /// The regular expression for matching a variable's components - /// - private static readonly Regex VARIABLE_MATCH = new Regex(@"(?\*)?(?\w+)(?\?)?(:(?[^\=\?]+))?(?\?)?(\=(?.*))?"); - - /// - /// The list of fragments in this route - /// - private readonly IFragment m_root; - - /// - /// Initializes a new instance of the class. - /// - /// The route specification to parse. - public RouteParser(string route, bool caseinsensitive, RouteEntry target) - { - var fragments = new List(); - - var ix = 0; - var slurp = false; - foreach (Match m in CURLY_MATCH.Matches(route)) - { - if (slurp) - throw new Exception($"Cannot have trailing data after slurp: {m.Value}"); - - if (ix != m.Index) - fragments.Add(new Literal(route.Substring(ix, m.Index - ix), caseinsensitive, null)); - - var mv = VARIABLE_MATCH.Match(m.Groups["name"].Value); - if (!mv.Success) - throw new ArgumentException($"Failed to parse {m.Groups["name"].Value} as a valid variable expression"); - - var v = new Variable(mv.Groups["name"].Value, mv.Groups["default"].Value, mv.Groups["optional"].Success, mv.Groups["constraint"].Value, mv.Groups["slurp"].Success, null); - - if (fragments.Count > 0 && !(fragments.Last() is Literal)) - throw new Exception(string.Format("Must have literal spacer between {0} and {1}", fragments[fragments.Count - 2], v)); - - fragments.Add(v); - - ix = m.Index + m.Length; - } - - if (ix != route.Length) - fragments.Add(new Literal(route.Substring(ix, route.Length - ix), caseinsensitive, null)); - - fragments.Add(new Result(target)); - - m_root = LinkList(fragments); - } - - /// - /// Initializes a new instance of the class. - /// - /// The root fragment instance. - private RouteParser(IFragment root) - { - m_root = root; - } - - /// - /// Merges a list of entries into a new tree - /// - /// The entries to merge. - private static IFragment Merge(List entries) - { - if (entries.Count == 0) - throw new Exception("Cannot work with empty list"); - if (entries.Count == 1) - return entries.First(); - - if (entries.All(x => x is Literal)) - { - var roots = entries.OrderBy(x => ((Literal)x).Value).Cast().ToList(); - var shortest = roots.First(); - - // Get the longest shared prefix - var sb = new StringBuilder(); - for (var n = 0; n < shortest.Value.Length; n++) - { - var cmp = shortest.Value[n]; - if (roots.All(x => x.Value[n] == cmp)) - sb.Append(cmp); - else - break; - } - - if (sb.Length > 0) - { - var childchoices = - roots - .Where(x => x.Value.Length > sb.Length) - .Select(x => new Literal(x.Value.Substring(sb.Length), shortest.IsCaseSensitive, x.Children)) - .GroupBy( - x => x.Value.Length == 0 ? string.Empty : x.Value.Substring(0, 1), - x => x - ) - .Select(x => Merge(x.Cast().ToList())) - .Union( - roots - .Where(x => x.Value.Length == sb.Length) - .SelectMany(x => x.Children) - .GroupBy(x => x.GetType(), (key, list) => Merge(list.ToList())).ToArray() - ) - .ToArray(); - - return new Literal(sb.ToString(), shortest.IsCaseSensitive, childchoices); - } - } - else if (entries.All(x => x is Variable)) - { - // TODO: This does not work, if some variables are optional, and others not.... - var first = (Variable)entries.First(); - if (entries.All(x => ((Variable)x).Name == first.Name)) - { - return first.AttachChildren( - entries - .SelectMany(x => x.Children) - .GroupBy(x => x.GetType(), (key, list) => Merge(list.ToList())) - .ToArray()); - } - else - { - return new Choice(entries.GroupBy(x => ((Variable)x).Name, (key, list) => Merge(list.ToList())).ToArray()); - } - } - else if (entries.All(x => x is Result)) - { - var lst = entries.Cast().ToList(); - var allverbs = lst.Where(x => x.Route.AcceptsAllVerbs).ToList(); - if (allverbs.Count > 1) - throw new Exception(string.Format("Unable to disambiguate the routes for: {0}{1}", Environment.NewLine, string.Join(Environment.NewLine, allverbs.Select(x => x.Route.Action.Method)))); - - var specificverbs = lst.Where(x => !x.Route.AcceptsAllVerbs); - var verblist = specificverbs.SelectMany(x => x.Route.Verbs.Distinct().Select(y => new { Verb = y, Route = x.Route })); - var duplicates = verblist.GroupBy(x => x.Verb).Where(x => x.Count() > 1).Select(x => x.ToList()).FirstOrDefault(); - if (duplicates != null) - throw new Exception(string.Format("Unable to disambiguate the routes for HTTP verb {2}: {0}{1}", Environment.NewLine, string.Join(Environment.NewLine, duplicates.Select(x => x.Route.Action.Method)), duplicates.First().Verb)); - - // "false" is first, so items without wildcard http are seen first - return new Choice(lst.OrderBy(x => x.Route.AcceptsAllVerbs).Cast().ToArray()); - } - else - { - var f = entries.First(); - if (entries.All(x => x.GetType() == f.GetType())) - return new Choice(entries.ToArray()); - } - - return new Choice(entries.GroupBy(x => x.GetType(), (key, list) => Merge(list.ToList())).ToArray()); - } - - /// - /// Merges a list of routes - /// - /// The routes to merge. - public static RouteParser Merge(IEnumerable entries) - { - if (entries.Count() == 0) - throw new Exception("Cannot work with empty list"); - if (entries.Count() == 1) - return entries.First(); - - var roots = entries.Select(x => x.m_root).ToList(); - if (roots.Any(x => !(x is Literal))) - throw new Exception("Invalid initial values"); - - if (roots.Any(x => !((Literal)x).Value.StartsWith("/", StringComparison.Ordinal))) - throw new Exception("Invalid initial values"); - - return new RouteParser(Merge(roots)); - } - - /// - /// A state keeper to track the current position in the matching sequence - /// - private struct LookupStackEntry - { - /// - /// The fragment this entry represents - /// - public readonly IFragment Fragment; - /// - /// The string offset matched so far - /// - public readonly int Offset; - /// - /// The list of variables picked up so far - /// - public readonly Dictionary Variables; - /// - /// The number of pre-matched characters - /// - public readonly int MatchedCharacters; - - /// - /// Initializes a new instance of the struct. - /// - /// The fragment to use. - /// The string offset. - /// The variable dictionary. - public LookupStackEntry(IFragment fragment, int offset, Dictionary variables, int prematched) - { - Fragment = fragment; - Offset = offset; - Variables = variables; - MatchedCharacters = prematched; - - } - } - - /// - /// Attempts to match a request to routes - /// - /// The matched potential routes. - /// Teh request to match. - internal IEnumerable>> MatchRequest(string request) - { - if (!string.IsNullOrWhiteSpace(request)) - { - var work = new Stack(); - var reuse = true; - var prev = new LookupStackEntry(m_root, 0, new Dictionary(), -1); - - while (work.Count > 0 || reuse) - { - // If we re-use, don't bother with the stack - var e = reuse ? prev : work.Pop(); - reuse = false; - - // If we have pre-matched, don't match again - var m = e.MatchedCharacters < 0 ? e.Fragment.Matches(request.Substring(e.Offset)) : e.MatchedCharacters; - if (m >= 0) - { - if (e.Fragment is Result) - { - // Otherwise we have unmatched trailing chars - if (e.Offset + m == request.Length) - yield return new KeyValuePair>(((Result)e.Fragment).Route, e.Variables); - } - else if (e.Fragment.Children != null) - { - // If this entry introduced variables, update the dictionary - var dict = e.Variables; - if (e.Fragment is Variable) - { - dict = new Dictionary(dict); - dict[((Variable)e.Fragment).Name] = request.Substring(e.Offset, m); - } - else if (e.Fragment is BoundVariable) - { - dict = new Dictionary(dict); - dict[((BoundVariable)e.Fragment).Name] = request.Substring(e.Offset, m); - } - - // Add to work stack, re-using if possible - var offset = e.Offset + m; - var frag = request.Substring(offset); - foreach(var c in e.Fragment.Children) - { - var m2 = c.Matches(frag); - if (m2 < 0) - continue; - - if (!reuse) - { - prev = new LookupStackEntry(c, offset, dict, m2); - reuse = true; - } - else - { - work.Push(new LookupStackEntry(c, offset, dict, m2)); - } - } - } - } - } - } - } - - /// - /// Clones the list, by assigning each element with children from the previous entry - /// - /// The cloned list. - /// The root entry. - /// An optional conversion/filter function. - private static IFragment CloneList(IFragment cur, Func conv = null) - { - var lst = new List(); - conv = conv ?? (x => x); - - while (cur != null) - { - var cv = conv(cur); - if (cv == null) - break; - - lst.Add(cv); - - if (cur.Children == null) - cur = null; - else if (cur.Children.Length != 1) - throw new Exception("Cannot modify choice entry"); - else - cur = cur.Children.First(); - } - - return LinkList(lst); - } - - /// - /// Builds a sequential list from a root fragment - /// - /// The sequential list. - /// The root fragment - private static List BuildList(IFragment f) - { - var lst = new List(); - var r = f; - while (r != null) - { - lst.Add(r); - - if (r.Children == null) - r = null; - else if (r.Children.Length != 1) - throw new Exception("Cannot modify choice entry"); - else - r = r.Children.First(); - } - - return lst; - } - - /// - /// Re-links a list by assigning the children - /// - /// The root elemnt. - /// The list to link. - private static IFragment LinkList(List lst) - { - if (lst.Count == 0) - throw new ArgumentException(nameof(lst), "Cannot use an empty list"); - - if (!(lst[lst.Count - 1] is Result)) - { - lst[lst.Count - 1] = lst[lst.Count - 1].AttachChildren(null); - - if (lst.Count == 1) - return lst.First().AttachChildren(null); - } - - for (var i = lst.Count - 1; i > 0; i--) - lst[i - 1] = lst[i - 1].AttachChildren(new[] { lst[i] }); - - return lst.First(); - } - - /// - /// Constructs a new route by appending a path to this instance - /// - /// The path to append. - /// If set to true, comapres are performed case insensitive. - /// The target method. - /// The combined route - public RouteParser Append(string path, bool caseinsensitive, RouteEntry target) - { - return Append(new RouteParser(path, caseinsensitive, target)); - } - - /// - /// Appends a route to the end of this route - /// - /// The route to append. - /// The combined route - public RouteParser Append(RouteParser suffix) - { - var lst = BuildList(this.m_root); - lst.RemoveAt(lst.Count - 1); - lst.AddRange(BuildList(suffix.m_root)); - - if (!(lst.Last() is Result)) - throw new InvalidOperationException("Cannot append an entry that does not terminate"); - - return new RouteParser(LinkList(lst)); - } - - /// - /// Prunes the list, by removing empty entries and joining adjacent literals - /// - /// The pruned list. - /// The list to prune - private List PruneList(List lst) - { - IFragment prev = null; - for (var i = 0; i < lst.Count; i++) - { - var cur = lst[i]; - if (prev != null) - { - if (i != 0 && cur is Literal && string.IsNullOrEmpty(((Literal)cur).Value)) - { - lst.RemoveAt(i); - i--; - continue; - } - - if (prev is Literal && cur is Literal) - { - var s1 = ((Literal)prev).Value; - var s2 = ((Literal)cur).Value; - - var joinchar = s1.EndsWith("/", StringComparison.Ordinal) || s2.EndsWith("/", StringComparison.Ordinal) ? "/" : ""; - var s3 = s1.TrimEnd(new[] { '/' }) + joinchar + s2.TrimStart(new[] { '/' }); - - prev = lst[i - 1] = new Literal(s3, ((Literal)prev).IsCaseSensitive, null); - - // Remove it and continue - lst.RemoveAt(i); - i--; - continue; - } - else if (prev is Literal && cur is Result) - { - var s = ((Literal)prev).Value.TrimEnd(new[] { '/' }); - - // Fixup if we attempt to remove the root slash - if (lst.Count == 2 && s.Length == 0) - s += '/'; - - if (string.IsNullOrEmpty(s)) - lst.RemoveAt(i - 1); - else - prev = lst[i - 1] = new Literal(s, ((Literal)prev).IsCaseSensitive, null); - continue; - } - } - - prev = cur; - } - - return lst; - } - - /// - /// Constructs a new route by pruning this instance - /// - /// The pruned route. - public RouteParser PrunePath() - { - return new RouteParser(LinkList(PruneList(BuildList(this.m_root)))); - } - - /// - /// Bind the named variable(s) to the given value - /// - /// The name of the variable to bind. - /// The literal value to bind to. - /// If set to true, compares are performed case sensitive. - /// If set to true, binding is done with literal values. - public RouteParser Bind(string name, string value, bool iscasesensitive, bool asliteral) - { - var lst = BuildList(this.m_root); - for (var i = 0; i < lst.Count; i++) - { - var x = lst[i]; - if (x is Variable && ((Variable)x).Name == name) - { - if (asliteral) - lst[i] = new Literal(value, iscasesensitive, x.Children); - else - lst[i] = new BoundVariable(name, value, iscasesensitive, x.Children); - - //break; // If we want a single match - } - } - - var rp = new RouteParser(LinkList(lst)); - - return rp; - } - - /// - /// Gets the default value for a variable from this route - /// - /// The default value. - /// The name of the variable. - public string GetDefaultValue(string name) - { - var r = this.m_root; - while (r != null) - { - if (r is Variable && ((Variable)r).Name == name) - return ((Variable)r).DefaultValue; - - if (r.Children == null) - r = null; - else if (r.Children.Length != 1) - throw new Exception("Cannot search choice entry"); - else if (r.Children.First() is Result) - r = null; - else - r = r.Children.First(); - } - - return null; - } - - public IEnumerable> Variables - { - get - { - var lst = BuildList(this.m_root); - return - lst - .Where(x => x is Variable) - .Select(x => new KeyValuePair(((Variable)x).Name, ((Variable)x).Optional)) - .Union( - lst - .Where(x => x is BoundVariable) - .Select(x => new KeyValuePair(((BoundVariable)x).Name, false)) - ) - .Distinct(x => x.Key) - ; - } - } - - /// - /// Replaces the target entry with one based on the given input - /// - /// The new route. - /// The controller to use. - /// The method to call. - /// The accepted verbs. - public RouteParser ReplaceTarget(Controller controller, System.Reflection.MethodInfo method, string[] verbs) - { - var lst = BuildList(this.m_root); - lst = lst.Take(lst.Count - 1).ToList(); - lst.Add(new Result(new RouteEntry(controller, method, verbs, Variables))); - return new RouteParser(LinkList(lst)); - } - - /// - /// Returns a string-like representation of this entry - /// - public string Path { get { return CloneList(m_root, x => (x is Result) ? null : x).ToString(); } } - - /// - /// Returns a that represents the current . - /// - /// A that represents the current . - public override string ToString() - { - return string.Join(Environment.NewLine, GetAllRoutes()); - } - - /// - /// Enumerates all routes and builds a path-like string for each path - /// - /// The strings representing the routes. - private IEnumerable GetAllRoutes() - { - var s = new Stack>(); - s.Push(new KeyValuePair(string.Empty, m_root)); - - while (s.Count > 0) - { - var c = s.Pop(); - var str = c.Key; - if (c.Value is Literal) - str += ((Literal)c.Value).Value; - else if (c.Value is Variable) - str += "{" + ((Variable)c.Value).Name + "}"; - else if (c.Value is BoundVariable) - str += "{" + ((BoundVariable)c.Value).Name + "}"; - else if (c.Value is Result) - str += ((Result)c.Value).ToString(); - else if (!(c.Value is Choice)) - throw new Exception(string.Format("Unable to work with {0}", c.Value.GetType())); - - if (c.Value.Children == null) - yield return str; - else - foreach (var n in c.Value.Children) - s.Push(new KeyValuePair(str, n)); - - - } - } - } + /// + /// Class for parsing route descriptions + /// + internal class RouteParser + { + /// + /// Common interface for fragments + /// + private interface IFragment + { + /// + /// Checks if the fragment matches + /// + /// The fragment to check. + /// The number of characters matched, negative numbers indicate no match + int Matches(string fragment); + + /// + /// Gets the children of this entry. + /// + IFragment[] Children { get; } + + /// + /// Returns a copy of the instance with the children entry set to the designated child + /// + /// The copy of this entry. + /// The children to attach. + IFragment AttachChildren(IFragment[] children); + } + + /// + /// Represents a literal token + /// + private struct Literal : IFragment + { + /// + /// The literal value for this fragment + /// + private readonly string m_value; + /// + /// The string comparer used for this instance + /// + private readonly StringComparison m_stringComparer; + /// + /// The list of child entries + /// + private readonly IFragment[] m_children; + + /// + /// Gets a value indicating whether this is case sensitive. + /// + public bool IsCaseSensitive { get { return m_stringComparer == StringComparison.OrdinalIgnoreCase; } } + /// + /// Gets the literal value. + /// + public string Value { get { return m_value; } } + /// + /// Gets the children. + /// + public IFragment[] Children { get { return m_children; } } + + /// + /// Initializes a new instance of the struct. + /// + /// The literal value to use. + /// If set to true, matches will be case insensitive. + /// The children associated with this entry. + public Literal(string value, bool caseinsensitive, IFragment[] children) + { + m_value = value; + m_stringComparer = caseinsensitive ? StringComparison.OrdinalIgnoreCase : StringComparison.Ordinal; + m_children = children; + } + + /// + /// Matches the fragment with the literal value. + /// + /// The fragment to match. + /// The number of charaters matched, negative numbers indicate no match + public int Matches(string fragment) + { + return fragment.StartsWith(m_value, m_stringComparer) ? m_value.Length : -1; + } + + /// + /// Returns a that represents the current . + /// + /// A that represents the current . + public override string ToString() + { + var v = m_value; + + if (this.Children != null) + v = string.Join("|", this.Children.Select(x => v + x.ToString())); + + return v; + } + + /// + /// Creates a clone of this entry, but assigned to new children + /// + /// The cloned copy. + /// The new children. + public IFragment AttachChildren(IFragment[] children) + { + return new Literal(m_value, m_stringComparer == StringComparison.OrdinalIgnoreCase, children); + } + } + + /// + /// A bound variable + /// + private struct BoundVariable : IFragment + { + /// + /// The name of the variable + /// + private readonly string m_name; + /// + /// The bound value for the variable + /// + private readonly string m_value; + /// + /// The string comparer used for this instance + /// + private readonly StringComparison m_stringComparer; + /// + /// The children. + /// + private readonly IFragment[] m_children; + + /// + /// Gets a value indicating whether this is case sensitive. + /// + public bool IsCaseSensitive { get { return m_stringComparer == StringComparison.OrdinalIgnoreCase; } } + /// + /// Gets the bound value. + /// + public string Value { get { return m_value; } } + /// + /// Gets the bound name + /// + public string Name { get { return m_name; } } + /// + /// Gets the children. + /// + public IFragment[] Children { get { return m_children; } } + + /// + /// Initializes a new instance of the struct. + /// + /// The name of the variable. + /// The bound value. + /// If set to true, comapres are performed case insensitive. + /// The children to assign. + public BoundVariable(string name, string value, bool caseinsensitive, IFragment[] children) + { + m_name = name; + m_value = value; + m_stringComparer = caseinsensitive ? StringComparison.OrdinalIgnoreCase : StringComparison.Ordinal; + m_children = children; + } + + /// + /// Checks if the fragment matches + /// + /// The fragment to check. + /// The number of characters matched, negative numbers indicate no match + public int Matches(string fragment) + { + return string.Equals(m_value, fragment, m_stringComparer) ? m_value.Length : -1; + } + + /// + /// Returns a that represents the current . + /// + /// A that represents the current . + public override string ToString() + { + var v = $"[{m_name}={m_value}]"; + + if (this.Children != null) + v = string.Join("|", this.Children.Select(x => v + x.ToString())); + + return v; + } + + /// + /// Returns a copy of the instance with the children entry set to the designated child + /// + /// The copy of this entry. + /// The children to attach. + public IFragment AttachChildren(IFragment[] children) + { + return new BoundVariable(m_name, m_value, m_stringComparer == StringComparison.OrdinalIgnoreCase, children); + } + } + + /// + /// Represents a variable + /// + private struct Variable : IFragment + { + /// + /// The variable name + /// + private readonly string m_name; + /// + /// The variable default value, if any + /// + private readonly string m_defaultvalue; + /// + /// A flag indicating if the variable is optional + /// + private readonly bool m_optional; + /// + /// A flag indicating if this variable slurps up the rest of the url + /// + private readonly bool m_slurp; + /// + /// Additional constraints for matching + /// + private readonly string m_constraint; + /// + /// A string delimiting the variable + /// + private readonly string m_delimiter; + /// + /// The assigned children. + /// + private readonly IFragment[] m_children; + + /// + /// Gets the children. + /// + public IFragment[] Children { get { return m_children; } } + + /// + /// Initializes a new instance of the struct. + /// + /// Name. + /// Defaultvalue. + /// If set to true optional. + /// Contraint. + /// If set to true slurp. + /// Children. + public Variable(string name, string defaultvalue, bool optional, string contraint, bool slurp, IFragment[] children) + { + m_name = name; + m_defaultvalue = defaultvalue; + m_optional = optional; + m_constraint = contraint; + m_slurp = slurp; + m_children = children; + if (children == null || m_children.Length == 0) + m_delimiter = "/"; + else + { + var firstliteral = m_children.Where(x => x is Literal).Select(x => ((Literal)x).Value).FirstOrDefault(); + if (string.IsNullOrWhiteSpace(firstliteral)) + m_delimiter = "/"; + else + m_delimiter = firstliteral.Substring(0); + } + } + + /// + /// Checks if the fragment matches + /// + /// The fragment to check. + /// The number of characters matched, negative numbers indicate no match + public int Matches(string fragment) + { + if (string.IsNullOrWhiteSpace(fragment)) + return m_optional ? 0 : -1; + + if (m_slurp) + return fragment.Length; + + var ix = fragment.IndexOf(m_delimiter, StringComparison.Ordinal); + return ix < 0 ? fragment.Length : ix; + } + + /// + /// Returns a that represents the current . + /// + /// A that represents the current . + public override string ToString() + { + var ext = string.IsNullOrWhiteSpace(m_defaultvalue) ? "" : "=" + m_defaultvalue; + var cst = string.IsNullOrWhiteSpace(m_constraint) ? "" : ":" + m_constraint; + var str = "{" + string.Format(string.Format("{0}{1}{2}{3}", m_slurp ? "*" : "", m_name, cst, ext)) + "}"; + + if (this.Children != null) + str = string.Join("|", this.Children.Select(x => str + x.ToString())); + + return str; + } + + /// + /// Gets the name of the variable. + /// + public string Name { get { return m_name; } } + /// + /// Gets a value indicating if the variable is optional + /// + public bool Optional { get { return m_optional; } } + /// + /// Gets the default value + /// + public string DefaultValue { get { return m_defaultvalue; } } + + /// + /// Returns a copy of the instance with the children entry set to the designated child + /// + /// The copy of this entry. + /// The children to attach. + public IFragment AttachChildren(IFragment[] children) + { + return new Variable(m_name, m_defaultvalue, m_optional, m_constraint, m_slurp, children); + } + } + + /// + /// Represents a terminator + /// + private struct Result : IFragment + { + /// + /// The target route this entry points to + /// + public readonly RouteEntry Route; + + /// + /// Initializes a new instance of the struct. + /// + /// The entry to represent. + public Result(RouteEntry entry) + { + Route = entry; + } + + /// + /// Checks if the fragment matches + /// + /// The fragment to check. + /// The number of characters matched, negative numbers indicate no match + public int Matches(string fragment) + { + return 0; + } + + /// + /// Returns a copy of the instance with the children entry set to the designated child + /// + /// The copy of this entry. + /// The children to attach. + public IFragment AttachChildren(IFragment[] children) + { + throw new Exception("Cannot attach children to a result node"); + } + + /// + /// Gets the children. + /// + public IFragment[] Children { get { return null; } } + + /// + /// Returns a that represents the current . + /// + /// A that represents the current . + public override string ToString() + { + return string.Format(" => {0}, {1}", Route.Controller == null ? Route.Action.Method.DeclaringType.FullName : Route.Controller.GetType().FullName, Route.Action.Method); + } + } + + /// + /// Represents a choice between different fragments + /// + private struct Choice : IFragment + { + /// + /// Teh children representing the choices + /// + private readonly IFragment[] m_children; + + /// + /// Gets the children. + /// + public IFragment[] Children { get { return m_children; } } + + /// + /// Initializes a new instance of the struct. + /// + /// The choices to use. + public Choice(IFragment[] choices) + { + if (choices == null || choices.Length == 0) + throw new ArgumentNullException(nameof(choices)); + m_children = choices; + } + + /// + /// Checks if the fragment matches + /// + /// The fragment to check. + /// The number of characters matched, negative numbers indicate no match + public int Matches(string fragment) + { + return 0; + } + + /// + /// Returns a that represents the current . + /// + /// A that represents the current . + public override string ToString() + { + return string.Join("|", m_children.Select(x => x.ToString())); + } + + /// + /// Returns a copy of the instance with the children entry set to the designated child + /// + /// The copy of this entry. + /// The children to attach. + public IFragment AttachChildren(IFragment[] children) + { + throw new InvalidOperationException($"Cannot set child on a choice"); + } + } + + /// + /// The regluar expression that matches variables + /// + private static readonly Regex CURLY_MATCH = new Regex(@"((?[^\}]+)\}(?!\})"); + + /// + /// The regular expression for matching a variable's components + /// + private static readonly Regex VARIABLE_MATCH = new Regex(@"(?\*)?(?\w+)(?\?)?(:(?[^\=\?]+))?(?\?)?(\=(?.*))?"); + + /// + /// The list of fragments in this route + /// + private readonly IFragment m_root; + + /// + /// Initializes a new instance of the class. + /// + /// The route specification to parse. + public RouteParser(string route, bool caseinsensitive, RouteEntry target) + { + var fragments = new List(); + + var ix = 0; + var slurp = false; + foreach (Match m in CURLY_MATCH.Matches(route)) + { + if (slurp) + throw new Exception($"Cannot have trailing data after slurp: {m.Value}"); + + if (ix != m.Index) + fragments.Add(new Literal(route.Substring(ix, m.Index - ix), caseinsensitive, null)); + + var mv = VARIABLE_MATCH.Match(m.Groups["name"].Value); + if (!mv.Success) + throw new ArgumentException($"Failed to parse {m.Groups["name"].Value} as a valid variable expression"); + + var v = new Variable(mv.Groups["name"].Value, mv.Groups["default"].Value, mv.Groups["optional"].Success, mv.Groups["constraint"].Value, mv.Groups["slurp"].Success, null); + + if (fragments.Count > 0 && !(fragments.Last() is Literal)) + throw new Exception(string.Format("Must have literal spacer between {0} and {1}", fragments[fragments.Count - 2], v)); + + fragments.Add(v); + + ix = m.Index + m.Length; + } + + if (ix != route.Length) + fragments.Add(new Literal(route.Substring(ix, route.Length - ix), caseinsensitive, null)); + + fragments.Add(new Result(target)); + + m_root = LinkList(fragments); + } + + /// + /// Initializes a new instance of the class. + /// + /// The root fragment instance. + private RouteParser(IFragment root) + { + m_root = root; + } + + /// + /// Merges a list of entries into a new tree + /// + /// The entries to merge. + private static IFragment Merge(List entries) + { + if (entries.Count == 0) + throw new Exception("Cannot work with empty list"); + if (entries.Count == 1) + return entries.First(); + + if (entries.All(x => x is Literal)) + { + var roots = entries.OrderBy(x => ((Literal)x).Value).Cast().ToList(); + var shortest = roots.First(); + + // Get the longest shared prefix + var sb = new StringBuilder(); + for (var n = 0; n < shortest.Value.Length; n++) + { + var cmp = shortest.Value[n]; + if (roots.All(x => x.Value[n] == cmp)) + sb.Append(cmp); + else + break; + } + + if (sb.Length > 0) + { + var childchoices = + roots + .Where(x => x.Value.Length > sb.Length) + .Select(x => new Literal(x.Value.Substring(sb.Length), shortest.IsCaseSensitive, x.Children)) + .GroupBy( + x => x.Value.Length == 0 ? string.Empty : x.Value.Substring(0, 1), + x => x + ) + .Select(x => Merge(x.Cast().ToList())) + .Union( + roots + .Where(x => x.Value.Length == sb.Length) + .SelectMany(x => x.Children) + .GroupBy(x => x.GetType(), (key, list) => Merge(list.ToList())).ToArray() + ) + .ToArray(); + + return new Literal(sb.ToString(), shortest.IsCaseSensitive, childchoices); + } + } + else if (entries.All(x => x is Variable)) + { + // TODO: This does not work, if some variables are optional, and others not.... + var first = (Variable)entries.First(); + if (entries.All(x => ((Variable)x).Name == first.Name)) + { + return first.AttachChildren( + entries + .SelectMany(x => x.Children) + .GroupBy(x => x.GetType(), (key, list) => Merge(list.ToList())) + .ToArray()); + } + else + { + return new Choice(entries.GroupBy(x => ((Variable)x).Name, (key, list) => Merge(list.ToList())).ToArray()); + } + } + else if (entries.All(x => x is Result)) + { + var lst = entries.Cast().ToList(); + var allverbs = lst.Where(x => x.Route.AcceptsAllVerbs).ToList(); + if (allverbs.Count > 1) + throw new Exception(string.Format("Unable to disambiguate the routes for: {0}{1}", Environment.NewLine, string.Join(Environment.NewLine, allverbs.Select(x => x.Route.Action.Method)))); + + var specificverbs = lst.Where(x => !x.Route.AcceptsAllVerbs); + var verblist = specificverbs.SelectMany(x => x.Route.Verbs.Distinct().Select(y => new { Verb = y, Route = x.Route })); + var duplicates = verblist.GroupBy(x => x.Verb).Where(x => x.Count() > 1).Select(x => x.ToList()).FirstOrDefault(); + if (duplicates != null) + throw new Exception(string.Format("Unable to disambiguate the routes for HTTP verb {2}: {0}{1}", Environment.NewLine, string.Join(Environment.NewLine, duplicates.Select(x => x.Route.Action.Method)), duplicates.First().Verb)); + + // "false" is first, so items without wildcard http are seen first + return new Choice(lst.OrderBy(x => x.Route.AcceptsAllVerbs).Cast().ToArray()); + } + else + { + var f = entries.First(); + if (entries.All(x => x.GetType() == f.GetType())) + return new Choice(entries.ToArray()); + } + + return new Choice(entries.GroupBy(x => x.GetType(), (key, list) => Merge(list.ToList())).ToArray()); + } + + /// + /// Merges a list of routes + /// + /// The routes to merge. + public static RouteParser Merge(IEnumerable entries) + { + if (entries.Count() == 0) + throw new Exception("Cannot work with empty list"); + if (entries.Count() == 1) + return entries.First(); + + var roots = entries.Select(x => x.m_root).ToList(); + if (roots.Any(x => !(x is Literal))) + throw new Exception("Invalid initial values"); + + if (roots.Any(x => !((Literal)x).Value.StartsWith("/", StringComparison.Ordinal))) + throw new Exception("Invalid initial values"); + + return new RouteParser(Merge(roots)); + } + + /// + /// A state keeper to track the current position in the matching sequence + /// + private struct LookupStackEntry + { + /// + /// The fragment this entry represents + /// + public readonly IFragment Fragment; + /// + /// The string offset matched so far + /// + public readonly int Offset; + /// + /// The list of variables picked up so far + /// + public readonly Dictionary Variables; + /// + /// The number of pre-matched characters + /// + public readonly int MatchedCharacters; + + /// + /// Initializes a new instance of the struct. + /// + /// The fragment to use. + /// The string offset. + /// The variable dictionary. + public LookupStackEntry(IFragment fragment, int offset, Dictionary variables, int prematched) + { + Fragment = fragment; + Offset = offset; + Variables = variables; + MatchedCharacters = prematched; + + } + } + + /// + /// Attempts to match a request to routes + /// + /// The matched potential routes. + /// Teh request to match. + internal IEnumerable>> MatchRequest(string request) + { + if (!string.IsNullOrWhiteSpace(request)) + { + var work = new Stack(); + var reuse = true; + var prev = new LookupStackEntry(m_root, 0, new Dictionary(), -1); + + while (work.Count > 0 || reuse) + { + // If we re-use, don't bother with the stack + var e = reuse ? prev : work.Pop(); + reuse = false; + + // If we have pre-matched, don't match again + var m = e.MatchedCharacters < 0 ? e.Fragment.Matches(request.Substring(e.Offset)) : e.MatchedCharacters; + if (m >= 0) + { + if (e.Fragment is Result) + { + // Otherwise we have unmatched trailing chars + if (e.Offset + m == request.Length) + yield return new KeyValuePair>(((Result)e.Fragment).Route, e.Variables); + } + else if (e.Fragment.Children != null) + { + // If this entry introduced variables, update the dictionary + var dict = e.Variables; + if (e.Fragment is Variable) + { + dict = new Dictionary(dict); + dict[((Variable)e.Fragment).Name] = request.Substring(e.Offset, m); + } + else if (e.Fragment is BoundVariable) + { + dict = new Dictionary(dict); + dict[((BoundVariable)e.Fragment).Name] = request.Substring(e.Offset, m); + } + + // Add to work stack, re-using if possible + var offset = e.Offset + m; + var frag = request.Substring(offset); + foreach (var c in e.Fragment.Children) + { + var m2 = c.Matches(frag); + if (m2 < 0) + continue; + + if (!reuse) + { + prev = new LookupStackEntry(c, offset, dict, m2); + reuse = true; + } + else + { + work.Push(new LookupStackEntry(c, offset, dict, m2)); + } + } + } + } + } + } + } + + /// + /// Clones the list, by assigning each element with children from the previous entry + /// + /// The cloned list. + /// The root entry. + /// An optional conversion/filter function. + private static IFragment CloneList(IFragment cur, Func conv = null) + { + var lst = new List(); + conv = conv ?? (x => x); + + while (cur != null) + { + var cv = conv(cur); + if (cv == null) + break; + + lst.Add(cv); + + if (cur.Children == null) + cur = null; + else if (cur.Children.Length != 1) + throw new Exception("Cannot modify choice entry"); + else + cur = cur.Children.First(); + } + + return LinkList(lst); + } + + /// + /// Builds a sequential list from a root fragment + /// + /// The sequential list. + /// The root fragment + private static List BuildList(IFragment f) + { + var lst = new List(); + var r = f; + while (r != null) + { + lst.Add(r); + + if (r.Children == null) + r = null; + else if (r.Children.Length != 1) + throw new Exception("Cannot modify choice entry"); + else + r = r.Children.First(); + } + + return lst; + } + + /// + /// Re-links a list by assigning the children + /// + /// The root elemnt. + /// The list to link. + private static IFragment LinkList(List lst) + { + if (lst.Count == 0) + throw new ArgumentException(nameof(lst), "Cannot use an empty list"); + + if (!(lst[lst.Count - 1] is Result)) + { + lst[lst.Count - 1] = lst[lst.Count - 1].AttachChildren(null); + + if (lst.Count == 1) + return lst.First().AttachChildren(null); + } + + for (var i = lst.Count - 1; i > 0; i--) + lst[i - 1] = lst[i - 1].AttachChildren(new[] { lst[i] }); + + return lst.First(); + } + + /// + /// Constructs a new route by appending a path to this instance + /// + /// The path to append. + /// If set to true, comapres are performed case insensitive. + /// The target method. + /// The combined route + public RouteParser Append(string path, bool caseinsensitive, RouteEntry target) + { + return Append(new RouteParser(path, caseinsensitive, target)); + } + + /// + /// Appends a route to the end of this route + /// + /// The route to append. + /// The combined route + public RouteParser Append(RouteParser suffix) + { + var lst = BuildList(this.m_root); + lst.RemoveAt(lst.Count - 1); + lst.AddRange(BuildList(suffix.m_root)); + + if (!(lst.Last() is Result)) + throw new InvalidOperationException("Cannot append an entry that does not terminate"); + + return new RouteParser(LinkList(lst)); + } + + /// + /// Prunes the list, by removing empty entries and joining adjacent literals + /// + /// The pruned list. + /// The list to prune + private List PruneList(List lst) + { + IFragment prev = null; + for (var i = 0; i < lst.Count; i++) + { + var cur = lst[i]; + if (prev != null) + { + if (i != 0 && cur is Literal && string.IsNullOrEmpty(((Literal)cur).Value)) + { + lst.RemoveAt(i); + i--; + continue; + } + + if (prev is Literal && cur is Literal) + { + var s1 = ((Literal)prev).Value; + var s2 = ((Literal)cur).Value; + + var joinchar = s1.EndsWith("/", StringComparison.Ordinal) || s2.EndsWith("/", StringComparison.Ordinal) ? "/" : ""; + var s3 = s1.TrimEnd(new[] { '/' }) + joinchar + s2.TrimStart(new[] { '/' }); + + prev = lst[i - 1] = new Literal(s3, ((Literal)prev).IsCaseSensitive, null); + + // Remove it and continue + lst.RemoveAt(i); + i--; + continue; + } + else if (prev is Literal && cur is Result) + { + var s = ((Literal)prev).Value.TrimEnd(new[] { '/' }); + + // Fixup if we attempt to remove the root slash + if (lst.Count == 2 && s.Length == 0) + s += '/'; + + if (string.IsNullOrEmpty(s)) + lst.RemoveAt(i - 1); + else + prev = lst[i - 1] = new Literal(s, ((Literal)prev).IsCaseSensitive, null); + continue; + } + } + + prev = cur; + } + + return lst; + } + + /// + /// Constructs a new route by pruning this instance + /// + /// The pruned route. + public RouteParser PrunePath() + { + return new RouteParser(LinkList(PruneList(BuildList(this.m_root)))); + } + + /// + /// Bind the named variable(s) to the given value + /// + /// The name of the variable to bind. + /// The literal value to bind to. + /// If set to true, compares are performed case sensitive. + /// If set to true, binding is done with literal values. + public RouteParser Bind(string name, string value, bool iscasesensitive, bool asliteral) + { + var lst = BuildList(this.m_root); + for (var i = 0; i < lst.Count; i++) + { + var x = lst[i]; + if (x is Variable && ((Variable)x).Name == name) + { + if (asliteral) + lst[i] = new Literal(value, iscasesensitive, x.Children); + else + lst[i] = new BoundVariable(name, value, iscasesensitive, x.Children); + + //break; // If we want a single match + } + } + + var rp = new RouteParser(LinkList(lst)); + + return rp; + } + + /// + /// Gets the default value for a variable from this route + /// + /// The default value. + /// The name of the variable. + public string GetDefaultValue(string name) + { + var r = this.m_root; + while (r != null) + { + if (r is Variable && ((Variable)r).Name == name) + return ((Variable)r).DefaultValue; + + if (r.Children == null) + r = null; + else if (r.Children.Length != 1) + throw new Exception("Cannot search choice entry"); + else if (r.Children.First() is Result) + r = null; + else + r = r.Children.First(); + } + + return null; + } + + public IEnumerable> Variables + { + get + { + var lst = BuildList(this.m_root); + return + lst + .Where(x => x is Variable) + .Select(x => new KeyValuePair(((Variable)x).Name, ((Variable)x).Optional)) + .Union( + lst + .Where(x => x is BoundVariable) + .Select(x => new KeyValuePair(((BoundVariable)x).Name, false)) + ) + .Distinct(x => x.Key) + ; + } + } + + /// + /// Replaces the target entry with one based on the given input + /// + /// The new route. + /// The controller to use. + /// The method to call. + /// The accepted verbs. + public RouteParser ReplaceTarget(Controller controller, System.Reflection.MethodInfo method, string[] verbs) + { + var lst = BuildList(this.m_root); + lst = lst.Take(lst.Count - 1).ToList(); + lst.Add(new Result(new RouteEntry(controller, method, verbs, Variables))); + return new RouteParser(LinkList(lst)); + } + + /// + /// Returns a string-like representation of this entry + /// + public string Path { get { return CloneList(m_root, x => (x is Result) ? null : x).ToString(); } } + + /// + /// Returns a that represents the current . + /// + /// A that represents the current . + public override string ToString() + { + return string.Join(Environment.NewLine, GetAllRoutes()); + } + + /// + /// Enumerates all routes and builds a path-like string for each path + /// + /// The strings representing the routes. + private IEnumerable GetAllRoutes() + { + var s = new Stack>(); + s.Push(new KeyValuePair(string.Empty, m_root)); + + while (s.Count > 0) + { + var c = s.Pop(); + var str = c.Key; + if (c.Value is Literal) + str += ((Literal)c.Value).Value; + else if (c.Value is Variable) + str += "{" + ((Variable)c.Value).Name + "}"; + else if (c.Value is BoundVariable) + str += "{" + ((BoundVariable)c.Value).Name + "}"; + else if (c.Value is Result) + str += ((Result)c.Value).ToString(); + else if (!(c.Value is Choice)) + throw new Exception(string.Format("Unable to work with {0}", c.Value.GetType())); + + if (c.Value.Children == null) + yield return str; + else + foreach (var n in c.Value.Children) + s.Push(new KeyValuePair(str, n)); + + + } + } + } } diff --git a/libraries/MTConnect.NET-HTTP/Clients/MTConnectHttpClient.cs b/libraries/MTConnect.NET-HTTP/Clients/MTConnectHttpClient.cs index a63328394..f3ec94e84 100644 --- a/libraries/MTConnect.NET-HTTP/Clients/MTConnectHttpClient.cs +++ b/libraries/MTConnect.NET-HTTP/Clients/MTConnectHttpClient.cs @@ -653,7 +653,7 @@ private async Task Worker() if (probe != null) { _lastResponse = UnixDateTime.Now; - ResponseReceived?.Invoke(this, new EventArgs()); + ResponseReceived?.Invoke(this, new EventArgs()); ProcessProbeDocument(probe); @@ -735,7 +735,7 @@ private async Task Worker() // Run Stream (Blocking call) await _stream.Run(_stop.Token); } - + initialRequest = false; if (!_stop.Token.IsCancellationRequested) @@ -1176,6 +1176,11 @@ private async void CheckAssetChanged(IEnumerable observations, Can } + /// + /// Builds the agent base URL string (without trailing slash) by appending + /// to when the port is positive. + /// Returns null for null or empty . + /// public static string CreateUrl(string hostname, int port) { if (!string.IsNullOrEmpty(hostname)) diff --git a/libraries/MTConnect.NET-HTTP/Clients/MTConnectHttpClientStream.cs b/libraries/MTConnect.NET-HTTP/Clients/MTConnectHttpClientStream.cs index d41a3002c..9fe6dc59e 100644 --- a/libraries/MTConnect.NET-HTTP/Clients/MTConnectHttpClientStream.cs +++ b/libraries/MTConnect.NET-HTTP/Clients/MTConnectHttpClientStream.cs @@ -31,6 +31,15 @@ public class MTConnectHttpClientStream : IDisposable private string _documentFormat = DocumentFormat.XML; + /// + /// Constructs an HTTP streaming reader for the MTConnect long-poll sample response + /// at . The stream assigns itself a fresh , defaults + /// the read timeout to five minutes, advertises the standard + /// on Accept-Encoding, and picks + /// the matching Accept MIME type for . + /// + /// The fully built sample URL with interval / heartbeat parameters. + /// Document format key (e.g. xml, json) to request and to parse the response with. public MTConnectHttpClientStream(string url, string documentFormat = DocumentFormat.XML) { Id = Guid.NewGuid().ToString(); @@ -44,6 +53,7 @@ public MTConnectHttpClientStream(string url, string documentFormat = DocumentFor _httpClient.Timeout = TimeSpan.FromMilliseconds(DefaultTimeout); } + /// Disposes the underlying . The stream itself should be ped first; does not cancel pending reads. public void Dispose() { if (_httpClient != null) _httpClient.Dispose(); @@ -76,23 +86,37 @@ public void Dispose() public string ContentType { get; set; } + /// Raised for every successfully parsed MTConnectStreams document received from the agent. public event EventHandler DocumentReceived; + /// Raised when the agent returns a parsed MTConnectError document (e.g. invalid sequence number, no such device). public event EventHandler ErrorReceived; + /// Raised when an incoming multipart part could not be parsed in the configured . public event EventHandler FormatError; + /// Raised for unexpected exceptions inside the stream pump (parsing, timer callbacks, dispatch); the loop tries to keep running. public event EventHandler InternalError; + /// Raised for transport-level failures (DNS, refused connection, TLS error) while opening or reading the HTTP response. public event EventHandler ConnectionError; + /// Raised before the background read task is scheduled. public event EventHandler Starting; + /// Raised once the background read task has begun consuming the response body. public event EventHandler Started; + /// Raised when is invoked, before the cancellation token is cancelled. public event EventHandler Stopping; + /// Raised after the background read task has exited cleanly. public event EventHandler Stopped; + /// + /// Starts the background read loop. is wired so that + /// the stream stops cleanly when the caller's token is cancelled; can + /// also be called directly. Raises before the task is scheduled. + /// public void Start(CancellationToken cancellationToken) { _stop = new CancellationTokenSource(); @@ -104,6 +128,11 @@ public void Start(CancellationToken cancellationToken) _ = Task.Run(() => Run(_stop.Token)); } + /// + /// Signals the background read loop to exit. Raises first, then + /// cancels the internal token. is raised by the background task + /// when it finally returns. + /// public void Stop() { // Raise Stopping Event @@ -113,6 +142,14 @@ public void Stop() } + /// + /// The background read loop: opens the long-poll sample request to + /// , parses each MIME multipart part as an MTConnect document, raises + /// the appropriate / event, + /// and continues until is cancelled or the agent + /// closes the response. Transport failures raise ; the loop + /// then reconnects after a short delay so transient outages do not require restart. + /// public async Task Run(CancellationToken cancellationToken) { if (!string.IsNullOrEmpty(Url)) @@ -350,6 +387,15 @@ private static Stream ReadBody(Stream stream, int length) return null; } + /// + /// Decompresses according to + /// (the agent's Content-Encoding response header) and dispatches the resulting + /// MTConnect document to , , or + /// depending on the document type. Override to inject custom + /// per-part processing while preserving the standard event surface. + /// + /// A single multipart part containing one formatted MTConnect document. + /// The agent-reported content encoding, or null when the part is uncompressed. protected virtual void ProcessResponseBody(Stream responseBody, string contentEncoding = null) { if (responseBody != null && responseBody.Length > 0) diff --git a/libraries/MTConnect.NET-HTTP/Clients/MTConnectHttpCurrentClient.cs b/libraries/MTConnect.NET-HTTP/Clients/MTConnectHttpCurrentClient.cs index a18b905ff..f77cd5cd7 100644 --- a/libraries/MTConnect.NET-HTTP/Clients/MTConnectHttpCurrentClient.cs +++ b/libraries/MTConnect.NET-HTTP/Clients/MTConnectHttpCurrentClient.cs @@ -266,10 +266,23 @@ public async Task GetAsync(CancellationToken cancellat } + /// Builds the current request URI from the client's own , , , , and . public Uri CreateUri() => CreateUri(Authority, Device, Path, At, DocumentFormat); + /// Convenience overload that passes 0 for , taking the port from if present. + /// Agent base URL or hostname. + /// Optional device key; null requests an agent-scoped current. + /// Optional XPath/JSONPath filter (becomes the path query parameter). + /// The sequence number to snapshot at (at query parameter); 0 means unset. + /// Optional document format (documentFormat query parameter). public static Uri CreateUri(string hostname, string device = null, string path = null, long at = 0, string documentFormat = null) => CreateUri(hostname, 0, device, path, at, documentFormat); + /// + /// Builds the absolute current request URI. Combines + /// (with appended if positive) and the + /// segment, then adds /current together with the standard query parameters + /// path, at, and documentFormat for the supplied non-default values. + /// public static Uri CreateUri(string hostname, int port, string device = null, string path = null, long at = 0, string documentFormat = null) { if (!string.IsNullOrEmpty(hostname)) diff --git a/libraries/MTConnect.NET-HTTP/Clients/MTConnectHttpProbeClient.cs b/libraries/MTConnect.NET-HTTP/Clients/MTConnectHttpProbeClient.cs index d40d36642..3fb848a1a 100644 --- a/libraries/MTConnect.NET-HTTP/Clients/MTConnectHttpProbeClient.cs +++ b/libraries/MTConnect.NET-HTTP/Clients/MTConnectHttpProbeClient.cs @@ -30,6 +30,15 @@ static MTConnectHttpProbeClient() _httpClient.Timeout = TimeSpan.FromMilliseconds(DefaultTimeout); } + /// + /// Resolves to its first IPv4 address using DNS. Used + /// when callers need the agent's numeric address (for instance to constrain TLS hostname + /// verification or to record the actual endpoint in logs). Catches and swallows DNS errors, + /// returning false with set to null. + /// + /// Hostname, URL, or already-numeric address to resolve. + /// On success the resolved IPv4 address; on failure null. + /// true if at least one IPv4 record was returned; otherwise false. public static bool GetResolvedConnecionIPAddress(string serverNameOrURL, out IPAddress resolvedIPAddress) { bool isResolved = false; @@ -215,7 +224,7 @@ public IDevicesResponseDocument Get() // Create Uri and Send Request #if NET5_0_OR_GREATER - using (var response = _httpClient.Send(request)) + using (var response = _httpClient.Send(request)) #else using (var response = _httpClient.SendAsync(request).Result) #endif @@ -304,10 +313,21 @@ public async Task GetAsync(CancellationToken cancellat } + /// Builds the probe request URI from the client's own , , and . public Uri CreateUri() => CreateUri(Authority, Device, DocumentFormat); + /// Convenience overload that passes 0 for , taking the port from if present. + /// Agent base URL or hostname. + /// Optional device key; null requests the agent-scoped probe. + /// Optional document format (documentFormat query parameter). public static Uri CreateUri(string hostname, string device = null, string documentFormat = null) => CreateUri(hostname, 0, device, documentFormat); + /// + /// Builds the absolute probe request URI. Combines + /// (with appended if positive) and the + /// segment, then adds /probe together with the documentFormat query + /// parameter when supplied. + /// public static Uri CreateUri(string hostname, int port, string device = null, string documentFormat = null) { if (!string.IsNullOrEmpty(hostname)) diff --git a/libraries/MTConnect.NET-HTTP/Clients/MTConnectHttpSampleClient.cs b/libraries/MTConnect.NET-HTTP/Clients/MTConnectHttpSampleClient.cs index 10c58491b..a0da5520f 100644 --- a/libraries/MTConnect.NET-HTTP/Clients/MTConnectHttpSampleClient.cs +++ b/libraries/MTConnect.NET-HTTP/Clients/MTConnectHttpSampleClient.cs @@ -283,10 +283,26 @@ public async Task GetAsync(CancellationToken cancel) } + /// Builds the sample request URI from the client's own , , , , , , and . public Uri CreateUri() => CreateUri(Authority, Device, Path, From, To, Count, DocumentFormat); + /// Convenience overload that passes 0 for , so the port is taken from if it carries one. + /// Agent base URL or hostname. + /// Optional device key; null requests an agent-scoped sample. + /// Optional XPath/JSONPath filter (becomes the path query parameter). + /// The starting sequence number (from query parameter); 0 means unset. + /// The ending sequence number (to query parameter); 0 means unset. + /// The maximum number of observations (count query parameter); 0 means unset. + /// Optional document format (documentFormat query parameter). public static Uri CreateUri(string hostname, string device = null, string path = null, long from = 0, long to = 0, long count = 0, string documentFormat = null) => CreateUri(hostname, 0, device, path, from, to, count, documentFormat); + /// + /// Builds the absolute sample request URI. Combines + /// (with appended if positive) and the + /// segment, then adds /sample together with the standard MTConnect query + /// parameters path, from, to, count, and documentFormat + /// for the supplied non-default values. + /// public static Uri CreateUri(string hostname, int port, string device = null, string path = null, long from = 0, long to = 0, long count = 0, string documentFormat = null) { if (!string.IsNullOrEmpty(hostname)) diff --git a/libraries/MTConnect.NET-HTTP/Configurations/HttpClientConfiguration.cs b/libraries/MTConnect.NET-HTTP/Configurations/HttpClientConfiguration.cs index c48ddac3f..372efe998 100644 --- a/libraries/MTConnect.NET-HTTP/Configurations/HttpClientConfiguration.cs +++ b/libraries/MTConnect.NET-HTTP/Configurations/HttpClientConfiguration.cs @@ -46,19 +46,25 @@ public string Id public int Port { get; set; } /// - /// + /// The polling/streaming interval in milliseconds. For polling clients this is the wait + /// between successive current/sample requests; for streaming clients it is + /// the interval query parameter sent to the agent's sample long-poll. /// [JsonPropertyName("interval")] public int Interval { get; set; } /// - /// + /// The streaming heartbeat in milliseconds passed to the agent as the heartbeat + /// query parameter on sample long-poll requests. The agent emits an empty document + /// each heartbeat to keep the HTTP connection alive when no observations are produced. /// [JsonPropertyName("heartbeat")] public int Heartbeat { get; set; } /// - /// + /// When true, the client connects to the agent over https://; when false, over + /// http://. Any explicit scheme already present in is + /// rewritten to match this flag. /// [JsonPropertyName("useSSL")] public bool UseSSL { get; set; } @@ -82,6 +88,11 @@ public string Id public bool UseStreaming { get; set; } + /// + /// Initialises a new client configuration with the MTConnect-default port (5000), a 500 ms + /// interval, a 1000 ms heartbeat, connection-information output enabled, streaming sampling + /// enabled, and current-only mode disabled. + /// public HttpClientConfiguration() { Port = 5000; @@ -93,6 +104,12 @@ public HttpClientConfiguration() } + /// + /// Builds the agent base URI (scheme + host + port, no trailing slash, no path) from a + /// configuration instance. Any pre-existing http:// or https:// prefix in + /// is stripped and replaced according to . + /// Returns null if is null. + /// public static string CreateBaseUri(HttpClientConfiguration configuration) { if (configuration != null) diff --git a/libraries/MTConnect.NET-HTTP/Configurations/HttpServerConfiguration.cs b/libraries/MTConnect.NET-HTTP/Configurations/HttpServerConfiguration.cs index 0a6978bc7..2ca82fbfa 100644 --- a/libraries/MTConnect.NET-HTTP/Configurations/HttpServerConfiguration.cs +++ b/libraries/MTConnect.NET-HTTP/Configurations/HttpServerConfiguration.cs @@ -9,6 +9,12 @@ namespace MTConnect.Configurations { + /// + /// Default implementation deserialised from the + /// agent's JSON/YAML configuration. The class also exposes the + /// shadow property that captures the textual form of + /// for round-tripping through configuration files. + /// public class HttpServerConfiguration : IHttpServerConfiguration { /// @@ -76,6 +82,12 @@ public IEnumerable ResponseCompression } } + /// + /// The textual round-tripping companion of . Holds the + /// raw enum names (e.g. Gzip, Deflate, Br) as they appear in the + /// agent's JSON/YAML configuration; projects this list + /// to the strongly-typed enum. + /// [JsonPropertyName("responseCompression")] [YamlMember(Alias = "responseCompression")] public IEnumerable ResponseCompressionString { get; set; } @@ -132,6 +144,13 @@ public IEnumerable ResponseCompression public IEnumerable Files { get; set; } + /// + /// Initialises a new server configuration with sensible defaults: bind to the MTConnect + /// default port 5000, no explicit hostname (listen on all interfaces), XML as the default + /// document format, the standard text/xml / application/xml / application/json + /// accept-header mappings, indented output, no comments, PUT/POST disallowed, and validation + /// level . + /// public HttpServerConfiguration() { Server = null; diff --git a/libraries/MTConnect.NET-HTTP/Configurations/IHttpClientConfiguration.cs b/libraries/MTConnect.NET-HTTP/Configurations/IHttpClientConfiguration.cs index e6cb4446b..a66c2bf1d 100644 --- a/libraries/MTConnect.NET-HTTP/Configurations/IHttpClientConfiguration.cs +++ b/libraries/MTConnect.NET-HTTP/Configurations/IHttpClientConfiguration.cs @@ -26,7 +26,7 @@ public interface IHttpClientConfiguration /// /// The port to connect to the client MTConnect Agent. /// - int Port { get; } + int Port { get; } /// /// diff --git a/libraries/MTConnect.NET-HTTP/Configurations/IHttpServerConfiguration.cs b/libraries/MTConnect.NET-HTTP/Configurations/IHttpServerConfiguration.cs index 8f214bf88..687caa899 100644 --- a/libraries/MTConnect.NET-HTTP/Configurations/IHttpServerConfiguration.cs +++ b/libraries/MTConnect.NET-HTTP/Configurations/IHttpServerConfiguration.cs @@ -7,6 +7,12 @@ namespace MTConnect.Configurations { + /// + /// The transport-level settings consumed by the MTConnect HTTP server: bind address, TLS, + /// accepted document formats, response compression, PUT/POST policy, default schema version, + /// default output behaviour, validation level, and the optional list of static files served + /// alongside MTConnect responses. + /// public interface IHttpServerConfiguration { /// diff --git a/libraries/MTConnect.NET-HTTP/Devices/HttpAdapterComponent.cs b/libraries/MTConnect.NET-HTTP/Devices/HttpAdapterComponent.cs index fa4f093c7..83c246bb5 100644 --- a/libraries/MTConnect.NET-HTTP/Devices/HttpAdapterComponent.cs +++ b/libraries/MTConnect.NET-HTTP/Devices/HttpAdapterComponent.cs @@ -12,8 +12,10 @@ namespace MTConnect.Devices.Components /// public class HttpAdapterComponent : AdapterComponent { + /// The agent base URI (scheme + host + port, no path) the HTTP adapter targets, as produced by . public string BaseUri { get; set; } + /// The full device-scoped URI under the agent ( + the configured deviceKey) that this adapter component reports. public string Uri { get; set; } diff --git a/libraries/MTConnect.NET-HTTP/HttpContentEncoding.cs b/libraries/MTConnect.NET-HTTP/HttpContentEncoding.cs index 7aea70dec..a0571512a 100644 --- a/libraries/MTConnect.NET-HTTP/HttpContentEncoding.cs +++ b/libraries/MTConnect.NET-HTTP/HttpContentEncoding.cs @@ -3,12 +3,32 @@ namespace MTConnect.Http { + /// + /// Enumerates the HTTP content encodings that an MTConnect client may request from the agent + /// through the Accept-Encoding request header. Each value corresponds to one of the + /// IANA-registered HTTP content-coding tokens that the agent's HTTP transport can apply to + /// MTConnect response payloads (probe, current, sample, and asset documents). + /// public enum HttpContentEncoding { + /// + /// The gzip content coding (RFC 1952). Universally supported across .NET targets + /// via . + /// Gzip, + + /// + /// The deflate content coding (RFC 1951 raw deflate stream as described by RFC 7230 + /// for HTTP). Supported on all .NET targets through . + /// Deflate, #if NET5_0_OR_GREATER + /// + /// The br Brotli content coding (RFC 7932). Only emitted on .NET 5.0 or newer where + /// is available; older target frameworks + /// omit this member from the enum. + /// Br #endif } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-HTTP/HttpContentEncodings.cs b/libraries/MTConnect.NET-HTTP/HttpContentEncodings.cs index 9bdc58dc7..8f660236d 100644 --- a/libraries/MTConnect.NET-HTTP/HttpContentEncodings.cs +++ b/libraries/MTConnect.NET-HTTP/HttpContentEncodings.cs @@ -5,19 +5,35 @@ namespace MTConnect.Http { + /// + /// Constants and presets that describe the HTTP content codings recognised by the MTConnect + /// HTTP transport. The string constants are the canonical lower-case tokens used in the + /// Accept-Encoding and Content-Encoding headers, and the default-accept list is + /// what clients advertise when they have no explicit preference. + /// public static class HttpContentEncodings { - public static readonly IEnumerable DefaultAccept = new List - { - HttpContentEncoding.Gzip, + /// + /// The default Accept-Encoding set that an MTConnect HTTP client sends when no + /// override is supplied. The list is ordered by preference: gzip, deflate, + /// and on .NET 5.0+ br. Servers should pick the first member they can produce. + /// + public static readonly IEnumerable DefaultAccept = new List + { + HttpContentEncoding.Gzip, HttpContentEncoding.Deflate, #if NET5_0_OR_GREATER - HttpContentEncoding.Br + HttpContentEncoding.Br #endif }; + /// The literal gzip token used in HTTP Content-Encoding / Accept-Encoding headers. public const string Gzip = "gzip"; + + /// The literal deflate token used in HTTP Content-Encoding / Accept-Encoding headers. public const string Deflate = "deflate"; + + /// The literal br token (Brotli, RFC 7932) used in HTTP Content-Encoding / Accept-Encoding headers. public const string Brotli = "br"; } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-HTTP/HttpHeaders.cs b/libraries/MTConnect.NET-HTTP/HttpHeaders.cs index 6348e88db..8a4b83115 100644 --- a/libraries/MTConnect.NET-HTTP/HttpHeaders.cs +++ b/libraries/MTConnect.NET-HTTP/HttpHeaders.cs @@ -3,13 +3,28 @@ namespace MTConnect.Http { + /// + /// Canonical string constants for the HTTP request and response headers that the MTConnect + /// HTTP transport reads and writes when negotiating document format and payload compression. + /// Using these constants in place of raw literals keeps spelling and capitalisation consistent + /// between client () and server + /// () code paths. + /// public static class HttpHeaders { + /// The Accept request header — used by clients to advertise the MTConnect document format (XML, JSON, etc.) they prefer. public const string Accept = "Accept"; + + /// The Accept-Encoding request header — used by clients to advertise the content codings (gzip, deflate, br) they can decode. public const string AcceptEncoding = "Accept-Encoding"; + /// The Content-encoding response header — set by the server to identify the content coding actually applied to the payload. public const string ContentEncoding = "Content-encoding"; + + /// The Content-type response header — set by the server to identify the MIME type of the MTConnect document (e.g. application/xml, application/json). public const string ContentType = "Content-type"; + + /// The Content-length response header — set by the server to the size in bytes of the encoded response body. public const string ContentLength = "Content-length"; } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-HTTP/HttpResponseCompression.cs b/libraries/MTConnect.NET-HTTP/HttpResponseCompression.cs index 3a34960a8..890f4e754 100644 --- a/libraries/MTConnect.NET-HTTP/HttpResponseCompression.cs +++ b/libraries/MTConnect.NET-HTTP/HttpResponseCompression.cs @@ -3,13 +3,25 @@ namespace MTConnect.Http { + /// + /// Enumerates the response-side compression strategies that the MTConnect HTTP server applies + /// to outgoing MTConnect documents. Unlike which only lists + /// codings that imply compression, this enum also includes so that a server + /// can be configured to send payloads uncompressed regardless of what the client advertises. + /// public enum HttpResponseCompression { + /// Responses are written uncompressed; no Content-Encoding header is added. None, + + /// Responses are compressed with gzip (RFC 1952) when the client's Accept-Encoding permits it. Gzip, + + /// Responses are compressed with the HTTP deflate coding when the client's Accept-Encoding permits it. Deflate, #if NET5_0_OR_GREATER + /// Responses are compressed with Brotli (br, RFC 7932) when the client's Accept-Encoding permits it. Only available on .NET 5.0 or newer. Br #endif } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-HTTP/MTConnectRequestType.cs b/libraries/MTConnect.NET-HTTP/MTConnectRequestType.cs index e685469fc..4492b5e0e 100644 --- a/libraries/MTConnect.NET-HTTP/MTConnectRequestType.cs +++ b/libraries/MTConnect.NET-HTTP/MTConnectRequestType.cs @@ -3,12 +3,27 @@ namespace MTConnect.Http { + /// + /// String constants for the MTConnect HTTP request types as defined by Part 1 of the MTConnect + /// Standard. These are the leading path segments that an MTConnect agent recognises (for + /// example http://agent/probe or http://agent/device/sample) and that this + /// library uses to dispatch incoming requests to the appropriate response builder. + /// public static class MTConnectRequestType { + /// The MTConnect probe request — returns an MTConnectDevices response document describing the device model. public const string Probe = "probe"; + + /// The MTConnect current request — returns an MTConnectStreams document with the most recent observation for each data item. public const string Current = "current"; + + /// The MTConnect sample request — returns an MTConnectStreams document with the time-ordered observations between two sequence numbers. public const string Sample = "sample"; + + /// The MTConnect assets request — returns an MTConnectAssets document with multiple assets that match the supplied filter. public const string Assets = "assets"; + + /// The MTConnect asset request — returns an MTConnectAssets document for a single asset identified by its assetId. public const string Asset = "asset"; } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-HTTP/OutputValidationLevel.cs b/libraries/MTConnect.NET-HTTP/OutputValidationLevel.cs index 19250d24b..eea423fb6 100644 --- a/libraries/MTConnect.NET-HTTP/OutputValidationLevel.cs +++ b/libraries/MTConnect.NET-HTTP/OutputValidationLevel.cs @@ -3,10 +3,21 @@ namespace MTConnect.Http { + /// + /// Controls how aggressively the MTConnect HTTP server validates outgoing response documents + /// against the configured MTConnect schema version before they are written to the wire. + /// Strict validation gives the strongest conformance guarantees at the cost of per-response + /// CPU; the looser modes trade that for throughput. + /// public enum OutputValidationLevel { + /// Skip schema validation entirely; the agent emits documents as built without further checks. Ignore, + + /// Validate each outgoing document and log any failures, but still return the response to the client. Warning, + + /// Validate each outgoing document and refuse to return responses that fail validation (the client receives an error). Strict } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-HTTP/README.md b/libraries/MTConnect.NET-HTTP/README.md index 4728302ac..fd6d56f0d 100644 --- a/libraries/MTConnect.NET-HTTP/README.md +++ b/libraries/MTConnect.NET-HTTP/README.md @@ -1,7 +1,9 @@ ![MTConnect.NET Logo](https://raw.githubusercontent.com/TrakHound/MTConnect.NET/master/img/mtconnect-net-03-md.png) # MTConnect.NET-HTTP -Classes to implement HTTP Clients & Servers for MTConnect +Classes to implement HTTP Clients & Servers for MTConnect. + +For the HTTP server / adapter module pages and end-to-end configuration recipes, see [docs/modules](../../docs/modules/) and [docs/configure](../../docs/configure/). ## Nuget
diff --git a/libraries/MTConnect.NET-HTTP/Servers/MTConnectAssetInputArgs.cs b/libraries/MTConnect.NET-HTTP/Servers/MTConnectAssetInputArgs.cs index 618de1674..d4d766ad0 100644 --- a/libraries/MTConnect.NET-HTTP/Servers/MTConnectAssetInputArgs.cs +++ b/libraries/MTConnect.NET-HTTP/Servers/MTConnectAssetInputArgs.cs @@ -1,18 +1,28 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Servers { + /// + /// Carries the inputs of a PUT-style request that adds or updates a single asset on + /// the MTConnect agent. The structure is filled in by the HTTP transport from the request + /// route, query string, and body, then handed to the agent's asset-handling pipeline. + /// public struct MTConnectAssetInputArgs { + /// The MTConnect assetId targeted by the request (typically the last path segment of the asset URL). public string AssetId { get; set; } + /// The MTConnect asset type (e.g. CuttingTool, Pallet) supplied with the request and used to dispatch to the matching deserialiser. public string AssetType { get; set; } + /// The device key (UUID or name) the asset is associated with; empty if the asset is unattached. public string DeviceKey { get; set; } + /// The MTConnect document format of the request body (e.g. xml, json), used to pick the asset deserialiser. public string DocumentFormat { get; set; } + /// The raw HTTP request body containing the serialised asset document. public byte[] RequestBody { get; set; } } } diff --git a/libraries/MTConnect.NET-HTTP/Servers/MTConnectAssetResponseHandler.cs b/libraries/MTConnect.NET-HTTP/Servers/MTConnectAssetResponseHandler.cs index 6a2792e81..891d34f2c 100644 --- a/libraries/MTConnect.NET-HTTP/Servers/MTConnectAssetResponseHandler.cs +++ b/libraries/MTConnect.NET-HTTP/Servers/MTConnectAssetResponseHandler.cs @@ -13,6 +13,15 @@ namespace MTConnect.Servers { + /// + /// Ceen request handler for the single-asset MTConnect endpoint + /// (GET /asset/{assetId}). Returns an MTConnectAssets Response + /// Document containing the asset identified by the trailing path + /// segment, or an MTConnectError document with status 404 when no + /// such asset exists. The response document format is negotiated + /// via the documentFormat query parameter (xml | json | + /// json-cppagent) and defaults to XML. + /// class MTConnectAssetResponseHandler : MTConnectHttpResponseHandler { public MTConnectAssetResponseHandler(IHttpServerConfiguration serverConfiguration, IMTConnectAgentBroker mtconnectAgent) : base(serverConfiguration, mtconnectAgent) { } diff --git a/libraries/MTConnect.NET-HTTP/Servers/MTConnectAssetsResponseHandler.cs b/libraries/MTConnect.NET-HTTP/Servers/MTConnectAssetsResponseHandler.cs index e86cb2055..3c066ec15 100644 --- a/libraries/MTConnect.NET-HTTP/Servers/MTConnectAssetsResponseHandler.cs +++ b/libraries/MTConnect.NET-HTTP/Servers/MTConnectAssetsResponseHandler.cs @@ -13,6 +13,16 @@ namespace MTConnect.Servers { + /// + /// Ceen request handler for the MTConnect Assets endpoint + /// (GET /assets and GET /{deviceKey}/assets). Returns an + /// MTConnectAssets Response Document containing the asset records + /// known to the agent. The optional leading path segment scopes the + /// response to assets owned by a specific device; the type, removed, + /// and count query parameters filter the asset set; documentFormat + /// (xml | json | json-cppagent, default XML) and indentOutput + /// negotiate the rendered representation. + /// class MTConnectAssetsResponseHandler : MTConnectHttpResponseHandler { public MTConnectAssetsResponseHandler(IHttpServerConfiguration serverConfiguration, IMTConnectAgentBroker mtconnectAgent) : base(serverConfiguration, mtconnectAgent) { } diff --git a/libraries/MTConnect.NET-HTTP/Servers/MTConnectCurrentResponseHandler.cs b/libraries/MTConnect.NET-HTTP/Servers/MTConnectCurrentResponseHandler.cs index 88fd40b33..b672cd8ff 100644 --- a/libraries/MTConnect.NET-HTTP/Servers/MTConnectCurrentResponseHandler.cs +++ b/libraries/MTConnect.NET-HTTP/Servers/MTConnectCurrentResponseHandler.cs @@ -12,6 +12,20 @@ namespace MTConnect.Servers.Http { + /// + /// Ceen request handler for the MTConnect Current endpoint + /// (GET /current and GET /{deviceKey}/current). Returns an + /// MTConnectStreams Response Document containing the current + /// observation snapshot for every data item visible to the agent, + /// optionally filtered by an XPath in the path query parameter and + /// anchored to a sequence number via at. When interval is supplied, + /// the handler upgrades the response to a multipart + /// x-mixed-replace stream and emits a fresh snapshot every interval + /// milliseconds, interleaved with heartbeats. The response document + /// format is negotiated via documentFormat (xml | json | + /// json-cppagent), defaulting to XML; deviceType, version, + /// indentOutput, and outputComments further shape the payload. + /// class MTConnectCurrentResponseHandler : MTConnectHttpResponseHandler { private const int _minimumHeartbeat = 500; // 500 ms diff --git a/libraries/MTConnect.NET-HTTP/Servers/MTConnectFormatOptionsArgs.cs b/libraries/MTConnect.NET-HTTP/Servers/MTConnectFormatOptionsArgs.cs index 1f02a5ff1..16c683de9 100644 --- a/libraries/MTConnect.NET-HTTP/Servers/MTConnectFormatOptionsArgs.cs +++ b/libraries/MTConnect.NET-HTTP/Servers/MTConnectFormatOptionsArgs.cs @@ -1,18 +1,30 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. using System; namespace MTConnect.Servers { + /// + /// Context passed to format-option providers (registered through the formatter extension + /// points) so they can decide which serialisation knobs apply to a particular MTConnect + /// response. The HTTP server populates this once per outgoing response. + /// public struct MTConnectFormatOptionsArgs { + /// The MTConnect request type being formatted (see ). public string RequestType { get; set; } + /// The document format key (e.g. xml, json) that will be produced. public string DocumentFormat { get; set; } + /// The MTConnect schema version that should be honoured when serialising the document. public Version MTConnectVersion { get; set; } + /// + /// The numeric mapping of that tells + /// the formatter how strictly to validate the produced document. + /// public int ValidationLevel { get; set; } } } diff --git a/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpRequests.cs b/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpRequests.cs index e547ef6ad..b78a448ac 100644 --- a/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpRequests.cs +++ b/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpRequests.cs @@ -25,10 +25,10 @@ public static class MTConnectHttpRequests /// Flags used for Formatting the Response /// An MTConnectHttpResponse public static MTConnectHttpResponse GetProbeRequest( - IMTConnectAgentBroker mtconnectAgent, + IMTConnectAgentBroker mtconnectAgent, string deviceType = null, Version mtconnectVersion = null, - string documentFormat = DocumentFormat.XML, + string documentFormat = DocumentFormat.XML, IEnumerable> formatOptions = null ) { @@ -80,7 +80,7 @@ public static MTConnectHttpResponse GetProbeRequest( /// Flags used for Formatting the Response /// An MTConnectHttpResponse public static MTConnectHttpResponse GetDeviceProbeRequest( - IMTConnectAgentBroker mtconnectAgent, + IMTConnectAgentBroker mtconnectAgent, string deviceKey, Version mtconnectVersion = null, string documentFormat = DocumentFormat.XML, @@ -493,8 +493,8 @@ public static MTConnectHttpResponse GetDeviceSampleRequest( IEnumerable> formatOptions = null ) { - var stpw = Stopwatch.StartNew(); - + var stpw = Stopwatch.StartNew(); + // Get list of DataItem ID's based on Path (XPath) parameter var dataItemIds = PathProcessor.GetDataItemIds(mtconnectAgent, path, documentFormat); diff --git a/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpResponse.cs b/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpResponse.cs index e73eb7db5..db483564f 100644 --- a/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpResponse.cs +++ b/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpResponse.cs @@ -11,29 +11,55 @@ namespace MTConnect.Servers.Http { + /// + /// The HTTP-transport-ready result of formatting one MTConnect response document. The struct + /// captures the formatted byte stream together with the negotiated content type, the HTTP + /// status code to return, formatter diagnostics, and timing metrics so the host can both + /// write the response and report transport-level instrumentation. + /// public struct MTConnectHttpResponse { + /// True when the document was formatted without unrecoverable errors; false sets to 500. public bool Success { get; set; } + /// The formatted MTConnect document, ready to be copied to the HTTP response body. public Stream Content { get; set; } + /// The MIME content type chosen by the formatter (e.g. application/xml, application/json). public string ContentType { get; set; } + /// The HTTP status code that should accompany the response (200 on success, 500 on formatter failure, or the explicit code supplied for error documents). public int StatusCode { get; set; } + /// Informational messages produced by the formatter (for example notes about applied defaults). public IEnumerable FormatMessages { get; set; } + /// Non-fatal warnings produced by the formatter (e.g. soft schema violations under Warning validation level). public IEnumerable FormatWarnings { get; set; } + /// Errors produced by the formatter (populated when is false). public IEnumerable FormatErrors { get; set; } + /// Time in milliseconds the formatter spent serialising the document. public double FormatDuration { get; set; } + /// Time in milliseconds the agent spent producing the underlying response document (excluding HTTP write). public double ResponseDuration { get; set; } + /// Time in milliseconds spent writing to the HTTP response body; filled in by the transport after the write completes. public double WriteDuration { get; set; } + /// + /// Formats a probe-style devices response document for the wire using the supplied + /// document format and format options. On success holds the encoded + /// MTConnectDevices document and is 200; otherwise 500 with + /// populated. + /// + /// The devices response document produced by the agent. + /// The document format key (e.g. xml, json) to serialise to. + /// Time in milliseconds spent building . + /// Key/value formatter options passed verbatim to the registered formatter. public MTConnectHttpResponse( IDevicesResponseDocument document, string documentFormat, @@ -66,6 +92,15 @@ IEnumerable> formatOptions } } + /// + /// Formats a current or sample streams response document for the wire. The + /// document is taken by ref because the streaming formatter may rent buffers that + /// it returns to the caller, allowing them to be released after the response is written. + /// + /// The streams response document produced by the agent. Passed by ref to allow buffer reuse. + /// The document format key to serialise to. + /// Time in milliseconds spent building . + /// Key/value formatter options passed verbatim to the registered formatter. public MTConnectHttpResponse( ref IStreamsResponseOutputDocument document, string documentFormat, @@ -98,6 +133,13 @@ IEnumerable> formatOptions } } + /// + /// Formats an assets or single asset response document for the wire. + /// + /// The assets response document produced by the agent. + /// The document format key to serialise to. + /// Time in milliseconds spent building . + /// Key/value formatter options passed verbatim to the registered formatter. public MTConnectHttpResponse( IAssetsResponseDocument document, string documentFormat, @@ -130,6 +172,16 @@ IEnumerable> formatOptions } } + /// + /// Formats an MTConnectError response document for the wire. The caller supplies + /// the HTTP status code (e.g. 400, 404) explicitly because MTConnect agents return errors + /// with a wide range of status codes that the formatter itself does not infer. + /// + /// The error response document produced by the agent. + /// The HTTP status code to use (typically 400 or 404 for client errors, 500 for server errors). + /// The document format key to serialise to. + /// Time in milliseconds spent building . + /// Key/value formatter options passed verbatim to the registered formatter. public MTConnectHttpResponse( IErrorResponseDocument document, int statusCode, @@ -163,4 +215,4 @@ IEnumerable> formatOptions } } } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs b/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs index 69088b240..fabc831dc 100644 --- a/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs +++ b/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServer.cs @@ -23,7 +23,10 @@ namespace MTConnect.Servers.Http /// public class MTConnectHttpServer : IDisposable { + /// The agent broker the server forwards parsed requests to and pulls response documents from. protected readonly IMTConnectAgentBroker _mtconnectAgent; + + /// The HTTP-transport configuration that controls bind address, TLS, encoding, accept mappings, and PUT/POST policy. protected readonly IHttpServerConfiguration _configuration; private CancellationTokenSource _stop; @@ -45,9 +48,11 @@ public class MTConnectHttpServer : IDisposable /// URL Prefix that the HttpListener is listening for requests on public event EventHandler ServerStopped; + /// Raised after the server loads its TLS certificate from ; carries the resolved . public event EventHandler ServerCertificateLoaded; + /// Raised for each diagnostic log line emitted by the underlying Ceen HTTP listener (intentionally spelled ServerLogRecevied for API compatibility). public event EventHandler ServerLogRecevied; /// @@ -72,6 +77,12 @@ public class MTConnectHttpServer : IDisposable public event EventHandler ClientException; + /// + /// Constructs the HTTP server bound to and the agent + /// reachable through . Neither object is captured for + /// later disposal; the caller continues to own both. The server itself is started by a + /// subsequent call. + /// public MTConnectHttpServer(IHttpServerConfiguration configuration, IMTConnectAgentBroker mtconnectAgent) { _mtconnectAgent = mtconnectAgent; @@ -107,6 +118,11 @@ internal virtual void OnConfigureServer(ServerConfig serverConfig) { } protected virtual List> OnCreateFormatOptions(MTConnectFormatOptionsArgs args) { return null; } + /// + /// Starts the HTTP listener on a background task. The method is non-blocking and returns + /// immediately; is raised once the listener is bound. Has no + /// effect when is null. + /// public void Start() { _stop = new CancellationTokenSource(); @@ -117,11 +133,16 @@ public void Start() } } + /// + /// Signals the listener task to shut down. is raised once the + /// background task exits. Safe to call before . + /// public void Stop() { if (_stop != null) _stop.Cancel(); } + /// Calls to release the listener; the agent broker is not disposed by this server. public void Dispose() { Stop(); } @@ -193,9 +214,9 @@ private async Task StartServer(IHttpServerConfiguration serverConfiguration, Can if (ServerStarted != null) ServerStarted.Invoke(this, endpointId); await HttpServer.ListenAsync( - endpoint, - useSsl, - config, + endpoint, + useSsl, + config, cancellationToken); } catch (Exception ex) @@ -269,26 +290,26 @@ private ServerConfig CreateServerConfig(IHttpServerConfiguration serverConfigura assetHandler.ClientException += ClientException; assetHandler.CreateFormatOptionsFunction = OnCreateFormatOptions; - // Setup the Put Request Handler - var putHandler = new MTConnectPutResponseHandler(serverConfiguration, _mtconnectAgent); - putHandler.ResponseSent += ResponseSent; - putHandler.ClientConnected += ClientConnected; - putHandler.ClientDisconnected += ClientDisconnected; - putHandler.ClientException += ClientException; - putHandler.ProcessFunction = OnObservationInput; - putHandler.CreateFormatOptionsFunction = OnCreateFormatOptions; - - // Setup the Post Request Handler - var postHandler = new MTConnectPostResponseHandler(serverConfiguration, _mtconnectAgent); - postHandler.ResponseSent += ResponseSent; - postHandler.ClientConnected += ClientConnected; - postHandler.ClientDisconnected += ClientDisconnected; - postHandler.ClientException += ClientException; - postHandler.ProcessFunction = OnAssetInput; - postHandler.CreateFormatOptionsFunction = OnCreateFormatOptions; - - // Setup the Static Request Handler - var staticHandler = new MTConnectStaticResponseHandler(serverConfiguration, _mtconnectAgent); + // Setup the Put Request Handler + var putHandler = new MTConnectPutResponseHandler(serverConfiguration, _mtconnectAgent); + putHandler.ResponseSent += ResponseSent; + putHandler.ClientConnected += ClientConnected; + putHandler.ClientDisconnected += ClientDisconnected; + putHandler.ClientException += ClientException; + putHandler.ProcessFunction = OnObservationInput; + putHandler.CreateFormatOptionsFunction = OnCreateFormatOptions; + + // Setup the Post Request Handler + var postHandler = new MTConnectPostResponseHandler(serverConfiguration, _mtconnectAgent); + postHandler.ResponseSent += ResponseSent; + postHandler.ClientConnected += ClientConnected; + postHandler.ClientDisconnected += ClientDisconnected; + postHandler.ClientException += ClientException; + postHandler.ProcessFunction = OnAssetInput; + postHandler.CreateFormatOptionsFunction = OnCreateFormatOptions; + + // Setup the Static Request Handler + var staticHandler = new MTConnectStaticResponseHandler(serverConfiguration, _mtconnectAgent); staticHandler.ResponseSent += ResponseSent; staticHandler.ClientConnected += ClientConnected; staticHandler.ClientDisconnected += ClientDisconnected; @@ -301,15 +322,15 @@ private ServerConfig CreateServerConfig(IHttpServerConfiguration serverConfigura { return await DeviceRootHandler(probeHandler, context); }); - serverConfig.AddRoute(async (context) => - { - return await PutHandler(putHandler, context); - }); + serverConfig.AddRoute(async (context) => + { + return await PutHandler(putHandler, context); + }); serverConfig.AddRoute(async (context) => { return await PostHandler(postHandler, context); }); - serverConfig.AddRoute("/", probeHandler); + serverConfig.AddRoute("/", probeHandler); serverConfig.AddRoute("/probe", probeHandler); serverConfig.AddRoute("/*/probe", probeHandler); serverConfig.AddRoute("/current", currentHandler); diff --git a/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServerStream.cs b/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServerStream.cs index 16b8d5041..f7e5a2d27 100644 --- a/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServerStream.cs +++ b/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpServerStream.cs @@ -15,6 +15,14 @@ namespace MTConnect.Servers.Http { + /// + /// Server-side pump that produces the body of an MTConnect long-poll sample response + /// (or a repeating current if is used). The stream pulls + /// fresh MTConnectStreams documents from the agent on each tick, formats them in the + /// negotiated , wraps the result in a multipart-mixed + /// chunk, and raises / so the + /// hosting HTTP framework can write the chunk to the open response. + /// public class MTConnectHttpServerStream { private const int _minInterval = 1; // 1 millisecond minimum interval @@ -39,28 +47,56 @@ public class MTConnectHttpServerStream private bool _currentOnly; + /// Unique random identifier for this stream instance; included in event payloads so multiple concurrent streams can be distinguished. public string Id => _id; + /// The MIME multipart boundary string emitted between chunks; derived from a fresh timestamp hash so each stream has its own boundary. public string Boundary => _boundary; + /// The content codings the client advertised via Accept-Encoding; the stream selects from this set when deciding whether to compress chunks. public IEnumerable AcceptEncodings => _acceptEncodings; + /// True while the worker task is running and emitting chunks; flipped to false by or once the task exits. public bool IsConnected => _isConnected; + /// Extra HTTP response headers the hosting framework should send alongside the multipart body (e.g. CORS or cache directives). public IEnumerable> Headers { get; set; } + /// Raised once the worker task begins emitting chunks; the argument is . public event EventHandler StreamStarted; + /// Raised after the worker task exits; the argument is . public event EventHandler StreamStopped; + /// Raised when the worker task aborts because of an exception; the worker then rethrows so the caller can tear down the connection. public event EventHandler StreamException; + /// Raised for each chunk that carries new observations; the args expose the formatted multipart body and the time spent producing it. public event EventHandler DocumentReceived; + /// Raised for each empty-document keep-alive chunk emitted after the configured heartbeat interval elapses with no observations. public event EventHandler HeartbeatReceived; + /// + /// Builds the server-side stream pump from the agent, device scope, and the request + /// parameters parsed from the long-poll URL (from, count, interval, + /// heartbeat, documentFormat, path-resolved DataItem ids, and + /// Accept-Encoding). The pump itself is not started until + /// or is called. + /// + /// HTTP server configuration used to pick a response compression coding. + /// The agent broker observations are read from. + /// Device key the stream is scoped to; null requests an agent-wide stream. + /// Optional filter of DataItem ids resolved from a path query parameter. + /// Initial sequence number passed to the agent; zero means start from the earliest available observation. + /// Maximum observations per chunk; zero means no per-chunk limit. + /// Polling interval in milliseconds between chunks (clamped at 1 ms minimum). + /// Heartbeat interval in milliseconds; if no observations appear within this window, an empty document is emitted instead. + /// MTConnect document format used to serialise each chunk. + /// The Accept-Encoding tokens the client offered, used to negotiate compression. + /// Additional document-format options passed through to the registered formatter. public MTConnectHttpServerStream( IHttpServerConfiguration configuration, IMTConnectAgentBroker mtconnectAgent, @@ -89,6 +125,12 @@ public MTConnectHttpServerStream( } + /// + /// Launches the streaming worker on a background task in sample mode: each tick + /// reads new observations starting from the most recent acknowledged sequence number. + /// is wired so the stream stops when the request + /// is aborted. + /// public void StartSample(CancellationToken cancellationToken) { _stop = new CancellationTokenSource(); @@ -96,11 +138,17 @@ public void StartSample(CancellationToken cancellationToken) _currentOnly = false; - _= Task.Run(Worker, _stop.Token); + _ = Task.Run(Worker, _stop.Token); _isConnected = true; } + /// + /// Launches the streaming worker on a background task in current mode: each tick + /// emits a fresh MTConnectStreams snapshot rather than incremental observations, + /// useful for periodic-refresh dashboards. stops the + /// stream when the request is aborted. + /// public void StartCurrent(CancellationToken cancellationToken) { _stop = new CancellationTokenSource(); @@ -113,12 +161,18 @@ public void StartCurrent(CancellationToken cancellationToken) _isConnected = true; } + /// Cancels the worker task and marks the stream disconnected. Safe to call from any thread, including before Start*. public void Stop() { if (_stop != null) _stop.Cancel(); _isConnected = false; } + /// + /// Synchronous equivalent of : runs the + /// worker loop on the caller's thread until is + /// cancelled. Useful for HTTP frameworks that own the response thread directly. + /// public void RunSample(CancellationToken cancellationToken) { _stop = new CancellationTokenSource(); @@ -130,6 +184,11 @@ public void RunSample(CancellationToken cancellationToken) _isConnected = true; } + /// + /// Synchronous equivalent of : emits the + /// periodic-snapshot stream on the caller's thread. must be called + /// from another thread to break the loop. + /// public void RunCurrent() { _stop = new CancellationTokenSource(); @@ -251,7 +310,7 @@ private string GetContentEncoding() if (_configuration != null && !_configuration.ResponseCompression.IsNullOrEmpty()) { // Gzip - if (_configuration.ResponseCompression.Contains(HttpResponseCompression.Gzip) && + if (_configuration.ResponseCompression.Contains(HttpResponseCompression.Gzip) && !_acceptEncodings.IsNullOrEmpty() && _acceptEncodings.Contains(HttpContentEncodings.Gzip)) { return HttpContentEncodings.Gzip; diff --git a/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpStreamArgs.cs b/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpStreamArgs.cs index 12ceb9780..a3d8f8942 100644 --- a/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpStreamArgs.cs +++ b/libraries/MTConnect.NET-HTTP/Servers/MTConnectHttpStreamArgs.cs @@ -5,15 +5,28 @@ namespace MTConnect.Servers.Http { + /// + /// One chunk of an MTConnect HTTP streaming response (the long-poll sample request with + /// interval). The server emits a sequence of these as a multipart-mixed body; each + /// instance carries the formatted MTConnect document fragment together with timing metadata + /// used to throttle and observe the stream. + /// public struct MTConnectHttpStreamArgs { + /// Identifier of the stream the chunk belongs to; used by handlers that route multiple concurrent streams. public string StreamId { get; set; } + /// The already-formatted MTConnect document bytes to write as the next multipart part. public Stream Message { get; set; } + /// The duration in milliseconds spent producing this chunk (formatter + queue wait). public double ResponseDuration { get; set; } + /// Constructs a chunk descriptor with its stream id, formatted payload, and the time taken to produce it. + /// Identifier of the stream the chunk belongs to. + /// The formatted MTConnect document to write. + /// Production duration in milliseconds. public MTConnectHttpStreamArgs(string streamId, Stream message, double responseDuration) { StreamId = streamId; @@ -21,4 +34,4 @@ public MTConnectHttpStreamArgs(string streamId, Stream message, double responseD ResponseDuration = responseDuration; } } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-HTTP/Servers/MTConnectObservationInputArgs.cs b/libraries/MTConnect.NET-HTTP/Servers/MTConnectObservationInputArgs.cs index a4616481c..6a2043c36 100644 --- a/libraries/MTConnect.NET-HTTP/Servers/MTConnectObservationInputArgs.cs +++ b/libraries/MTConnect.NET-HTTP/Servers/MTConnectObservationInputArgs.cs @@ -1,14 +1,22 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Servers { + /// + /// Carries the inputs of a PUT-style request that posts a single DataItem observation + /// to the MTConnect agent over HTTP. The HTTP transport populates this from the request path + /// and body and forwards it to the agent's observation buffer. + /// public struct MTConnectObservationInputArgs { + /// The device key (UUID or name) that owns the targeted DataItem. public string DeviceKey { get; set; } - public string DataItemKey { get; set; } + /// The DataItem identifier (id) or, where supported, its name that the observation applies to. + public string DataItemKey { get; set; } + /// The serialised observation value to record against the DataItem. public string Value { get; set; } } } diff --git a/libraries/MTConnect.NET-HTTP/Servers/MTConnectPostResponseHandler.cs b/libraries/MTConnect.NET-HTTP/Servers/MTConnectPostResponseHandler.cs index 9ed4c9e00..339739924 100644 --- a/libraries/MTConnect.NET-HTTP/Servers/MTConnectPostResponseHandler.cs +++ b/libraries/MTConnect.NET-HTTP/Servers/MTConnectPostResponseHandler.cs @@ -13,6 +13,16 @@ namespace MTConnect.Servers { + /// + /// Ceen request handler for asset ingestion over HTTP POST (POST / + /// and POST /asset/{assetId}). Accepts an asset document in the + /// request body, parses it according to the negotiated + /// documentFormat, and forwards the result to the configured + /// ProcessFunction for storage in the agent's asset buffer. The + /// response carries an HTTP status (200 on accept, 400 on malformed + /// payload, 500 on storage failure) and an optional MTConnectError + /// body when negotiated. + /// class MTConnectPostResponseHandler : MTConnectHttpResponseHandler { public Func ProcessFunction { get; set; } diff --git a/libraries/MTConnect.NET-HTTP/Servers/MTConnectProbeResponseHandler.cs b/libraries/MTConnect.NET-HTTP/Servers/MTConnectProbeResponseHandler.cs index e62bcd410..be0953bac 100644 --- a/libraries/MTConnect.NET-HTTP/Servers/MTConnectProbeResponseHandler.cs +++ b/libraries/MTConnect.NET-HTTP/Servers/MTConnectProbeResponseHandler.cs @@ -12,6 +12,17 @@ namespace MTConnect.Servers.Http { + /// + /// Ceen request handler for the MTConnect Probe endpoint + /// (GET /probe and GET /{deviceKey}/probe, plus the bare GET / + /// alias). Returns an MTConnectDevices Response Document describing + /// the device metadata visible to the agent. The optional leading + /// path segment selects a single device by name or UUID. The + /// response document format is negotiated via the documentFormat + /// query parameter (xml | json | json-cppagent) and defaults to + /// XML; deviceType, version, validationLevel, indentOutput, and + /// outputComments further shape the payload. + /// class MTConnectProbeResponseHandler : MTConnectHttpResponseHandler { public MTConnectProbeResponseHandler(IHttpServerConfiguration serverConfiguration, IMTConnectAgentBroker mtconnectAgent) : base(serverConfiguration, mtconnectAgent) { } diff --git a/libraries/MTConnect.NET-HTTP/Servers/MTConnectPutResponseHandler.cs b/libraries/MTConnect.NET-HTTP/Servers/MTConnectPutResponseHandler.cs index e67a88c78..ca4de6959 100644 --- a/libraries/MTConnect.NET-HTTP/Servers/MTConnectPutResponseHandler.cs +++ b/libraries/MTConnect.NET-HTTP/Servers/MTConnectPutResponseHandler.cs @@ -14,6 +14,16 @@ namespace MTConnect.Servers { + /// + /// Ceen request handler for the MTConnect input endpoint over HTTP + /// PUT (PUT / and PUT /{deviceKey}). Accepts data-item observation + /// input encoded as key=value pairs in the request body or query + /// string, validates the device-relative scope, and forwards each + /// pair to the configured ProcessFunction for ingestion into the + /// agent. The response carries an HTTP status (200 on accept, 400 + /// on malformed input, 404 on unknown device) and an optional + /// MTConnectError body when negotiated. + /// class MTConnectPutResponseHandler : MTConnectHttpResponseHandler { public Func ProcessFunction { get; set; } @@ -33,70 +43,70 @@ protected async override Task OnRequestReceived(IHttpCont { if (_serverConfiguration.AllowPut && (_serverConfiguration.AllowPutFrom.IsNullOrEmpty() || _serverConfiguration.AllowPutFrom.Contains(httpRequest.GetRemoteIP()))) { - if (httpRequest.QueryString != null && httpRequest.QueryString.Count > 0) - { - var urlSegments = GetUriSegments(httpRequest.Path); - - // Read DeviceKey from URL Path - var deviceKey = httpRequest.Path?.Trim('/'); - if (urlSegments.Length > 1) deviceKey = urlSegments[urlSegments.Length - 1]; - - // Get list of KeyValuePairs from Url Query - var items = new List>(); - foreach (var key in httpRequest.QueryString.Keys) - { - var urlValue = httpRequest.QueryString[key]; - if (!string.IsNullOrEmpty(urlValue)) - { - // Decode the input that was read from the URL - var value = System.Web.HttpUtility.UrlDecode(urlValue); - - // Add to list of items - items.Add(new KeyValuePair(key, value)); - } - } - - if (!items.IsNullOrEmpty()) - { - var success = false; - - foreach (var item in items) - { - if (ProcessFunction != null) - { - var args = new MTConnectObservationInputArgs(); - args.DeviceKey = deviceKey; - args.DataItemKey = item.Key; - args.Value = item.Value; - - success = ProcessFunction(args); - } - - // Call the OnObservationInput method that is intended to be overridden by a derived class - //success = OnObservationInput(deviceKey, item.Key, item.Value); - if (!success) break; - } - - if (success) - { - // Write the "" respone to the Http Response Stream - // along with a 200 Status Code - await WriteResponse("", httpResponse, HttpStatusCode.OK); - } - else - { - // Return MTConnectError Response Document along with a 404 Http Status Code - var errorDocument = _mtconnectAgent.GetErrorResponseDocument(ErrorCode.UNSUPPORTED, $"Cannot find device: {deviceKey}"); - var mtconnectResponse = new MTConnectHttpResponse(errorDocument, 404, DocumentFormat.XML, 0, null); - await WriteResponse(mtconnectResponse, httpResponse); - } - } - } - } - else - { - response.StatusCode = 403; - } + if (httpRequest.QueryString != null && httpRequest.QueryString.Count > 0) + { + var urlSegments = GetUriSegments(httpRequest.Path); + + // Read DeviceKey from URL Path + var deviceKey = httpRequest.Path?.Trim('/'); + if (urlSegments.Length > 1) deviceKey = urlSegments[urlSegments.Length - 1]; + + // Get list of KeyValuePairs from Url Query + var items = new List>(); + foreach (var key in httpRequest.QueryString.Keys) + { + var urlValue = httpRequest.QueryString[key]; + if (!string.IsNullOrEmpty(urlValue)) + { + // Decode the input that was read from the URL + var value = System.Web.HttpUtility.UrlDecode(urlValue); + + // Add to list of items + items.Add(new KeyValuePair(key, value)); + } + } + + if (!items.IsNullOrEmpty()) + { + var success = false; + + foreach (var item in items) + { + if (ProcessFunction != null) + { + var args = new MTConnectObservationInputArgs(); + args.DeviceKey = deviceKey; + args.DataItemKey = item.Key; + args.Value = item.Value; + + success = ProcessFunction(args); + } + + // Call the OnObservationInput method that is intended to be overridden by a derived class + //success = OnObservationInput(deviceKey, item.Key, item.Value); + if (!success) break; + } + + if (success) + { + // Write the "" respone to the Http Response Stream + // along with a 200 Status Code + await WriteResponse("", httpResponse, HttpStatusCode.OK); + } + else + { + // Return MTConnectError Response Document along with a 404 Http Status Code + var errorDocument = _mtconnectAgent.GetErrorResponseDocument(ErrorCode.UNSUPPORTED, $"Cannot find device: {deviceKey}"); + var mtconnectResponse = new MTConnectHttpResponse(errorDocument, 404, DocumentFormat.XML, 0, null); + await WriteResponse(mtconnectResponse, httpResponse); + } + } + } + } + else + { + response.StatusCode = 403; + } } return response; diff --git a/libraries/MTConnect.NET-HTTP/Servers/MTConnectSampleResponseHandler.cs b/libraries/MTConnect.NET-HTTP/Servers/MTConnectSampleResponseHandler.cs index 130c21b32..fa6f6df6c 100644 --- a/libraries/MTConnect.NET-HTTP/Servers/MTConnectSampleResponseHandler.cs +++ b/libraries/MTConnect.NET-HTTP/Servers/MTConnectSampleResponseHandler.cs @@ -13,6 +13,20 @@ namespace MTConnect.Servers { + /// + /// Ceen request handler for the MTConnect Sample endpoint + /// (GET /sample and GET /{deviceKey}/sample). Returns an + /// MTConnectStreams Response Document containing a slice of + /// historical observations bounded by the from / to / count query + /// parameters, optionally filtered by an XPath in path. When + /// interval is supplied, the handler upgrades the response to a + /// multipart x-mixed-replace stream and emits successive sample + /// windows every interval milliseconds, interleaved with + /// heartbeats. The response document format is negotiated via + /// documentFormat (xml | json | json-cppagent), defaulting to XML; + /// deviceType, version, indentOutput, and outputComments further + /// shape the payload. + /// class MTConnectSampleResponseHandler : MTConnectHttpResponseHandler { private const int _minimumHeartbeat = 500; // 500 ms @@ -102,7 +116,7 @@ protected async override Task OnRequestReceived(IHttpCont var dataItemIds = PathProcessor.GetDataItemIds(_mtconnectAgent, path, documentFormat); var sampleStream = new MTConnectHttpServerStream( - _serverConfiguration, + _serverConfiguration, _mtconnectAgent, deviceKey, dataItemIds, diff --git a/libraries/MTConnect.NET-HTTP/Servers/MTConnectStaticFileRequest.cs b/libraries/MTConnect.NET-HTTP/Servers/MTConnectStaticFileRequest.cs index d3925917d..ef5d034f2 100644 --- a/libraries/MTConnect.NET-HTTP/Servers/MTConnectStaticFileRequest.cs +++ b/libraries/MTConnect.NET-HTTP/Servers/MTConnectStaticFileRequest.cs @@ -1,4 +1,4 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. using MTConnect.Http; @@ -6,14 +6,24 @@ namespace MTConnect.Servers { + /// + /// Describes a request the MTConnect HTTP server has resolved to a static file (for example a + /// schema, styling document, or stylesheet referenced from an MTConnect response). The + /// resolved record bundles the originating HTTP request together with both the URL-relative + /// and the on-disk file paths so handlers can apply conditional headers and version pinning. + /// public struct MTConnectStaticFileRequest { + /// The originating HTTP request, including the headers used for cache validation and content negotiation. public IHttpRequest HttpRequest { get; set; } + /// The relative file path requested by the client (the URL portion below the static-files mount). public string FilePath { get; set; } + /// The fully resolved on-disk path that the relative maps to. public string LocalPath { get; set; } + /// The MTConnect schema version associated with the static asset (used to select the correct stylesheet or schema variant). public Version Version { get; set; } } } diff --git a/libraries/MTConnect.NET-HTTP/Servers/MTConnectStaticResponseHandler.cs b/libraries/MTConnect.NET-HTTP/Servers/MTConnectStaticResponseHandler.cs index c7e59b03c..616bfa6f6 100644 --- a/libraries/MTConnect.NET-HTTP/Servers/MTConnectStaticResponseHandler.cs +++ b/libraries/MTConnect.NET-HTTP/Servers/MTConnectStaticResponseHandler.cs @@ -14,6 +14,15 @@ namespace MTConnect.Servers { + /// + /// Ceen request handler that serves static files configured via the + /// agent's HTTP server FileConfiguration entries (each entry maps a + /// URL path prefix to a directory or file on disk). The handler + /// resolves the requested path, applies the configured caching + /// policy, and streams the file bytes back with the appropriate + /// Content-Type. The endpoint surface is whatever path prefixes the + /// host configuration registers; there is no fixed route template. + /// class MTConnectStaticResponseHandler : MTConnectHttpResponseHandler { public Func ProcessFunction { get; set; } diff --git a/libraries/MTConnect.NET-HTTP/Servers/PathProcessor.cs b/libraries/MTConnect.NET-HTTP/Servers/PathProcessor.cs index e52bcb5e1..3042dbc68 100644 --- a/libraries/MTConnect.NET-HTTP/Servers/PathProcessor.cs +++ b/libraries/MTConnect.NET-HTTP/Servers/PathProcessor.cs @@ -6,8 +6,24 @@ namespace MTConnect.Servers.Http { + /// + /// Helper that resolves an MTConnect XPath/JSONPath request path argument against the + /// currently configured device model and returns the set of DataItem identifiers that match. + /// The MTConnect HTTP server uses this when building sample, current, or + /// asset responses to narrow the observations to those addressed by the request path. + /// public static class PathProcessor { + /// + /// Resolves against the device model exposed by + /// and returns the matching DataItem identifiers, using + /// the document-format-specific path syntax (XPath for XML, JSONPath for JSON) selected by + /// . + /// + /// The agent broker whose MTConnectDevices document is queried; null returns null. + /// The path expression supplied by the client. Null or empty returns null. + /// The document-format key (e.g. xml, json) that selects the matching path formatter. + /// The collection of matching DataItem ids, or null if the agent could not produce a devices document. public static IEnumerable GetDataItemIds(IMTConnectAgentBroker mtconnectAgent, string path, string documentFormat) { if (mtconnectAgent != null && !string.IsNullOrEmpty(path)) @@ -22,4 +38,4 @@ public static IEnumerable GetDataItemIds(IMTConnectAgentBroker mtconnect return null; } } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-HTTP/Url.cs b/libraries/MTConnect.NET-HTTP/Url.cs index ad4d7ae18..3430142f7 100644 --- a/libraries/MTConnect.NET-HTTP/Url.cs +++ b/libraries/MTConnect.NET-HTTP/Url.cs @@ -5,8 +5,22 @@ namespace MTConnect.Http { + /// + /// Small URL-manipulation helpers used by the MTConnect HTTP client and server to build the + /// agent endpoint URLs (base + request path + query string). These are intentionally light + /// and string-based so they work uniformly across .NET Framework, .NET Standard, and .NET 5+ + /// where behaviour can subtly differ. + /// public static class Url { + /// + /// Joins a base URL and a path segment with a single forward slash, trimming any trailing + /// slashes from and any leading slashes from + /// so the result never contains a duplicated separator. + /// + /// The base URL (typically the agent endpoint, e.g. http://localhost:5000). If null or empty it is returned unchanged. + /// The relative path to append (e.g. probe, device/current). If empty, the empty path itself is returned. + /// The combined URL with exactly one slash between the parts. public static string Combine(string baseUrl, string path) { if (baseUrl == null || baseUrl.Length == 0) @@ -25,6 +39,15 @@ public static string Combine(string baseUrl, string path) return $"{baseUrl}/{path}"; } + /// + /// Inserts an explicit port into the authority portion of an HTTP(S) URL, leaving any + /// path or query intact. The port is appended to the hostname segment immediately after + /// the :// scheme separator; if already contains a path the + /// port is spliced before that path. URLs without a scheme are treated as bare authorities + /// and have :port appended. + /// + /// The URL to modify. If null, empty, or is non-positive, the original value is returned. + /// The TCP port to inject. Values less than or equal to zero are ignored. public static string AddPort(string url, int port) { if (!string.IsNullOrEmpty(url) && port > 0) @@ -58,6 +81,18 @@ public static string AddPort(string url, int port) return url; } + /// + /// Appends a single name=value pair to the query string of , + /// URL-encoding the value with . If the URL + /// already contains a ? the pair is concatenated with &; otherwise a + /// new query string is started. A null or empty (or its + /// ToString result) leaves the URL untouched, which is the behaviour MTConnect + /// callers rely on when optional request parameters such as from, to, or + /// interval have not been set. + /// + /// The base URL to extend. + /// The query parameter name. Ignored if null or empty. + /// The query parameter value; its is URL-encoded. public static string AddQueryParameter(string url, string parameterName, object parameterValue) { if (!string.IsNullOrEmpty(url) && !string.IsNullOrEmpty(parameterName) && parameterValue != null) @@ -98,4 +133,4 @@ public static string AddQueryParameter(string url, string parameterName, object return url; } } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCutterStatus.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCutterStatus.cs index 3bce147dc..dfe094851 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCutterStatus.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCutterStatus.cs @@ -6,20 +6,40 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a single CutterStatus + /// enumeration value (NEW, USED, RECONDITIONED, EXPIRED, etc.), + /// wrapped as an object so the cppagent shape can carry the value + /// under a value property. + /// public class JsonCutterStatus { + /// + /// The serialized cutter status enumeration name. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCutterStatus() { } + /// + /// Initializes the surrogate from a strongly-typed + /// value. + /// public JsonCutterStatus(CutterStatusType cutterStatus) { Value = cutterStatus.ToString(); } + /// + /// Parses the serialized status back into a + /// . + /// public CutterStatusType ToCutterStatus() { return Value.ConvertEnum(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCutterStatusCollection.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCutterStatusCollection.cs index 1f546cde5..66b0f4a46 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCutterStatusCollection.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCutterStatusCollection.cs @@ -7,14 +7,28 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for the typed container of cutter + /// status values reported on a CuttingTool, keyed by the singular + /// cppagent element name Status. + /// public class JsonCutterStatusCollection { + /// + /// The cutter statuses in the container. + /// [JsonPropertyName("Status")] public IEnumerable Status { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCutterStatusCollection() { } + /// + /// Initializes the container from a cutter-status sequence. + /// public JsonCutterStatusCollection(IEnumerable cutterStatuses) { if (!cutterStatuses.IsNullOrEmpty()) @@ -29,6 +43,10 @@ public JsonCutterStatusCollection(IEnumerable cutterStatuses) } + /// + /// Flattens the container back into a uniform + /// sequence. + /// public IEnumerable ToCutterStatus() { if (!Status.IsNullOrEmpty()) diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingItem.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingItem.cs index 2318b535b..07c775958 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingItem.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingItem.cs @@ -7,41 +7,86 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a CuttingItem in the + /// cppagent-compatible shape. Manufacturers are joined into a single + /// comma-separated string. Converts to and from the strongly-typed + /// model. + /// public class JsonCuttingItem { + /// + /// The unique identifier of the cutting item. + /// [JsonPropertyName("itemId")] public string ItemId { get; set; } + /// + /// The index or range of indices identifying the cutting item's + /// position on the tool. + /// [JsonPropertyName("indices")] public string Indices { get; set; } + /// + /// The material grade of the cutting item. + /// [JsonPropertyName("grade")] public string Grade { get; set; } + /// + /// The free-form description of the cutting item. + /// [JsonPropertyName("description")] public string Description { get; set; } + /// + /// The location of the cutting item relative to the tool. + /// [JsonPropertyName("locus")] public string Locus { get; set; } + /// + /// The manufacturers of the cutting item, joined as a comma-separated + /// string. + /// [JsonPropertyName("manufacturers")] public string Manufacturers { get; set; } + /// + /// The program tool group the cutting item is assigned to. + /// [JsonPropertyName("programToolGroup")] public string ProgramToolGroup { get; set; } + /// + /// The measured and remaining life values of the cutting item. + /// [JsonPropertyName("ItemLife")] public IEnumerable ItemLife { get; set; } + /// + /// The status values of the cutting item. + /// [JsonPropertyName("CutterStatus")] public JsonCutterStatusCollection CutterStatus { get; set; } + /// + /// The dimensional measurements of the cutting item. + /// [JsonPropertyName("Measurements")] public JsonMeasurements Measurements { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCuttingItem() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , joining manufacturers with a comma. + /// public JsonCuttingItem(ICuttingItem cuttingItem) { if (cuttingItem != null) @@ -80,6 +125,10 @@ public JsonCuttingItem(ICuttingItem cuttingItem) } + /// + /// Converts this surrogate to a strongly-typed , + /// splitting comma-separated manufacturers back into a collection. + /// public ICuttingItem ToCuttingItem() { var cuttingItem = new CuttingItem(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingItemCollection.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingItemCollection.cs index 650fd671d..c9e85c383 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingItemCollection.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingItemCollection.cs @@ -8,17 +8,38 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for the counted cutting-item + /// collection of a CuttingTool, in the cppagent shape that pairs + /// the inline item count with the typed item list under list. + /// public class JsonCuttingItemCollection { + /// + /// The number of cutting items in the collection, captured at + /// construction for round-trip and inspection convenience. + /// [JsonPropertyName("count")] public int Count { get; set; } + /// + /// The cutting items themselves under the cppagent list + /// key. + /// [JsonPropertyName("list")] public JsonCuttingItems CuttingItems { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCuttingItemCollection() { } + /// + /// Initializes the collection from a cutting-item sequence, + /// caching the count and projecting each item into the typed + /// container. + /// public JsonCuttingItemCollection(IEnumerable cuttingItems) { if (!cuttingItems.IsNullOrEmpty()) @@ -30,6 +51,10 @@ public JsonCuttingItemCollection(IEnumerable cuttingItems) } + /// + /// Flattens the typed cutting-item container back into a + /// uniform sequence. + /// public IEnumerable ToCuttingItems() { if (CuttingItems != null) diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingItems.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingItems.cs index 3fdbad50f..bcb235937 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingItems.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingItems.cs @@ -7,14 +7,29 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for the typed container of + /// entries inside a + /// , keyed by the singular + /// cppagent element name CuttingItem. + /// public class JsonCuttingItems { + /// + /// The cutting items in the container. + /// [JsonPropertyName("CuttingItem")] public IEnumerable CuttingItems { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCuttingItems() { } + /// + /// Initializes the container from a cutting-item sequence. + /// public JsonCuttingItems(IEnumerable cuttingItems) { if (!cuttingItems.IsNullOrEmpty()) @@ -29,6 +44,10 @@ public JsonCuttingItems(IEnumerable cuttingItems) } + /// + /// Flattens the container back into a uniform + /// sequence. + /// public IEnumerable ToCutterItems() { if (!CuttingItems.IsNullOrEmpty()) diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingToolArchetype.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingToolArchetype.cs index 347d7141b..7535e4a4b 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingToolArchetype.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingToolArchetype.cs @@ -6,14 +6,31 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for the + /// CuttingToolArchetype asset wrapper, carrying the + /// archetype's external + /// reference. Converts to and from the strongly-typed + /// . + /// public class JsonCuttingToolArchetype { + /// + /// The cutting-tool definition reference. + /// [JsonPropertyName("CuttingToolDefinition")] public JsonCuttingToolDefinition CuttingToolDefinition { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCuttingToolArchetype() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonCuttingToolArchetype(ICuttingToolArchetypeAsset cuttingToolArchetype) { if (cuttingToolArchetype != null) @@ -23,6 +40,10 @@ public JsonCuttingToolArchetype(ICuttingToolArchetypeAsset cuttingToolArchetype) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public ICuttingToolArchetypeAsset ToCuttingToolArchetype() { var cuttingToolArchetype = new CuttingToolArchetypeAsset(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingToolArchetypeReference.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingToolArchetypeReference.cs index 1c52cda83..ad3d362c1 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingToolArchetypeReference.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingToolArchetypeReference.cs @@ -6,17 +6,36 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a + /// CuttingToolArchetypeReference on a CuttingTool asset, + /// pointing at the archetype this physical tool was instantiated + /// from. + /// public class JsonCuttingToolArchetypeReference { + /// + /// The URL or identifier of the source archetype document. + /// [JsonPropertyName("source")] public string Source { get; set; } + /// + /// The reference value (typically the archetype asset id). + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCuttingToolArchetypeReference() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonCuttingToolArchetypeReference(ICuttingToolArchetypeReference cuttingToolArchetypeReference) { if (cuttingToolArchetypeReference != null) @@ -27,6 +46,10 @@ public JsonCuttingToolArchetypeReference(ICuttingToolArchetypeReference cuttingT } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public ICuttingToolArchetypeReference ToCuttingToolArchetypeReference() { var location = new CuttingToolArchetypeReference(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingToolAsset.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingToolAsset.cs index a5e5b3de0..000c202ba 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingToolAsset.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingToolAsset.cs @@ -8,50 +8,102 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for an MTConnect CuttingTool asset + /// in the cppagent-compatible shape. Converts to and from the + /// strongly-typed model. The cppagent shape + /// joins manufacturers into a single comma-separated string. + /// public class JsonCuttingToolAsset { + /// + /// The unique identifier of the asset. + /// [JsonPropertyName("assetId")] public string AssetId { get; set; } + /// + /// The asset type identifier, CuttingTool. + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The timestamp at which the asset was last reported. + /// [JsonPropertyName("timestamp")] public DateTime Timestamp { get; set; } + /// + /// The instance identifier of the agent that produced this asset. + /// [JsonPropertyName("instanceId")] public ulong InstanceId { get; set; } + /// + /// The UUID of the device the asset is associated with. + /// [JsonPropertyName("deviceUuid")] public string DeviceUuid { get; set; } + /// + /// Whether the asset has been removed from the agent. + /// [JsonPropertyName("removed")] public bool Removed { get; set; } + /// + /// The free-form description of the asset. + /// [JsonPropertyName("description")] public string Description { get; set; } ////[JsonIgnore] //public JsonDescription Description { get; set; } + /// + /// The serial number that uniquely identifies the cutting tool. + /// [JsonPropertyName("serialNumber")] public string SerialNumber { get; set; } + /// + /// The identifier of the tool's definition. + /// [JsonPropertyName("toolId")] public string ToolId { get; set; } + /// + /// The manufacturers of the cutting tool, joined as a comma-separated + /// string. + /// [JsonPropertyName("manufacturers")] public string Manufacturers { get; set; } + /// + /// The life cycle state of the cutting tool. + /// [JsonPropertyName("CuttingToolLifeCycle")] public JsonCuttingToolLifeCycle CuttingToolLifeCycle { get; set; } + /// + /// The reference to the cutting tool archetype this asset is an + /// instance of. + /// [JsonPropertyName("CuttingToolArchetypeReference")] public JsonCuttingToolArchetypeReference CuttingToolArchetypeReference { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCuttingToolAsset() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , joining manufacturers with a comma + /// for the cppagent shape. + /// public JsonCuttingToolAsset(ICuttingToolAsset asset) { if (asset != null) @@ -75,6 +127,11 @@ public JsonCuttingToolAsset(ICuttingToolAsset asset) } + /// + /// Converts this surrogate to a strongly-typed + /// , splitting the comma-separated + /// manufacturers back into a collection. + /// public ICuttingToolAsset ToCuttingToolAsset() { var asset = new CuttingToolAsset(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingToolDefinition.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingToolDefinition.cs index 7abd7ec85..4363b9068 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingToolDefinition.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingToolDefinition.cs @@ -6,14 +6,30 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a CuttingTool + /// CuttingToolDefinition, identifying the format the + /// definition document is expressed in (for example QIF, EXPRESS). + /// public class JsonCuttingToolDefinition { + /// + /// The format identifier of the definition document. + /// [JsonPropertyName("format")] public string Format { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCuttingToolDefinition() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , serializing the format + /// to its enumeration name. + /// public JsonCuttingToolDefinition(ICuttingToolDefinition cuttingToolDefinition) { if (cuttingToolDefinition != null) @@ -23,6 +39,11 @@ public JsonCuttingToolDefinition(ICuttingToolDefinition cuttingToolDefinition) } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing the format + /// enumeration from its serialized form. + /// public CuttingToolDefinition ToCuttingToolDefinition() { var cuttingToolDefinition = new CuttingToolDefinition(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingToolLifeCycle.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingToolLifeCycle.cs index c6e64a19f..f6a87baff 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingToolLifeCycle.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonCuttingToolLifeCycle.cs @@ -7,44 +7,90 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a CuttingToolLifeCycle in the + /// cppagent-compatible shape. Converts to and from the strongly-typed + /// model. + /// public class JsonCuttingToolLifeCycle { + /// + /// The program tool group the tool is assigned to. + /// [JsonPropertyName("ProgramToolGroup")] public string ProgramToolGroup { get; set; } + /// + /// The program tool number the tool is referenced by. + /// [JsonPropertyName("ProgramToolNumber")] public string ProgramToolNumber { get; set; } + /// + /// The connection code identifying the machine-side interface of the + /// tool. + /// [JsonPropertyName("ConnectionCodeMachineSide")] public string ConnectionCodeMachineSide { get; set; } + /// + /// The status values of the cutting tool. + /// [JsonPropertyName("CutterStatus")] public JsonCutterStatusCollection CutterStatus { get; set; } + /// + /// The number of times the tool has been reconditioned. + /// [JsonPropertyName("ReconditionCount")] public JsonReconditionCount ReconditionCount { get; set; } + /// + /// The measured and remaining tool life values. + /// [JsonPropertyName("ToolLife")] public IEnumerable ToolLife { get; set; } + /// + /// The location of the tool in the machine. + /// [JsonPropertyName("Location")] public JsonLocation Location { get; set; } + /// + /// The spindle speed limits the tool is intended to operate within. + /// [JsonPropertyName("ProcessSpindleSpeed")] public JsonProcessSpindleSpeed ProcessSpindleSpeed { get; set; } + /// + /// The feed rate limits the tool is intended to operate within. + /// [JsonPropertyName("ProcessFeedRate")] public JsonProcessFeedRate ProcessFeedRate { get; set; } + /// + /// The dimensional measurements of the tool assembly. + /// [JsonPropertyName("Measurements")] public JsonMeasurements Measurements { get; set; } + /// + /// The cutting items making up the tool. + /// [JsonPropertyName("CuttingItems")] public JsonCuttingItemCollection CuttingItems { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCuttingToolLifeCycle() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonCuttingToolLifeCycle(ICuttingToolLifeCycle cuttingToolLifeCycle) { if (cuttingToolLifeCycle != null) @@ -89,6 +135,10 @@ public JsonCuttingToolLifeCycle(ICuttingToolLifeCycle cuttingToolLifeCycle) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public ICuttingToolLifeCycle ToCuttingToolLifeCycle() { var cuttingToolLifeCycle = new CuttingToolLifeCycle(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonItemLife.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonItemLife.cs index 920551a0d..f0abf4f84 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonItemLife.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonItemLife.cs @@ -6,29 +6,65 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a CuttingItem ItemLife in + /// the cppagent-compatible shape. Tracks the consumed life of a + /// single cutting item (insert or edge) using the same counter + /// vocabulary as . Converts to and from + /// the strongly-typed model. + /// public class JsonItemLife { + /// + /// The current value of the item life counter. + /// [JsonPropertyName("value")] public double Value { get; set; } + /// + /// The kind of life being counted (for example MINUTES, PARTS, + /// WEAR). + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// Whether the counter counts UP or DOWN. + /// [JsonPropertyName("countDirection")] public string CountDirection { get; set; } + /// + /// Threshold at which a warning should be raised before the + /// limit is reached. + /// [JsonPropertyName("warning")] public double? Warning { get; set; } + /// + /// The hard limit at which the cutting item is considered fully + /// consumed. + /// [JsonPropertyName("limit")] public double? Limit { get; set; } + /// + /// The initial value the counter starts at after a reset. + /// [JsonPropertyName("initial")] public double? Initial { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonItemLife() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , serializing the type and count + /// direction to their enumeration names. + /// public JsonItemLife(IItemLife itemLife) { if (itemLife != null) @@ -43,6 +79,11 @@ public JsonItemLife(IItemLife itemLife) } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing the type and count direction + /// enumerations from their serialized forms. + /// public IItemLife ToItemLife() { var itemLife = new ItemLife(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonLocation.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonLocation.cs index 0b164d4df..e4bf7556d 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonLocation.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonLocation.cs @@ -6,38 +6,85 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a CuttingTool Location in + /// the cppagent-compatible shape. Identifies the storage position of a + /// cutting tool inside a tool changer, magazine, turret, or rack, with + /// optional overlap counts describing how many adjacent pockets the + /// tool occupies. Converts to and from the strongly-typed + /// model. + /// public class JsonLocation { + /// + /// The kind of storage location (for example POT, STATION, CRIB). + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// Number of additional pockets the tool occupies after its base + /// position. + /// [JsonPropertyName("positiveOverlap")] public int? PositiveOverlap { get; set; } + /// + /// Number of additional pockets the tool occupies before its base + /// position. + /// [JsonPropertyName("negativeOverlap")] public int? NegativeOverlap { get; set; } + /// + /// Identifier of the turret holding the tool. + /// [JsonPropertyName("turret")] public string Turret { get; set; } + /// + /// Identifier of the tool magazine holding the tool. + /// [JsonPropertyName("toolMagazine")] public string ToolMagazine { get; set; } + /// + /// Identifier of the tool bar holding the tool. + /// [JsonPropertyName("toolBar")] public string ToolBar { get; set; } + /// + /// Identifier of the tool rack holding the tool. + /// [JsonPropertyName("toolRack")] public string ToolRack { get; set; } + /// + /// Identifier of the automatic tool changer responsible for the + /// tool. + /// [JsonPropertyName("automaticToolChanger")] public string AutomaticToolChanger { get; set; } + /// + /// The pocket or station value of the location within its + /// container. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonLocation() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , serializing the location type to its + /// enumeration name. + /// public JsonLocation(ILocation location) { if (location != null) @@ -55,6 +102,11 @@ public JsonLocation(ILocation location) } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing the location-type enumeration + /// from its serialized form. + /// public ILocation ToLocation() { var location = new Location(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonMeasurement.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonMeasurement.cs index a52426a7b..982ca0919 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonMeasurement.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonMeasurement.cs @@ -6,35 +6,76 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a CuttingTool measurement value + /// in the cppagent-compatible shape. Carries the measured value with + /// its significant digits, units, native units, optional code, and + /// tolerance band (minimum, maximum, nominal). The measurement type + /// is stored on the dictionary key in the parent + /// Measurements container, so it is supplied to + /// rather than embedded in the surrogate. + /// public class JsonMeasurement { + /// + /// The measured value. + /// [JsonPropertyName("value")] public double? Value { get; set; } + /// + /// The number of significant digits in the measured value. + /// [JsonPropertyName("significantDigits")] public int? SignificantDigits { get; set; } + /// + /// Engineering units of the measured value. + /// [JsonPropertyName("units")] public string Units { get; set; } + /// + /// Native engineering units used by the equipment for this + /// measurement. + /// [JsonPropertyName("nativeUnits")] public string NativeUnits { get; set; } + /// + /// Optional measurement code (for example an ISO 13399 code). + /// [JsonPropertyName("code")] public string Code { get; set; } + /// + /// Upper tolerance bound of the measurement. + /// [JsonPropertyName("maximum")] public double? Maximum { get; set; } + /// + /// Lower tolerance bound of the measurement. + /// [JsonPropertyName("minimum")] public double? Minimum { get; set; } + /// + /// Nominal (designed) value of the measurement. + /// [JsonPropertyName("nominal")] public double? Nominal { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonMeasurement() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonMeasurement(IToolingMeasurement measurement) { if (measurement != null) @@ -51,6 +92,13 @@ public JsonMeasurement(IToolingMeasurement measurement) } + /// + /// Converts this surrogate to a strongly-typed + /// , restoring the measurement + /// type from the supplied dictionary key and delegating to + /// to materialize the + /// concrete measurement subtype. + /// public IToolingMeasurement ToMeasurement(string type) { var measurement = new ToolingMeasurement(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonMeasurements.g.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonMeasurements.g.cs index 9e543a63c..9451920de 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonMeasurements.g.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonMeasurements.g.cs @@ -8,139 +8,279 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// cppagent-style JSON representation of a cutting tool's measurements. Each + /// MTConnect measurement type is exposed as its own typed collection so the + /// serialized object shape matches the C++ reference agent's output. + /// public class JsonMeasurements { + /// + /// The BodyDiameterMax measurements declared on the cutting tool. + /// Largest diameter of the body of a tool item. + /// [JsonPropertyName("BodyDiameterMax")] public List BodyDiameterMaxMeasurements { get; set; } + /// + /// The BodyLengthMax measurements declared on the cutting tool. + /// Distance measured along the X axis from that point of the item closest to the workpiece, including the cutting item for a tool item but excluding a protruding locking mechanism for an adaptive item, to either the front of the flange on a flanged body or the beginning of the connection interface feature on the machine side for cylindrical or prismatic shanks. + /// [JsonPropertyName("BodyLengthMax")] public List BodyLengthMaxMeasurements { get; set; } + /// + /// The ChamferFlatLength measurements declared on the cutting tool. + /// Flat length of a chamfer. + /// [JsonPropertyName("ChamferFlatLength")] public List ChamferFlatLengthMeasurements { get; set; } + /// + /// The ChamferWidth measurements declared on the cutting tool. + /// Width of the chamfer. + /// [JsonPropertyName("ChamferWidth")] public List ChamferWidthMeasurements { get; set; } + /// + /// The CornerRadius measurements declared on the cutting tool. + /// Nominal radius of a rounded corner measured in the X Y-plane. + /// [JsonPropertyName("CornerRadius")] public List CornerRadiusMeasurements { get; set; } + /// + /// The CuttingDiameterMax measurements declared on the cutting tool. + /// Maximum diameter of a circle on which the defined point Pk of each of the master inserts is located on a tool item. The normal of the machined peripheral surface points towards the axis of the cutting tool. + /// [JsonPropertyName("CuttingDiameterMax")] public List CuttingDiameterMaxMeasurements { get; set; } + /// + /// The CuttingDiameter measurements declared on the cutting tool. + /// Diameter of a circle on which the defined point Pk located on this cutting tool. The normal of the machined peripheral surface points towards the axis of the cutting tool. + /// [JsonPropertyName("CuttingDiameter")] public List CuttingDiameterMeasurements { get; set; } + /// + /// The CuttingEdgeLength measurements declared on the cutting tool. + /// Theoretical length of the cutting edge of a cutting item over sharp corners. + /// [JsonPropertyName("CuttingEdgeLength")] public List CuttingEdgeLengthMeasurements { get; set; } + /// + /// The CuttingHeight measurements declared on the cutting tool. + /// Distance from the basal plane of the tool item to the cutting point. + /// [JsonPropertyName("CuttingHeight")] public List CuttingHeightMeasurements { get; set; } + /// + /// The CuttingReferencePoint measurements declared on the cutting tool. + /// Theoretical sharp point of the cutting tool from which the major functional dimensions are taken. + /// [JsonPropertyName("CuttingReferencePoint")] public List CuttingReferencePointMeasurements { get; set; } + /// + /// The DepthOfCutMax measurements declared on the cutting tool. + /// Maximum engagement of the cutting edge or edges with the workpiece measured perpendicular to the feed motion. + /// [JsonPropertyName("DepthOfCutMax")] public List DepthOfCutMaxMeasurements { get; set; } + /// + /// The DriveAngle measurements declared on the cutting tool. + /// Angle between the driving mechanism locator on a tool item and the main cutting edge. + /// [JsonPropertyName("DriveAngle")] public List DriveAngleMeasurements { get; set; } + /// + /// The FlangeDiameterMax measurements declared on the cutting tool. + /// Dimension between two parallel tangents on the outside edge of a flange. + /// [JsonPropertyName("FlangeDiameterMax")] public List FlangeDiameterMaxMeasurements { get; set; } + /// + /// The FlangeDiameter measurements declared on the cutting tool. + /// Dimension between two parallel tangents on the outside edge of a flange. + /// [JsonPropertyName("FlangeDiameter")] public List FlangeDiameterMeasurements { get; set; } + /// + /// The FunctionalLength measurements declared on the cutting tool. + /// Distance from the gauge plane or from the end of the shank to the furthest point on the tool, if a gauge plane does not exist, to the cutting reference point determined by the main function of the tool.The CuttingTool functional length will be the length of the entire tool, not a single cutting item. Each CuttingItem can have an independent FunctionalLength represented in its measurements. + /// [JsonPropertyName("FunctionalLength")] public List FunctionalLengthMeasurements { get; set; } + /// + /// The FunctionalWidth measurements declared on the cutting tool. + /// Distance between the cutting reference point and the rear backing surface of a turning tool or the axis of a boring bar. + /// [JsonPropertyName("FunctionalWidth")] public List FunctionalWidthMeasurements { get; set; } + /// + /// The IncribedCircleDiameter measurements declared on the cutting tool. + /// Diameter of a circle to which all edges of a equilateral and round regular insert are tangential. + /// [JsonPropertyName("IncribedCircleDiameter")] public List IncribedCircleDiameterMeasurements { get; set; } + /// + /// The InsertWidth measurements declared on the cutting tool. + /// W1 is used for the insert width when an inscribed circle diameter is not practical. + /// [JsonPropertyName("InsertWidth")] public List InsertWidthMeasurements { get; set; } + /// + /// The OverallToolLength measurements declared on the cutting tool. + /// Largest length dimension of the cutting tool including the master insert where applicable. + /// [JsonPropertyName("OverallToolLength")] public List OverallToolLengthMeasurements { get; set; } + /// + /// The PointAngle measurements declared on the cutting tool. + /// Angle between the major cutting edge and the same cutting edge rotated by 180 degrees about the tool axis. + /// [JsonPropertyName("PointAngle")] public List PointAngleMeasurements { get; set; } + /// + /// The ProtrudingLength measurements declared on the cutting tool. + /// Dimension from the yz-plane to the furthest point of the tool item or adaptive item measured in the -X direction. + /// [JsonPropertyName("ProtrudingLength")] public List ProtrudingLengthMeasurements { get; set; } + /// + /// The ShankDiameter measurements declared on the cutting tool. + /// Dimension of the diameter of a cylindrical portion of a tool item or an adaptive item that can participate in a connection. + /// [JsonPropertyName("ShankDiameter")] public List ShankDiameterMeasurements { get; set; } + /// + /// The ShankHeight measurements declared on the cutting tool. + /// Dimension of the height of the shank. + /// [JsonPropertyName("ShankHeight")] public List ShankHeightMeasurements { get; set; } + /// + /// The ShankLength measurements declared on the cutting tool. + /// Dimension of the length of the shank. + /// [JsonPropertyName("ShankLength")] public List ShankLengthMeasurements { get; set; } + /// + /// The StepDiameterLength measurements declared on the cutting tool. + /// Length of a portion of a stepped tool that is related to a corresponding cutting diameter measured from the cutting reference point of that cutting diameter to the point on the next cutting edge at which the diameter starts to change. + /// [JsonPropertyName("StepDiameterLength")] public List StepDiameterLengthMeasurements { get; set; } + /// + /// The StepIncludedAngle measurements declared on the cutting tool. + /// Angle between a major edge on a step of a stepped tool and the same cutting edge rotated 180 degrees about its tool axis. + /// [JsonPropertyName("StepIncludedAngle")] public List StepIncludedAngleMeasurements { get; set; } + /// + /// The ToolCuttingEdgeAngle measurements declared on the cutting tool. + /// Angle between the tool cutting edge plane and the tool feed plane measured in a plane parallel the xy-plane. + /// [JsonPropertyName("ToolCuttingEdgeAngle")] public List ToolCuttingEdgeAngleMeasurements { get; set; } + /// + /// The ToolLeadAngle measurements declared on the cutting tool. + /// Angle between the tool cutting edge plane and a plane perpendicular to the tool feed plane measured in a plane parallel the xy-plane. + /// [JsonPropertyName("ToolLeadAngle")] public List ToolLeadAngleMeasurements { get; set; } + /// + /// The ToolOrientation measurements declared on the cutting tool. + /// Angle of the tool with respect to the workpiece for a given process. The value is application specific. + /// [JsonPropertyName("ToolOrientation")] public List ToolOrientationMeasurements { get; set; } + /// + /// The UsableLengthMax measurements declared on the cutting tool. + /// Maximum length of a cutting tool that can be used in a particular cutting operation including the non-cutting portions of the tool. + /// [JsonPropertyName("UsableLengthMax")] public List UsableLengthMaxMeasurements { get; set; } + /// + /// The Weight measurements declared on the cutting tool. + /// Total weight of the cutting tool in grams. The force exerted by the mass of the cutting tool. + /// [JsonPropertyName("Weight")] public List WeightMeasurements { get; set; } + /// + /// The WiperEdgeLength measurements declared on the cutting tool. + /// Measure of the length of a wiper edge of a cutting item. + /// [JsonPropertyName("WiperEdgeLength")] public List WiperEdgeLengthMeasurements { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonMeasurements() { } + /// + /// Initializes a new instance from a flat sequence of , + /// bucketing each one into the typed collection that matches its MTConnect type. + /// public JsonMeasurements(IEnumerable measurements) { if (!measurements.IsNullOrEmpty()) @@ -340,17 +480,21 @@ public JsonMeasurements(IEnumerable measurements) WiperEdgeLengthMeasurements.Add(new JsonMeasurement(measurement)); break; - - } + + } } - } + } } + /// + /// Flattens every typed measurement collection back into a single + /// sequence, restoring each item's MTConnect type. + /// public IEnumerable ToMeasurements() { var measurements = new List(); - + if (!BodyDiameterMaxMeasurements.IsNullOrEmpty()) foreach (var measurement in BodyDiameterMaxMeasurements) measurements.Add(measurement.ToMeasurement(BodyDiameterMaxMeasurement.TypeId)); if (!BodyLengthMaxMeasurements.IsNullOrEmpty()) foreach (var measurement in BodyLengthMaxMeasurements) measurements.Add(measurement.ToMeasurement(BodyLengthMaxMeasurement.TypeId)); @@ -383,9 +527,9 @@ public IEnumerable ToMeasurements() if (!ToolOrientationMeasurements.IsNullOrEmpty()) foreach (var measurement in ToolOrientationMeasurements) measurements.Add(measurement.ToMeasurement(ToolOrientationMeasurement.TypeId)); if (!UsableLengthMaxMeasurements.IsNullOrEmpty()) foreach (var measurement in UsableLengthMaxMeasurements) measurements.Add(measurement.ToMeasurement(UsableLengthMaxMeasurement.TypeId)); if (!WeightMeasurements.IsNullOrEmpty()) foreach (var measurement in WeightMeasurements) measurements.Add(measurement.ToMeasurement(WeightMeasurement.TypeId)); - if (!WiperEdgeLengthMeasurements.IsNullOrEmpty()) foreach (var measurement in WiperEdgeLengthMeasurements) measurements.Add(measurement.ToMeasurement(WiperEdgeLengthMeasurement.TypeId)); + if (!WiperEdgeLengthMeasurements.IsNullOrEmpty()) foreach (var measurement in WiperEdgeLengthMeasurements) measurements.Add(measurement.ToMeasurement(WiperEdgeLengthMeasurement.TypeId)); return measurements; } } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonProcessFeedrate.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonProcessFeedrate.cs index 165c13da4..e50b7fac5 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonProcessFeedrate.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonProcessFeedrate.cs @@ -6,23 +6,50 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a CuttingTool + /// ProcessFeedRate in the cppagent-compatible shape. Carries + /// the feed-rate envelope (minimum, maximum, nominal) the tool + /// should be operated within, plus an optional current value. + /// Converts to and from the strongly-typed + /// model. + /// public class JsonProcessFeedRate { + /// + /// Upper bound of the recommended feed-rate envelope. + /// [JsonPropertyName("maximum")] public double? Maximum { get; set; } + /// + /// Lower bound of the recommended feed-rate envelope. + /// [JsonPropertyName("minimum")] public double? Minimum { get; set; } + /// + /// Nominal (target) feed rate. + /// [JsonPropertyName("nominal")] public double? Nominal { get; set; } + /// + /// The current operating feed rate, when reported. + /// [JsonPropertyName("value")] public double? Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonProcessFeedRate() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonProcessFeedRate(IProcessFeedRate processFeedrate) { if (processFeedrate != null) @@ -35,6 +62,10 @@ public JsonProcessFeedRate(IProcessFeedRate processFeedrate) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IProcessFeedRate ToProcessFeedrate() { var processFeedrate = new ProcessFeedRate(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonProcessSpindleSpeed.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonProcessSpindleSpeed.cs index 521d49104..a440107d8 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonProcessSpindleSpeed.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonProcessSpindleSpeed.cs @@ -6,23 +6,50 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a CuttingTool + /// ProcessSpindleSpeed in the cppagent-compatible shape. + /// Carries the spindle-speed envelope (minimum, maximum, nominal) + /// the tool should be operated within, plus an optional current + /// value. Converts to and from the strongly-typed + /// model. + /// public class JsonProcessSpindleSpeed { + /// + /// Upper bound of the recommended spindle-speed envelope. + /// [JsonPropertyName("maximum")] public double? Maximum { get; set; } + /// + /// Lower bound of the recommended spindle-speed envelope. + /// [JsonPropertyName("minimum")] public double? Minimum { get; set; } + /// + /// Nominal (target) spindle speed. + /// [JsonPropertyName("nominal")] public double? Nominal { get; set; } + /// + /// The current operating spindle speed, when reported. + /// [JsonPropertyName("value")] public double? Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonProcessSpindleSpeed() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonProcessSpindleSpeed(IProcessSpindleSpeed processSpindleSpeed) { if (processSpindleSpeed != null) @@ -35,6 +62,10 @@ public JsonProcessSpindleSpeed(IProcessSpindleSpeed processSpindleSpeed) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IProcessSpindleSpeed ToProcessSpindleSpeed() { var processSpindleSpeed = new ProcessSpindleSpeed(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonReconditionCount.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonReconditionCount.cs index 37cbfc052..9523524f7 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonReconditionCount.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonReconditionCount.cs @@ -6,17 +6,36 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a CuttingTool + /// ReconditionCount, tracking how many times the tool has + /// been reconditioned and an optional limit before it must be + /// retired. + /// public class JsonReconditionCount { + /// + /// The maximum allowed number of reconditions. + /// [JsonPropertyName("maximumCount")] public int? MaximumCount { get; set; } + /// + /// The current recondition count. + /// [JsonPropertyName("value")] public int? Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonReconditionCount() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonReconditionCount(IReconditionCount reconditionCount) { if (reconditionCount != null) @@ -27,6 +46,10 @@ public JsonReconditionCount(IReconditionCount reconditionCount) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IReconditionCount ToReconditionCount() { var reconditionCount = new ReconditionCount(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonToolLife.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonToolLife.cs index 02c5508a5..c0dba9ce5 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonToolLife.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/CuttingTools/JsonToolLife.cs @@ -6,29 +6,66 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a CuttingTool ToolLife in + /// the cppagent-compatible shape. Tracks the consumed life of an + /// entire tool against a typed counter (parts, time, or wear) with a + /// configurable count direction and optional warning/limit/initial + /// thresholds. Converts to and from the strongly-typed + /// model. + /// public class JsonToolLife { + /// + /// The current value of the life counter. + /// [JsonPropertyName("value")] public double Value { get; set; } + /// + /// The kind of life being counted (for example MINUTES, PARTS, + /// WEAR). + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// Whether the counter counts UP or DOWN. + /// [JsonPropertyName("countDirection")] public string CountDirection { get; set; } + /// + /// Threshold at which a warning should be raised before the + /// limit is reached. + /// [JsonPropertyName("warning")] public double? Warning { get; set; } + /// + /// The hard limit at which the tool is considered fully + /// consumed. + /// [JsonPropertyName("limit")] public double? Limit { get; set; } + /// + /// The initial value the counter starts at after a reset. + /// [JsonPropertyName("initial")] public double? Initial { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonToolLife() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , serializing the type and count + /// direction to their enumeration names. + /// public JsonToolLife(IToolLife toolLife) { if (toolLife != null) @@ -43,6 +80,11 @@ public JsonToolLife(IToolLife toolLife) } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing the type and count direction + /// enumerations from their serialized forms. + /// public IToolLife ToToolLife() { var toolLife = new ToolLife(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonAbstractFileAsset.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonAbstractFileAsset.cs index d02951b07..701cbed93 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonAbstractFileAsset.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonAbstractFileAsset.cs @@ -6,23 +6,52 @@ namespace MTConnect.Assets.Json.Files { + /// + /// Shared JSON serialization surrogate for the attributes common to + /// both the abstract and concrete File assets in the + /// cppagent-compatible shape. Extends with + /// file-specific identification (name, media type, application + /// category and type) and the optional file properties and comments + /// collections. + /// public abstract class JsonAbstractFileAsset : JsonAsset { + /// + /// The display name of the file. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// IANA media type of the file content (for example + /// application/pdf). + /// [JsonPropertyName("mediaType")] public string MediaType { get; set; } + /// + /// The high-level application category the file belongs to (for + /// example DESIGN, MAINTENANCE). + /// [JsonPropertyName("applicationCategory")] public string ApplicationCategory { get; set; } + /// + /// The specific application type the file serves within its + /// category. + /// [JsonPropertyName("applicationType")] public string ApplicationType { get; set; } + /// + /// Custom name/value properties attached to the file. + /// [JsonPropertyName("FileProperties")] public IEnumerable FileProperties { get; set; } + /// + /// Human-authored comments attached to the file. + /// [JsonPropertyName("FileComments")] public IEnumerable FileComments { get; set; } } diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonDestination.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonDestination.cs index 4d0b8baa9..99e5385a5 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonDestination.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonDestination.cs @@ -6,14 +6,33 @@ namespace MTConnect.Assets.Json.Files { + /// + /// JSON serialization surrogate for a Destination on a File + /// asset, identifying a downstream device by UUID that the file + /// should be delivered to. The cppagent shape emits the device UUID + /// under the value key (rather than deviceUuid) — see + /// the inline note on . + /// public class JsonDestination { + /// + /// UUID of the destination device. Note the JSON key is + /// value in the cppagent shape even though the XML + /// attribute is deviceUuid. + /// [JsonPropertyName("value")] // Not sure why this is "value" when it is listed as an XML attribute with the name of "deviceUuid" public string DeviceUuid { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDestination() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonDestination(IDestination destination) { if (destination != null) @@ -23,6 +42,10 @@ public JsonDestination(IDestination destination) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IDestination ToDestination() { var destination = new Destination(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonDestinationCollection.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonDestinationCollection.cs index 76b270ca3..17e033d16 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonDestinationCollection.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonDestinationCollection.cs @@ -7,14 +7,28 @@ namespace MTConnect.Assets.Json.Files { + /// + /// JSON serialization surrogate for the typed container of + /// entries attached to a File asset, + /// keyed by the singular cppagent element name Destination. + /// public class JsonDestinationCollection { + /// + /// The destinations in the container. + /// [JsonPropertyName("Destination")] public IEnumerable Destinations { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDestinationCollection() { } + /// + /// Initializes the container from a destination sequence. + /// public JsonDestinationCollection(IEnumerable destinations) { if (!destinations.IsNullOrEmpty()) @@ -29,6 +43,10 @@ public JsonDestinationCollection(IEnumerable destinations) } + /// + /// Flattens the container back into a uniform + /// sequence. + /// public IEnumerable ToDestinations() { if (!Destinations.IsNullOrEmpty()) diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonFileAsset.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonFileAsset.cs index 7d5a87ba7..abea0c35c 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonFileAsset.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonFileAsset.cs @@ -9,78 +9,157 @@ namespace MTConnect.Assets.Json.Files { + /// + /// JSON serialization surrogate for an MTConnect File asset in the + /// cppagent-compatible JSON shape. Converts to and from the strongly-typed + /// model. + /// public class JsonFileAsset { + /// + /// The unique identifier of the asset. + /// [JsonPropertyName("assetId")] public string AssetId { get; set; } + /// + /// The asset type identifier, File. + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The timestamp at which the asset was last reported. + /// [JsonPropertyName("timestamp")] public DateTime Timestamp { get; set; } + /// + /// The UUID of the device the asset is associated with. + /// [JsonPropertyName("deviceUuid")] public string DeviceUuid { get; set; } + /// + /// Whether the asset has been removed from the agent. + /// [JsonPropertyName("removed")] public bool Removed { get; set; } //[JsonPropertyName("description")] //public JsonDescription Description { get; set; } + /// + /// The free-form description of the asset. + /// [JsonPropertyName("description")] public string Description { get; set; } + /// + /// The name of the file. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The MIME media type of the file's contents. + /// [JsonPropertyName("mediaType")] public string MediaType { get; set; } + /// + /// The category of application the file is associated with, serialized + /// as the enumeration name. + /// [JsonPropertyName("applicationCategory")] public string ApplicationCategory { get; set; } + /// + /// The type of application the file is associated with, serialized as + /// the enumeration name. + /// [JsonPropertyName("applicationType")] public string ApplicationType { get; set; } + /// + /// The key/value properties describing the file. + /// [JsonPropertyName("FileProperties")] public IEnumerable FileProperties { get; set; } + /// + /// The comments associated with the file. + /// [JsonPropertyName("FileComments")] public IEnumerable FileComments { get; set; } + /// + /// The size of the file in bytes. + /// [JsonPropertyName("size")] public int Size { get; set; } + /// + /// The version identifier of the file. + /// [JsonPropertyName("versionId")] public string VersionId { get; set; } + /// + /// The state of the file, serialized as the enumeration name. + /// [JsonPropertyName("state")] public string State { get; set; } + /// + /// The location the file can be retrieved from. + /// [JsonPropertyName("FileLocation")] public JsonFileLocation FileLocation { get; set; } + /// + /// The cryptographic signature used to verify the file. + /// [JsonPropertyName("signature")] public string Signature { get; set; } + /// + /// The public key used to verify the file's . + /// [JsonPropertyName("publicKey")] public string PublicKey { get; set; } + /// + /// The destinations the file is intended to be transferred to, wrapped + /// in a counted container. + /// [JsonPropertyName("Destinations")] public JsonDestinationCollection Destinations { get; set; } + /// + /// The time the file was created. + /// [JsonPropertyName("CreationTime")] public DateTime CreationTime { get; set; } + /// + /// The time the file was last modified, when known. + /// [JsonPropertyName("ModificationTime")] public DateTime? ModificationTime { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonFileAsset() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , converting enumerations to strings and + /// each file property, comment, and destination. + /// public JsonFileAsset(IFileAsset asset) { if (asset != null) @@ -135,6 +214,11 @@ public JsonFileAsset(IFileAsset asset) } + /// + /// Converts this surrogate to a strongly-typed , + /// parsing enumerations and converting each file property, comment, and + /// destination. + /// public IFileAsset ToFileAsset() { var asset = new FileAsset(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonFileComment.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonFileComment.cs index cab0d11f1..f99e8f0c0 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonFileComment.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonFileComment.cs @@ -7,17 +7,34 @@ namespace MTConnect.Assets.Json.Files { + /// + /// JSON serialization surrogate for a timestamped + /// FileComment attached to a File asset. + /// public class JsonFileComment { + /// + /// The timestamp when the comment was authored. + /// [JsonPropertyName("timestamp")] public DateTime Timestamp { get; set; } + /// + /// The free-form comment text. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonFileComment() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonFileComment(IFileComment fileComment) { if (fileComment != null) @@ -28,6 +45,10 @@ public JsonFileComment(IFileComment fileComment) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IFileComment ToFileComment() { var fileComment = new FileComment(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonFileLocation.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonFileLocation.cs index 4f1561d08..1923c0312 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonFileLocation.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonFileLocation.cs @@ -6,17 +6,35 @@ namespace MTConnect.Assets.Json.Files { + /// + /// JSON serialization surrogate for the URL of a File asset's + /// content, modelled as an XLink with an optional XLink type + /// qualifier. + /// public class JsonFileLocation { + /// + /// The URL of the file content. + /// [JsonPropertyName("href")] public string Href { get; set; } + /// + /// The XLink type qualifier (typically locator). + /// [JsonPropertyName("xLinkType")] public string XLinkType { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonFileLocation() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonFileLocation(IFileLocation fileLocation) { if (fileLocation != null) @@ -27,6 +45,10 @@ public JsonFileLocation(IFileLocation fileLocation) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IFileLocation ToFileLocation() { var fileLocation = new FileLocation(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonFileProperty.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonFileProperty.cs index 0b784cd72..8df5e42e1 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonFileProperty.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/Files/JsonFileProperty.cs @@ -6,17 +6,34 @@ namespace MTConnect.Assets.Json.Files { + /// + /// JSON serialization surrogate for a single name/value + /// FileProperty attached to a File asset. + /// public class JsonFileProperty { + /// + /// The property name. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The property value. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonFileProperty() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonFileProperty(IFileProperty fileProperty) { if (fileProperty != null) @@ -27,6 +44,10 @@ public JsonFileProperty(IFileProperty fileProperty) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IFileProperty ToFileProperty() { var fileProperty = new FileProperty(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonAsset.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonAsset.cs index ada92d280..2fd62e53e 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonAsset.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonAsset.cs @@ -6,23 +6,47 @@ namespace MTConnect.Assets.Json { + /// + /// Shared JSON envelope for the common attributes of every asset in + /// the cppagent-compatible shape. Subclassed by each typed asset + /// surrogate (CuttingTool, File, RawMaterial, QIFDocumentWrapper), + /// so the envelope members do not need to be redeclared per type. + /// public class JsonAsset { + /// + /// The unique identifier of the asset. + /// [JsonPropertyName("assetId")] public string AssetId { get; set; } + /// + /// The asset type discriminator (the concrete element name). + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The timestamp when the asset was reported. + /// [JsonPropertyName("timestamp")] public DateTime Timestamp { get; set; } + /// + /// The UUID of the device the asset is associated with. + /// [JsonPropertyName("deviceUuid")] public string DeviceUuid { get; set; } + /// + /// Whether the asset has been marked as removed. + /// [JsonPropertyName("removed")] public bool Removed { get; set; } + /// + /// Free-form description of the asset. + /// [JsonPropertyName("description")] public string Description { get; set; } } diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonAssetContainer.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonAssetContainer.cs index 2f80031f9..a3ee86d06 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonAssetContainer.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonAssetContainer.cs @@ -12,26 +12,54 @@ namespace MTConnect.Assets.Json { + /// + /// JSON serialization surrogate that wraps a single asset of any + /// supported type in the cppagent-compatible shape. The cppagent + /// asset envelope keys each asset by its element name + /// (CuttingTool, File, RawMaterial), so this + /// container exposes one optional property per asset type and only + /// the property matching the wrapped asset is populated. Converts + /// to and from the strongly-typed model. + /// public class JsonAssetContainer { //[JsonPropertyName("ComponentConfigurationParameters")] //public List ComponentConfigurationParameters { get; set; } + /// + /// The wrapped CuttingTool asset, when the container + /// holds one. + /// [JsonPropertyName("CuttingTool")] public JsonCuttingToolAsset CuttingTool { get; set; } + /// + /// The wrapped File asset, when the container holds one. + /// [JsonPropertyName("File")] public JsonFileAsset File { get; set; } //[JsonPropertyName("QIF")] //public List QIF { get; set; } + /// + /// The wrapped RawMaterial asset, when the container + /// holds one. + /// [JsonPropertyName("RawMaterial")] public JsonRawMaterialAsset RawMaterial { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonAssetContainer() { } + /// + /// Initializes the container from a strongly-typed + /// , dispatching to the appropriate typed + /// property by the asset's TypeId discriminator. + /// public JsonAssetContainer(IAsset asset) { if (asset != null) @@ -54,6 +82,11 @@ public JsonAssetContainer(IAsset asset) } + /// + /// Wraps the contained asset in a single-element + /// , returning null + /// when the container is empty. + /// public IAssetsResponseDocument ToAssetsDocument() { var asset = ToAsset(); @@ -73,6 +106,10 @@ public IAssetsResponseDocument ToAssetsDocument() return null; } + /// + /// Returns the contained asset by inspecting the populated + /// property, returning null when none is populated. + /// public IAsset ToAsset() { if (CuttingTool != null) diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonAssets.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonAssets.cs index 80e11437b..05d007371 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonAssets.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonAssets.cs @@ -12,26 +12,52 @@ namespace MTConnect.Assets.Json { + /// + /// JSON serialization surrogate that holds every asset in an Assets + /// response document partitioned by asset type into typed lists. + /// The cppagent shape keys each list by the asset element name + /// (CuttingTool, File, RawMaterial), so this + /// container exposes one list per supported asset type and only the + /// lists with content are populated. Converts to and from a uniform + /// collection. + /// public class JsonAssets { //[JsonPropertyName("ComponentConfigurationParameters")] //public List ComponentConfigurationParameters { get; set; } + /// + /// CuttingTool assets in the document. + /// [JsonPropertyName("CuttingTool")] public List CuttingTools { get; set; } + /// + /// File assets in the document. + /// [JsonPropertyName("File")] public List Files { get; set; } //[JsonPropertyName("QIF")] //public List QIF { get; set; } + /// + /// RawMaterial assets in the document. + /// [JsonPropertyName("RawMaterial")] public List RawMaterials { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonAssets() { } + /// + /// Initializes the container from a uniform asset collection, + /// partitioning each asset into the appropriate typed list by + /// its TypeId discriminator. + /// public JsonAssets(IEnumerable assets) { if (!assets.IsNullOrEmpty()) @@ -60,6 +86,11 @@ public JsonAssets(IEnumerable assets) } + /// + /// Flattens the typed asset lists back into a uniform + /// collection in CuttingTool, File, + /// RawMaterial order. + /// public IEnumerable ToAssets() { var assets = new List(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonAssetsHeader.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonAssetsHeader.cs index 8e5c188ac..89ca75eed 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonAssetsHeader.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonAssetsHeader.cs @@ -7,11 +7,21 @@ namespace MTConnect.Assets.Json { + /// + /// JSON serialization surrogate for the Header of an + /// MTConnectAssets document in the cppagent-compatible shape. + /// public class JsonAssetsHeader { + /// + /// The instance identifier of the agent. + /// [JsonPropertyName("instanceId")] public ulong InstanceId { get; set; } + /// + /// The agent's version. + /// [JsonPropertyName("version")] public string Version { get; set; } @@ -22,18 +32,34 @@ public class JsonAssetsHeader [JsonPropertyName("schemaVersion")] public string SchemaVersion { get; set; } + /// + /// The identifier of the agent that produced the document. + /// [JsonPropertyName("sender")] public string Sender { get; set; } + /// + /// The maximum number of assets the agent can store. + /// [JsonPropertyName("assetBufferSize")] public ulong AssetBufferSize { get; set; } + /// + /// The number of assets currently stored by the agent. + /// [JsonPropertyName("assetCount")] public ulong AssetCount { get; set; } + /// + /// The timestamp of the most recent change to the device model. + /// [JsonPropertyName("deviceModelChangeTime")] public string DeviceModelChangeTime { get; set; } + /// + /// Whether the document was produced for testing rather than + /// production use. + /// [JsonPropertyName("testIndicator")] public bool TestIndicator { get; set; } @@ -44,12 +70,22 @@ public class JsonAssetsHeader [JsonPropertyName("validation")] public bool Validation { get; set; } + /// + /// The time the document was created. + /// [JsonPropertyName("creationTime")] public DateTime CreationTime { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonAssetsHeader() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonAssetsHeader(IMTConnectAssetsHeader header) { if (header != null) @@ -68,6 +104,10 @@ public JsonAssetsHeader(IMTConnectAssetsHeader header) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public virtual IMTConnectAssetsHeader ToAssetsHeader() { var header = new MTConnectAssetsHeader(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonAssetsResponseDocument.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonAssetsResponseDocument.cs index fcafffe11..3e237d7aa 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonAssetsResponseDocument.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonAssetsResponseDocument.cs @@ -5,20 +5,41 @@ namespace MTConnect.Assets.Json { + /// + /// Outer JSON envelope for an Assets response document in the + /// cppagent-compatible shape, with the actual content wrapped in a + /// single MTConnectAssets property to mirror the XML root + /// element name. + /// public class JsonAssetsResponseDocument { + /// + /// The wrapped assets document. + /// [JsonPropertyName("MTConnectAssets")] public JsonMTConnectAssets MTConnectAssets { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonAssetsResponseDocument() { } + /// + /// Initializes the envelope from a strongly-typed assets + /// document. + /// public JsonAssetsResponseDocument(IAssetsResponseDocument assetsDocument) { MTConnectAssets = new JsonMTConnectAssets(assetsDocument); } + /// + /// Unwraps the envelope and converts it to a strongly-typed + /// assets document, returning null when the envelope is + /// empty. + /// public IAssetsResponseDocument ToAssetsDocument() { if (MTConnectAssets != null) diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonMTConnectAssets.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonMTConnectAssets.cs index 5564a589b..0625ab876 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonMTConnectAssets.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/JsonMTConnectAssets.cs @@ -5,17 +5,39 @@ namespace MTConnect.Assets.Json { + /// + /// JSON serialization surrogate for the top-level + /// MTConnectAssets document in the cppagent-compatible + /// shape. Sits inside a + /// envelope and carries the agent header plus the typed + /// asset container. Converts to and from the strongly-typed + /// model. + /// public class JsonMTConnectAssets { + /// + /// The MTConnect Agent header. + /// [JsonPropertyName("Header")] public JsonAssetsHeader Header { get; set; } + /// + /// The typed asset container holding every asset in the + /// document. + /// [JsonPropertyName("Assets")] public JsonAssets Assets { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonMTConnectAssets() { } + /// + /// Initializes the container from a strongly-typed + /// . + /// public JsonMTConnectAssets(IAssetsResponseDocument assetsDocument) { if (assetsDocument != null) @@ -27,6 +49,10 @@ public JsonMTConnectAssets(IAssetsResponseDocument assetsDocument) } + /// + /// Converts the container to a strongly-typed + /// . + /// public IAssetsResponseDocument ToAssetsDocument() { var assetsDocument = new AssetsResponseDocument(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/QIF/JsonQIFDocumentWrapperAsset.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/QIF/JsonQIFDocumentWrapperAsset.cs index 842783f88..1c881d062 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/QIF/JsonQIFDocumentWrapperAsset.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/QIF/JsonQIFDocumentWrapperAsset.cs @@ -8,42 +8,88 @@ namespace MTConnect.Assets.Json.QIF { + /// + /// JSON serialization surrogate for a QIFDocumentWrapper asset in + /// the cppagent-compatible shape. Carries the standard asset envelope + /// (asset id, timestamp, instance id, device uuid, removed flag) plus + /// the embedded QIF (Quality Information Framework) document type and + /// the document payload itself. Converts to and from the strongly-typed + /// . + /// public class JsonQIFDocumentWrapperAsset { + /// + /// The unique identifier of the asset. + /// [JsonPropertyName("assetId")] public string AssetId { get; set; } + /// + /// The asset type discriminator (always + /// QIFDocumentWrapper for this asset). + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The timestamp when the asset was reported. + /// [JsonPropertyName("timestamp")] public DateTime Timestamp { get; set; } + /// + /// The MTConnect Agent instance identifier this asset was reported + /// against. + /// [JsonPropertyName("instanceId")] public ulong InstanceId { get; set; } + /// + /// The UUID of the device the asset is associated with. + /// [JsonPropertyName("deviceUuid")] public string DeviceUuid { get; set; } + /// + /// Whether the asset has been marked as removed. + /// [JsonPropertyName("removed")] public bool Removed { get; set; } //[JsonPropertyName("description")] //public JsonDescription Description { get; set; } + /// + /// Free-form description of the asset. + /// [JsonPropertyName("description")] public string Description { get; set; } + /// + /// The kind of QIF document being wrapped (for example PLAN, + /// RESULTS, RULES, STATISTICS). + /// [JsonPropertyName("qifDocumentType")] public string QIFDocumentType { get; set; } + /// + /// The serialized QIF document content. + /// [JsonPropertyName("qifDocument")] public string QIFDocument { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonQIFDocumentWrapperAsset() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , serializing the QIF + /// document type as its enumeration name. + /// public JsonQIFDocumentWrapperAsset(QIFDocumentWrapperAsset asset) { if (asset != null) @@ -64,6 +110,11 @@ public JsonQIFDocumentWrapperAsset(QIFDocumentWrapperAsset asset) } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing the QIF document + /// type enumeration from its serialized form. + /// public QIFDocumentWrapperAsset ToQIFDocumentWrapperAsset() { var asset = new QIFDocumentWrapperAsset(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/RawMaterials/JsonMaterial.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/RawMaterials/JsonMaterial.cs index 629399e40..1d83882ca 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/RawMaterials/JsonMaterial.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/RawMaterials/JsonMaterial.cs @@ -7,35 +7,75 @@ namespace MTConnect.Assets.Json.RawMaterials { + /// + /// JSON serialization surrogate for the Material sub-element of + /// a RawMaterial asset in the cppagent-compatible shape. Identifies + /// the material itself (composition, manufacturer, lot, manufacturing + /// date and codes) independently of the consumable quantity reported + /// on the containing RawMaterial asset. Converts to and from the + /// strongly-typed model. + /// public class JsonMaterial { + /// + /// The unique id of the material. + /// [JsonPropertyName("id")] public string Id { get; set; } + /// + /// The descriptive name of the material. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The kind of material (for example BAR, SHEET, BLOCK). + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The lot or batch number of the material. + /// [JsonPropertyName("Lot")] public string Lot { get; set; } + /// + /// The manufacturer of the material. + /// [JsonPropertyName("Manufacturer")] public string Manufacturer { get; set; } + /// + /// The date the material was manufactured. + /// [JsonPropertyName("ManufacturingDate")] public DateTime? ManufacturingDate { get; set; } + /// + /// The manufacturer's part or production code for the material. + /// [JsonPropertyName("ManufacturingCode")] public string ManufacturingCode { get; set; } + /// + /// The material composition code (for example an alloy or grade + /// designation). + /// [JsonPropertyName("MaterialCode")] public string MaterialCode { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonMaterial() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonMaterial(IMaterial material) { if (material != null) @@ -52,6 +92,10 @@ public JsonMaterial(IMaterial material) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IMaterial ToMaterial() { var material = new Material(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Assets/RawMaterials/JsonRawMaterialAsset.cs b/libraries/MTConnect.NET-JSON-cppagent/Assets/RawMaterials/JsonRawMaterialAsset.cs index 046984ff0..4fe8ea143 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Assets/RawMaterials/JsonRawMaterialAsset.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Assets/RawMaterials/JsonRawMaterialAsset.cs @@ -8,80 +8,162 @@ namespace MTConnect.Assets.Json.RawMaterials { + /// + /// JSON serialization surrogate for an MTConnect RawMaterial asset + /// in the cppagent-compatible JSON shape. Converts to and from the + /// strongly-typed model. + /// public class JsonRawMaterialAsset { + /// + /// The unique identifier of the asset. + /// [JsonPropertyName("assetId")] public string AssetId { get; set; } + /// + /// The timestamp at which the asset was last reported. + /// [JsonPropertyName("timestamp")] public DateTime Timestamp { get; set; } + /// + /// The instance identifier of the agent that produced this asset. + /// [JsonPropertyName("instanceId")] public ulong InstanceId { get; set; } + /// + /// The UUID of the device the asset is associated with. + /// [JsonPropertyName("deviceUuid")] public string DeviceUuid { get; set; } + /// + /// Whether the asset has been removed from the agent. + /// [JsonPropertyName("removed")] public bool Removed { get; set; } //[JsonPropertyName("description")] //public JsonDescription Description { get; set; } + /// + /// The free-form description of the asset. + /// [JsonPropertyName("description")] public string Description { get; set; } + /// + /// The human-readable name of the raw material. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The type of container holding the raw material. + /// [JsonPropertyName("containerType")] public string ContainerType { get; set; } + /// + /// The manufacturing process the raw material is intended for. + /// [JsonPropertyName("processKind")] public string ProcessKind { get; set; } + /// + /// The serial number that uniquely identifies this raw material. + /// [JsonPropertyName("serialNumber")] public string SerialNumber { get; set; } + /// + /// The physical form of the material (for example BAR, BLOCK, or + /// POWDER), serialized as the enumeration name. + /// [JsonPropertyName("Form")] public string Form { get; set; } + /// + /// Whether the container currently holds material. + /// [JsonPropertyName("HasMaterial")] public bool? HasMaterial { get; set; } + /// + /// The date the raw material was manufactured. + /// [JsonPropertyName("ManufacturingDate")] public DateTime? ManufacturingDate { get; set; } + /// + /// The date the raw material was first used. + /// [JsonPropertyName("FirstUseDate")] public DateTime? FirstUseDate { get; set; } + /// + /// The date the raw material was last used. + /// [JsonPropertyName("LastUseDate")] public DateTime? LastUseDate { get; set; } + /// + /// The volume of unused material when first received. + /// [JsonPropertyName("InitialVolume")] public double? InitialVolume { get; set; } + /// + /// The dimension of unused material when first received, serialized as + /// a millimeter 3D string. + /// [JsonPropertyName("InitialDimension")] public string InitialDimension { get; set; } + /// + /// The quantity of unused material when first received. + /// [JsonPropertyName("InitialQuantity")] public int? InitialQuantity { get; set; } + /// + /// The volume of material currently remaining. + /// [JsonPropertyName("CurrentVolume")] public double? CurrentVolume { get; set; } + /// + /// The dimension of material currently remaining, serialized as a + /// millimeter 3D string. + /// [JsonPropertyName("CurrentDimension")] public string CurrentDimension { get; set; } + /// + /// The quantity of material currently remaining. + /// [JsonPropertyName("CurrentQuantity")] public int? CurrentQuantity { get; set; } + /// + /// The material the raw material is made of. + /// [JsonPropertyName("Material")] public JsonMaterial Material { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonRawMaterialAsset() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , converting enumerations and + /// dimensions to their string representations. + /// public JsonRawMaterialAsset(IRawMaterialAsset asset) { if (asset != null) @@ -116,6 +198,11 @@ public JsonRawMaterialAsset(IRawMaterialAsset asset) } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing enumerations and + /// millimeter 3D dimension strings. + /// public IRawMaterialAsset ToRawMaterialAsset() { var asset = new RawMaterialAsset(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonAbstractSpecification.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonAbstractSpecification.cs index e143c497e..59c919fef 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonAbstractSpecification.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonAbstractSpecification.cs @@ -6,38 +6,84 @@ namespace MTConnect.Devices.Json { + /// + /// Shared JSON serialization surrogate for the common attributes of any + /// Specification in the cppagent-compatible shape. Carries the + /// identifying attributes and the optional originator override, omitting + /// the originator field when it equals the implicit default of + /// MANUFACTURER to keep the wire shape minimal. + /// public class JsonAbstractSpecification { + /// + /// The unique id of the specification. + /// [JsonPropertyName("id")] public string Id { get; set; } + /// + /// The descriptive name of the specification. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The type of the specification (semantic category). + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// Optional sub-type qualifier of the specification. + /// [JsonPropertyName("subType")] public string SubType { get; set; } + /// + /// Reference to the id of the data item this specification + /// constrains. + /// [JsonPropertyName("dataItemIdRef")] public string DataItemIdRef { get; set; } + /// + /// Engineering units of the specification limits. + /// [JsonPropertyName("units")] public string Units { get; set; } + /// + /// Reference to the id of the composition the specification + /// applies to. + /// [JsonPropertyName("compositionIdRef")] public string CompositionIdRef { get; set; } + /// + /// Reference to the id of the coordinate system the + /// specification limits are expressed in. + /// [JsonPropertyName("coordinateSystemIdRef")] public string CoordinateSystemIdRef { get; set; } + /// + /// The party that authored the specification (only emitted when it + /// differs from the implicit MANUFACTURER default). + /// [JsonPropertyName("originator")] public string Originator { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonAbstractSpecification() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , suppressing the originator when it + /// equals the implicit default of MANUFACTURER. + /// public JsonAbstractSpecification(ISpecification specification) { if (specification != null) @@ -55,6 +101,11 @@ public JsonAbstractSpecification(ISpecification specification) } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing the originator enumeration + /// from its serialized form. + /// public virtual ISpecification ToSpecification() { var specification = new Specification(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonAlarmLimits.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonAlarmLimits.cs index e0a084b15..db45f7e81 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonAlarmLimits.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonAlarmLimits.cs @@ -6,23 +6,52 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for the AlarmLimits + /// sub-element of a ProcessSpecification in the + /// cppagent-compatible shape. Carries the engineering bounds whose + /// breach triggers an alarm condition, plus the early-warning + /// thresholds. Converts to and from the strongly-typed + /// model. + /// public class JsonAlarmLimits { + /// + /// The upper alarm limit; values above this should raise an + /// alarm. + /// [JsonPropertyName("UpperLimit")] public double? UpperLimit { get; set; } + /// + /// The upper warning threshold before the upper alarm limit. + /// [JsonPropertyName("UpperWarning")] public double? UpperWarning { get; set; } + /// + /// The lower alarm limit; values below this should raise an + /// alarm. + /// [JsonPropertyName("LowerLimit")] public double? LowerLimit { get; set; } + /// + /// The lower warning threshold before the lower alarm limit. + /// [JsonPropertyName("LowerWarning")] public double? LowerWarning { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonAlarmLimits() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonAlarmLimits(IAlarmLimits alarmLimits) { if (alarmLimits != null) @@ -35,6 +64,10 @@ public JsonAlarmLimits(IAlarmLimits alarmLimits) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IAlarmLimits ToAlarmLimits() { var alarmLimits = new AlarmLimits(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonAxisDataSet.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonAxisDataSet.cs index 2805fbbc0..2c1b936b3 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonAxisDataSet.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonAxisDataSet.cs @@ -12,20 +12,43 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a Configuration Axis + /// expressed as a data set in the cppagent-compatible shape. The + /// flat {"X": v, "Y": v, "Z": v} PascalCase object encoding + /// matches the cppagent v2 DataSet convention. Converts to and from + /// the strongly-typed model. + /// public class JsonAxisDataSet { + /// + /// Component of the axis along the X direction. + /// [JsonPropertyName("X")] public double X { get; set; } + /// + /// Component of the axis along the Y direction. + /// [JsonPropertyName("Y")] public double Y { get; set; } + /// + /// Component of the axis along the Z direction. + /// [JsonPropertyName("Z")] public double Z { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonAxisDataSet() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonAxisDataSet(IAxisDataSet dataSet) { if (dataSet != null) @@ -37,6 +60,10 @@ public JsonAxisDataSet(IAxisDataSet dataSet) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IAxisDataSet ToAxisDataSet() { var dataSet = new AxisDataSet(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonCellDefinition.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonCellDefinition.cs index a0a4b09fd..1413f9917 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonCellDefinition.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonCellDefinition.cs @@ -7,29 +7,61 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a CellDefinition in the + /// cppagent-compatible shape. Describes a single cell schema within + /// a TABLE entry definition. Converts to and from the strongly-typed + /// model. + /// public class JsonCellDefinition { + /// + /// The dictionary key the cell is keyed on at runtime. + /// [JsonPropertyName("key")] public string Key { get; set; } + /// + /// The semantic type of the key (for example a controlled + /// vocabulary identifier). + /// [JsonPropertyName("keyType")] public string KeyType { get; set; } + /// + /// Engineering units of the cell's value. + /// [JsonPropertyName("units")] public string Units { get; set; } + /// + /// The MTConnect type of the cell's value. + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// Optional sub-type qualifier of the cell's value. + /// [JsonPropertyName("subType")] public string SubType { get; set; } + /// + /// Free-form description of the cell. + /// [JsonPropertyName("Description")] public string Description { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCellDefinition() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonCellDefinition(ICellDefinition definition) { if (definition != null) @@ -49,6 +81,10 @@ public JsonCellDefinition(ICellDefinition definition) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public ICellDefinition ToCellDefinition() { var definition = new CellDefinition(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonCellDefinitions.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonCellDefinitions.cs index b7d003244..6ab86b244 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonCellDefinitions.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonCellDefinitions.cs @@ -6,14 +6,28 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a typed container of + /// items, keyed by the singular + /// cppagent element name CellDefinition. + /// public class JsonCellDefinitions { + /// + /// The cell definitions in the container. + /// [JsonPropertyName("CellDefinition")] public IEnumerable CellDefinitions { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCellDefinitions() { } + /// + /// Initializes the container from a cell-definition sequence. + /// public JsonCellDefinitions(IEnumerable cellDefinitions) { if (!cellDefinitions.IsNullOrEmpty()) @@ -27,6 +41,10 @@ public JsonCellDefinitions(IEnumerable cellDefinitions) } + /// + /// Flattens the container back into a uniform + /// sequence. + /// public IEnumerable ToCellDefinitions() { var cellDefinitions = new List(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonChannel.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonChannel.cs index bbfefb348..f5d21ef80 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonChannel.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonChannel.cs @@ -7,29 +7,62 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a sensor Channel in the + /// cppagent-compatible shape. Identifies a single signal channel + /// inside a SensorConfiguration, including its calibration + /// history. Converts to and from the strongly-typed + /// model. + /// public class JsonChannel { + /// + /// The numeric identifier of the channel within its sensor. + /// [JsonPropertyName("number")] public string Number { get; set; } + /// + /// The descriptive name of the channel. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// Date of the last calibration of the channel. + /// [JsonPropertyName("CalibrationDate")] public DateTime? CalibrationDate { get; set; } + /// + /// Date of the next scheduled calibration of the channel. + /// [JsonPropertyName("NextCalibrationDate")] public DateTime? NextCalibrationDate { get; set; } + /// + /// Initials of the technician who performed the most recent + /// calibration. + /// [JsonPropertyName("CalibrationInitials")] public string CalibrationInitials { get; set; } + /// + /// Free-form description of the channel. + /// [JsonPropertyName("Description")] public string Description { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonChannel() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonChannel(IChannel channel) { if (channel != null) @@ -49,6 +82,10 @@ public JsonChannel(IChannel channel) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IChannel ToChannel() { var channel = new Channel(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonChannels.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonChannels.cs index 31e135c4f..f3cfae52a 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonChannels.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonChannels.cs @@ -7,14 +7,28 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a typed container of + /// items inside a SensorConfiguration, + /// keyed by the singular cppagent element name Channel. + /// public class JsonChannels { + /// + /// The channel definitions in the container. + /// [JsonPropertyName("Channel")] public IEnumerable Channels { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonChannels() { } + /// + /// Initializes the container from a channel sequence. + /// public JsonChannels(IEnumerable channels) { if (!channels.IsNullOrEmpty()) @@ -28,6 +42,10 @@ public JsonChannels(IEnumerable channels) } + /// + /// Flattens the container back into a uniform + /// sequence. + /// public IEnumerable ToChannels() { var channels = new List(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonComponent.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonComponent.cs index ad1f2bee3..5ce7906bc 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonComponent.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonComponent.cs @@ -5,51 +5,111 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for an MTConnect Component in the + /// cppagent-compatible shape. The component's type is implicit in + /// the parent's container property name, so this surrogate omits it and + /// receives it back when reconstructed via + /// . + /// public class JsonComponent { + /// + /// The unique id of the component. + /// [JsonPropertyName("id")] public string Id { get; set; } + /// + /// The optional human-readable name of the component. Omitted + /// from the JSON output when not set. + /// [JsonPropertyName("name")] [JsonIgnore(Condition = JsonIgnoreCondition.WhenWritingNull)] public string Name { get; set; } + /// + /// The name the component is known by in the native data source. + /// [JsonPropertyName("nativeName")] public string NativeName { get; set; } + /// + /// The interval, in milliseconds, between samples of the component's + /// data, when reported. + /// [JsonPropertyName("sampleInterval")] public double? SampleInterval { get; set; } + /// + /// The rate, in samples per second, at which the component's data is + /// sampled, when reported. + /// [JsonPropertyName("sampleRate")] public double? SampleRate { get; set; } + /// + /// The universally unique identifier of the component instance. + /// [JsonPropertyName("uuid")] public string Uuid { get; set; } + /// + /// Reference to the id of a CoordinateSystem the component's + /// values are expressed relative to. + /// [JsonPropertyName("coordinateSystemIdRef")] public string CoordinateSystemIdRef { get; set; } + /// + /// The descriptive metadata for the component. + /// [JsonPropertyName("Description")] public JsonDescription Description { get; set; } + /// + /// The configuration of the component. + /// [JsonPropertyName("Configuration")] public JsonConfiguration Configuration { get; set; } + /// + /// The data items reported directly by the component, wrapped in a + /// counted container. + /// [JsonPropertyName("DataItems")] public JsonDataItems DataItems { get; set; } + /// + /// The compositions of the component, wrapped in a counted container. + /// [JsonPropertyName("Compositions")] public JsonCompositions Compositions { get; set; } + /// + /// The child components, wrapped in a counted container. + /// [JsonPropertyName("Components")] public JsonComponents Components { get; set; } + /// + /// The references from the component to other components and data + /// items. + /// [JsonPropertyName("References")] public JsonReferenceContainer References { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonComponent() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , wrapping the child collections in their + /// counted container types. + /// public JsonComponent(IComponent component) { if (component != null) @@ -91,8 +151,17 @@ public JsonComponent(IComponent component) } + /// + /// Returns the JSON representation of this surrogate. + /// public override string ToString() => JsonFunctions.Convert(this); + /// + /// Converts this surrogate to a strongly-typed , + /// applying as the component's + /// MTConnect type (which is implicit in the wire format) and + /// unwrapping each child container. + /// public Component ToComponent(string componentType) { var component = new Component(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonComponentReference.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonComponentReference.cs index 6eaa5ebdf..61f549090 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonComponentReference.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonComponentReference.cs @@ -6,17 +6,35 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a ComponentReference in + /// the cppagent-compatible shape, pointing at a component by its + /// id with an optional display name. + /// public class JsonComponentReference { + /// + /// Reference to the id of the target component. + /// [JsonPropertyName("idRef")] public string IdRef { get; set; } + /// + /// Optional display name for the reference. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonComponentReference() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonComponentReference(IComponentReference reference) { if (reference != null) @@ -27,6 +45,10 @@ public JsonComponentReference(IComponentReference reference) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public virtual IReference ToReference() { var reference = new ComponentReference(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonComponents.g.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonComponents.g.cs index 0359cd80c..96b82711a 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonComponents.g.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonComponents.g.cs @@ -8,487 +8,976 @@ namespace MTConnect.Devices.Json { + /// + /// cppagent-style JSON representation of a device's component tree. Each MTConnect + /// component type is exposed as its own strongly-typed collection so the + /// System.Text.Json serializer emits one property per type, matching the + /// flattened object shape the C++ reference agent produces. + /// public class JsonComponents { + /// + /// The set of Actuator components on the device. + /// Component composed of a physical apparatus that moves or controls a mechanism or system. + /// [JsonPropertyName("Actuator")] public IEnumerable Actuator { get; set; } + /// + /// The set of Adapter components on the device. + /// Component that provides information about the data source for an MTConnect Agent. + /// [JsonPropertyName("Adapter")] public IEnumerable Adapter { get; set; } + /// + /// The set of Adapters components on the device. + /// Component that organize Adapter types. + /// [JsonPropertyName("Adapters")] public IEnumerable Adapters { get; set; } + /// + /// The set of AirHandler components on the device. + /// System that circulates air or regulates airflow without altering temperature or humidity. + /// [JsonPropertyName("AirHandler")] public IEnumerable AirHandler { get; set; } + /// + /// The set of Amplifier components on the device. + /// Leaf Component composed of an electronic component or circuit that amplifies power, electric current, or voltage. + /// [JsonPropertyName("Amplifier")] public IEnumerable Amplifier { get; set; } + /// + /// The set of AutomaticToolChanger components on the device. + /// ToolingDelivery composed of a tool delivery mechanism that moves tools between a ToolMagazine and a spindle a Turret. + /// [JsonPropertyName("AutomaticToolChanger")] public IEnumerable AutomaticToolChanger { get; set; } + /// + /// The set of Auxiliaries components on the device. + /// Component that organize Auxiliary types. + /// [JsonPropertyName("Auxiliaries")] public IEnumerable Auxiliaries { get; set; } + /// + /// The set of Auxiliary components on the device. + /// Abstract Component composed of removable part(s) of a piece of equipment that provides supplementary or extended functionality. + /// [JsonPropertyName("Auxiliary")] public IEnumerable Auxiliary { get; set; } + /// + /// The set of Axes components on the device. + /// Axis types. + /// [JsonPropertyName("Axes")] public IEnumerable Axes { get; set; } + /// + /// The set of Axis components on the device. + /// Abstract Component composed of a motion system that provides linear or rotational motion for a piece of equipment. + /// [JsonPropertyName("Axis")] public IEnumerable Axis { get; set; } + /// + /// The set of Ballscrew components on the device. + /// Leaf Component composed of a mechanical structure that transforms rotary motion into linear motion. + /// [JsonPropertyName("Ballscrew")] public IEnumerable Ballscrew { get; set; } + /// + /// The set of BarFeeder components on the device. + /// Loader that delivers bar stock to a piece of equipment. + /// [JsonPropertyName("BarFeeder")] public IEnumerable BarFeeder { get; set; } + /// + /// The set of Belt components on the device. + /// Leaf Component composed of an endless flexible band that transmits motion for a piece of equipment or conveys materials and objects. + /// [JsonPropertyName("Belt")] public IEnumerable Belt { get; set; } + /// + /// The set of Brake components on the device. + /// Leaf Component that slows or stops a moving object by the absorption or transfer of the energy of momentum, usually by means of friction, electrical force, or magnetic force. + /// [JsonPropertyName("Brake")] public IEnumerable Brake { get; set; } + /// + /// The set of Chain components on the device. + /// Leaf Component composed of interconnected series of objects that band together and are used to transmit motion for a piece of equipment or to convey materials and objects. + /// [JsonPropertyName("Chain")] public IEnumerable Chain { get; set; } + /// + /// The set of Chopper components on the device. + /// Leaf Component that breaks material into smaller pieces. + /// [JsonPropertyName("Chopper")] public IEnumerable Chopper { get; set; } + /// + /// The set of Chuck components on the device. + /// Leaf Component composed of a mechanism that holds a part or stock material in place. + /// [JsonPropertyName("Chuck")] public IEnumerable Chuck { get; set; } + /// + /// The set of Chute components on the device. + /// Leaf Component composed of an inclined channel that conveys material. + /// [JsonPropertyName("Chute")] public IEnumerable Chute { get; set; } + /// + /// The set of CircuitBreaker components on the device. + /// Leaf Component that interrupts an electric circuit. + /// [JsonPropertyName("CircuitBreaker")] public IEnumerable CircuitBreaker { get; set; } + /// + /// The set of Clamp components on the device. + /// Leaf Component that strengthens, support, or fastens objects in place. + /// [JsonPropertyName("Clamp")] public IEnumerable Clamp { get; set; } + /// + /// The set of Compressor components on the device. + /// Leaf Component composed of a pump or other mechanism that reduces volume and increases pressure of gases in order to condense the gases to drive pneumatically powered pieces of equipment. + /// [JsonPropertyName("Compressor")] public IEnumerable Compressor { get; set; } + /// + /// The set of Controller components on the device. + /// System that provides regulation or management of a system or component. ISO 16484-5:2017 + /// [JsonPropertyName("Controller")] public IEnumerable Controller { get; set; } + /// + /// The set of Controllers components on the device. + /// Component that organize Controller entities. + /// [JsonPropertyName("Controllers")] public IEnumerable Controllers { get; set; } + /// + /// The set of Coolant components on the device. + /// System that provides distribution and management of fluids that remove heat from a piece of equipment. + /// [JsonPropertyName("Coolant")] public IEnumerable Coolant { get; set; } + /// + /// The set of Cooling components on the device. + /// System that extracts controlled amounts of heat to achieve a target temperature at a specified cooling rate. + /// [JsonPropertyName("Cooling")] public IEnumerable Cooling { get; set; } + /// + /// The set of CoolingTower components on the device. + /// Leaf Component composed of a heat exchange system that uses a fluid to transfer heat to the atmosphere. + /// [JsonPropertyName("CoolingTower")] public IEnumerable CoolingTower { get; set; } + /// + /// The set of CuttingTorch components on the device. + /// Auxiliary that employs a concentrated flame to both sever materials through cutting and fuse them together in joining processes. + /// [JsonPropertyName("CuttingTorch")] public IEnumerable CuttingTorch { get; set; } + /// + /// The set of Deposition components on the device. + /// Auxiliary that manages the addition of material or state change of material being performed in an additive manufacturing process. + /// [JsonPropertyName("Deposition")] public IEnumerable Deposition { get; set; } + /// + /// The set of Dielectric components on the device. + /// System that manages a chemical mixture used in a manufacturing process being performed at that piece of equipment. + /// [JsonPropertyName("Dielectric")] public IEnumerable Dielectric { get; set; } + /// + /// The set of Door components on the device. + /// Component composed of a mechanical mechanism or closure that can cover a physical access portal into a piece of equipment allowing or restricting access to other parts of the equipment. + /// [JsonPropertyName("Door")] public IEnumerable Door { get; set; } + /// + /// The set of Drain components on the device. + /// Leaf Component that allows material to flow for the purpose of drainage from, for example, a vessel or tank. + /// [JsonPropertyName("Drain")] public IEnumerable Drain { get; set; } + /// + /// The set of Electric components on the device. + /// System composed of the main power supply for the piece of equipment that provides distribution of that power throughout the equipment. + /// [JsonPropertyName("Electric")] public IEnumerable Electric { get; set; } + /// + /// The set of Electrode components on the device. + /// Auxiliary that is used for many electrical discharge manufacturing processes like welding. + /// [JsonPropertyName("Electrode")] public IEnumerable Electrode { get; set; } + /// + /// The set of Enclosure components on the device. + /// System composed of a structure that is used to contain or isolate a piece of equipment or area. + /// [JsonPropertyName("Enclosure")] public IEnumerable Enclosure { get; set; } + /// + /// The set of Encoder components on the device. + /// Leaf Component that measures position. + /// [JsonPropertyName("Encoder")] public IEnumerable Encoder { get; set; } + /// + /// The set of EndEffector components on the device. + /// System composed of functions that form the last link segment of a piece of equipment. + /// [JsonPropertyName("EndEffector")] public IEnumerable EndEffector { get; set; } + /// + /// The set of Environmental components on the device. + /// Component that observes the surroundings of another Component.> Note: Environmental **SHOULD** be organized by Auxillaries, Systems or Parts depending on the relationship to the Component. + /// [JsonPropertyName("Environmental")] public IEnumerable Environmental { get; set; } + /// + /// The set of ExpiredPot components on the device. + /// Leaf Component that is a Pot for a tool that is no longer usable for removal from a ToolMagazine or Turret. + /// [JsonPropertyName("ExpiredPot")] public IEnumerable ExpiredPot { get; set; } + /// + /// The set of ExposureUnit components on the device. + /// Leaf Component that emits a type of radiation. + /// [JsonPropertyName("ExposureUnit")] public IEnumerable ExposureUnit { get; set; } + /// + /// The set of ExtrusionUnit components on the device. + /// Leaf Component that dispenses liquid or powered materials. + /// [JsonPropertyName("ExtrusionUnit")] public IEnumerable ExtrusionUnit { get; set; } + /// + /// The set of Fan components on the device. + /// Leaf Component that produces a current of air. + /// [JsonPropertyName("Fan")] public IEnumerable Fan { get; set; } + /// + /// The set of FeatureOccurrence components on the device. + /// Component that provides information related to an individual feature. + /// [JsonPropertyName("FeatureOccurrence")] public IEnumerable FeatureOccurrence { get; set; } + /// + /// The set of Feeder components on the device. + /// System that manages the delivery of materials within a piece of equipment. + /// [JsonPropertyName("Feeder")] public IEnumerable Feeder { get; set; } + /// + /// The set of Filter components on the device. + /// Leaf Component through which liquids or gases are passed to remove suspended impurities or to recover solids. + /// [JsonPropertyName("Filter")] public IEnumerable Filter { get; set; } + /// + /// The set of Galvanomotor components on the device. + /// Leaf Component composed of an electromechanical actuator that produces deflection of a beam of light or energy in response to electric current through its coil in a magnetic field. + /// [JsonPropertyName("Galvanomotor")] public IEnumerable Galvanomotor { get; set; } + /// + /// The set of GangToolBar components on the device. + /// ToolingDelivery composed of a tool mounting mechanism that holds any number of tools. + /// [JsonPropertyName("GangToolBar")] public IEnumerable GangToolBar { get; set; } + /// + /// The set of Gripper components on the device. + /// Leaf Component that holds a part, stock material, or any other item in place. + /// [JsonPropertyName("Gripper")] public IEnumerable Gripper { get; set; } + /// + /// The set of Heating components on the device. + /// System that delivers controlled amounts of heat to achieve a target temperature at a specified heating rate. + /// [JsonPropertyName("Heating")] public IEnumerable Heating { get; set; } + /// + /// The set of Hopper components on the device. + /// Leaf Component composed of a chamber or bin in which materials are stored temporarily, typically being filled through the top and dispensed through the bottom. + /// [JsonPropertyName("Hopper")] public IEnumerable Hopper { get; set; } + /// + /// The set of Hydraulic components on the device. + /// System that provides movement and distribution of pressurized liquid throughout the piece of equipment. + /// [JsonPropertyName("Hydraulic")] public IEnumerable Hydraulic { get; set; } + /// + /// The set of Interfaces components on the device. + /// Component that organize Interface types. + /// [JsonPropertyName("Interfaces")] public IEnumerable Interfaces { get; set; } + /// + /// The set of Linear components on the device. + /// Axis that provides prismatic motion along a fixed axis. + /// [JsonPropertyName("Linear")] public IEnumerable Linear { get; set; } + /// + /// The set of LinearPositionFeedback components on the device. + /// Leaf Component that measures linear motion or position.**DEPRECATION WARNING** : May be deprecated in the future. Recommend using Encoder. + /// [JsonPropertyName("LinearPositionFeedback")] public IEnumerable LinearPositionFeedback { get; set; } + /// + /// The set of Link components on the device. + /// Structure that provides a connection between Component entities. + /// [JsonPropertyName("Link")] public IEnumerable Link { get; set; } + /// + /// The set of Loader components on the device. + /// Auxiliary that provides movement and distribution of materials, parts, tooling, and other items to or from a piece of equipment. + /// [JsonPropertyName("Loader")] public IEnumerable Loader { get; set; } + /// + /// The set of Lock components on the device. + /// Component that physically prohibits a Device or Component from opening or operating. + /// [JsonPropertyName("Lock")] public IEnumerable Lock { get; set; } + /// + /// The set of Lubrication components on the device. + /// System that provides distribution and management of fluids used to lubricate portions of the piece of equipment. + /// [JsonPropertyName("Lubrication")] public IEnumerable Lubrication { get; set; } + /// + /// The set of Material components on the device. + /// Resource composed of material that is consumed or used by the piece of equipment for production of parts, materials, or other types of goods. + /// [JsonPropertyName("Material")] public IEnumerable Material { get; set; } + /// + /// The set of Materials components on the device. + /// Resources that organize Material types. + /// [JsonPropertyName("Materials")] public IEnumerable Materials { get; set; } + /// + /// The set of Motor components on the device. + /// Leaf Component that converts electrical, pneumatic, or hydraulic energy into mechanical energy. + /// [JsonPropertyName("Motor")] public IEnumerable Motor { get; set; } + /// + /// The set of Oil components on the device. + /// Leaf Component composed of a viscous liquid. + /// [JsonPropertyName("Oil")] public IEnumerable Oil { get; set; } + /// + /// The set of Part components on the device. + /// Abstract Component composed of a part being processed by a piece of equipment. + /// [JsonPropertyName("Part")] public IEnumerable Part { get; set; } + /// + /// The set of PartOccurrence components on the device. + /// Part that exists at a specific place and time, such as a specific instance of a bracket at a specific timestamp. + /// [JsonPropertyName("PartOccurrence")] public IEnumerable PartOccurrence { get; set; } + /// + /// The set of Parts components on the device. + /// Component that organize Part types. + /// [JsonPropertyName("Parts")] public IEnumerable Parts { get; set; } + /// + /// The set of Path components on the device. + /// Component that organizes an independent operation or function within a Controller. + /// [JsonPropertyName("Path")] public IEnumerable Path { get; set; } + /// + /// The set of Personnel components on the device. + /// Resource composed of an individual or individuals who either control, support, or otherwise interface with a piece of equipment. + /// [JsonPropertyName("Personnel")] public IEnumerable Personnel { get; set; } + /// + /// The set of PinTool components on the device. + /// System composed of a tool that performs the work for a Friction Stir Welding process + /// [JsonPropertyName("PinTool")] public IEnumerable PinTool { get; set; } + /// + /// The set of Pneumatic components on the device. + /// System that uses compressed gasses to actuate components or do work within the piece of equipment. + /// [JsonPropertyName("Pneumatic")] public IEnumerable Pneumatic { get; set; } + /// + /// The set of Pot components on the device. + /// Leaf Component composed of a tool storage location associated with a ToolMagazine or AutomaticToolChanger. + /// [JsonPropertyName("Pot")] public IEnumerable Pot { get; set; } + /// + /// The set of Power components on the device. + /// Power was **DEPRECATED** in *MTConnect Version 1.1* and was replaced by Availability data item type. + /// [JsonPropertyName("Power")] public IEnumerable Power { get; set; } + /// + /// The set of PowerSupply components on the device. + /// Leaf Component that provides power to electric mechanisms. + /// [JsonPropertyName("PowerSupply")] public IEnumerable PowerSupply { get; set; } + /// + /// The set of Pressure components on the device. + /// System that delivers compressed gas or fluid and controls the pressure and rate of pressure change to a desired target set-point. + /// [JsonPropertyName("Pressure")] public IEnumerable Pressure { get; set; } + /// + /// The set of Process components on the device. + /// Abstract Component composed of a manufacturing process being executed on a piece of equipment. + /// [JsonPropertyName("Process")] public IEnumerable Process { get; set; } + /// + /// The set of Processes components on the device. + /// Component that organize Process types. + /// [JsonPropertyName("Processes")] public IEnumerable Processes { get; set; } + /// + /// The set of ProcessOccurrence components on the device. + /// Process that takes place at a specific place and time, such as a specific instance of part-milling occurring at a specific timestamp. + /// [JsonPropertyName("ProcessOccurrence")] public IEnumerable ProcessOccurrence { get; set; } + /// + /// The set of ProcessPower components on the device. + /// System composed of a power source associated with a piece of equipment that supplies energy to the manufacturing process separate from the Electric system. + /// [JsonPropertyName("ProcessPower")] public IEnumerable ProcessPower { get; set; } + /// + /// The set of Protective components on the device. + /// System that provides functions used to detect or prevent harm or damage to equipment or personnel. + /// [JsonPropertyName("Protective")] public IEnumerable Protective { get; set; } + /// + /// The set of Pulley components on the device. + /// Leaf Component composed of a mechanism or wheel that turns in a frame or block and serves to change the direction of or to transmit force. + /// [JsonPropertyName("Pulley")] public IEnumerable Pulley { get; set; } + /// + /// The set of Pump components on the device. + /// Leaf Component that raises, drives, exhausts, or compresses fluids or gases by means of a piston, plunger, or set of rotating vanes. + /// [JsonPropertyName("Pump")] public IEnumerable Pump { get; set; } + /// + /// The set of Reel components on the device. + /// Leaf Component composed of a rotary storage unit for material. + /// [JsonPropertyName("Reel")] public IEnumerable Reel { get; set; } + /// + /// The set of RemovalPot components on the device. + /// Leaf Component that is a Pot for a tool that has to be removed from a ToolMagazine or Turret to a location outside of the piece of equipment. + /// [JsonPropertyName("RemovalPot")] public IEnumerable RemovalPot { get; set; } + /// + /// The set of Resource components on the device. + /// Abstract Component composed of material or personnel involved in a manufacturing process. + /// [JsonPropertyName("Resource")] public IEnumerable Resource { get; set; } + /// + /// The set of Resources components on the device. + /// Component that organize Resource types. + /// [JsonPropertyName("Resources")] public IEnumerable Resources { get; set; } + /// + /// The set of ReturnPot components on the device. + /// Leaf Component that is a Pot for a tool that has been removed from spindle or Turret and awaiting for return to a ToolMagazine. + /// [JsonPropertyName("ReturnPot")] public IEnumerable ReturnPot { get; set; } + /// + /// The set of Rotary components on the device. + /// Axis that provides rotation about a fixed axis. + /// [JsonPropertyName("Rotary")] public IEnumerable Rotary { get; set; } + /// + /// The set of SensingElement components on the device. + /// Leaf Component that provides a signal or measured value. + /// [JsonPropertyName("SensingElement")] public IEnumerable SensingElement { get; set; } + /// + /// The set of Sensor components on the device. + /// Component that responds to a physical stimulus and transmits a resulting impulse or value from a sensing unit. + /// [JsonPropertyName("Sensor")] public IEnumerable Sensor { get; set; } + /// + /// The set of Spindle components on the device. + /// Component that provides an axis of rotation for the purpose of rapidly rotating a part or a tool to provide sufficient surface speed for cutting operations.Spindle was **DEPRECATED** in *MTConnect Version 1.1* and was replaced by RotaryMode. + /// [JsonPropertyName("Spindle")] public IEnumerable Spindle { get; set; } + /// + /// The set of Spreader components on the device. + /// Leaf Component that flattens or spreading materials. + /// [JsonPropertyName("Spreader")] public IEnumerable Spreader { get; set; } + /// + /// The set of StagingPot components on the device. + /// Leaf Component that is a Pot for a tool that is awaiting transfer to a ToolMagazine or Turret from outside of the piece of equipment. + /// [JsonPropertyName("StagingPot")] public IEnumerable StagingPot { get; set; } + /// + /// The set of Station components on the device. + /// Leaf Component composed of a storage or mounting location for a tool associated with a Turret, GangToolBar, or ToolRack. + /// [JsonPropertyName("Station")] public IEnumerable Station { get; set; } + /// + /// The set of Stock components on the device. + /// Material that is used in a manufacturing process and to which work is applied in a machine or piece of equipment to produce parts. + /// [JsonPropertyName("Stock")] public IEnumerable Stock { get; set; } + /// + /// The set of StorageBattery components on the device. + /// Leaf Component composed of one or more cells in which chemical energy is converted into electricity and used as a source of power. + /// [JsonPropertyName("StorageBattery")] public IEnumerable StorageBattery { get; set; } + /// + /// The set of Structure components on the device. + /// Component composed of part(s) comprising the rigid bodies of the piece of equipment. + /// [JsonPropertyName("Structure")] public IEnumerable Structure { get; set; } + /// + /// The set of Structures components on the device. + /// Component that organize Structure types. + /// [JsonPropertyName("Structures")] public IEnumerable Structures { get; set; } + /// + /// The set of Switch components on the device. + /// Leaf Component that turns on or off an electric current or makes or breaks a circuit. + /// [JsonPropertyName("Switch")] public IEnumerable Switch { get; set; } + /// + /// The set of System components on the device. + /// Abstract Component that is permanently integrated into the piece of equipment. + /// [JsonPropertyName("System")] public IEnumerable System { get; set; } + /// + /// The set of Systems components on the device. + /// Component that organize System types. + /// [JsonPropertyName("Systems")] public IEnumerable Systems { get; set; } + /// + /// The set of Table components on the device. + /// Leaf Component composed of a surface for holding an object or material. + /// [JsonPropertyName("Table")] public IEnumerable Table { get; set; } + /// + /// The set of Tank components on the device. + /// Leaf Component generally composed of an enclosed container. + /// [JsonPropertyName("Tank")] public IEnumerable Tank { get; set; } + /// + /// The set of Tensioner components on the device. + /// Leaf Component that provides or applies a stretch or strain to another mechanism. + /// [JsonPropertyName("Tensioner")] public IEnumerable Tensioner { get; set; } + /// + /// The set of Thermostat components on the device. + /// Component composed of a sensor or an instrument that measures temperature.Thermostat was **DEPRECATED** in *MTConnect Version 1.2* and was replaced by Temperature. + /// [JsonPropertyName("Thermostat")] public IEnumerable Thermostat { get; set; } + /// + /// The set of ToolHolder components on the device. + /// System that securely interfaces a Component with a Device + /// [JsonPropertyName("ToolHolder")] public IEnumerable ToolHolder { get; set; } + /// + /// The set of ToolingDelivery components on the device. + /// Auxiliary that manages, positions, stores, and delivers tooling within a piece of equipment. + /// [JsonPropertyName("ToolingDelivery")] public IEnumerable ToolingDelivery { get; set; } + /// + /// The set of ToolMagazine components on the device. + /// ToolingDelivery composed of a tool storage mechanism that holds any number of tools. + /// [JsonPropertyName("ToolMagazine")] public IEnumerable ToolMagazine { get; set; } + /// + /// The set of ToolRack components on the device. + /// ToolingDelivery composed of a linear or matrixed tool storage mechanism that holds any number of tools. + /// [JsonPropertyName("ToolRack")] public IEnumerable ToolRack { get; set; } + /// + /// The set of TransferArm components on the device. + /// Leaf Component that physically moves a tool from one location to another. + /// [JsonPropertyName("TransferArm")] public IEnumerable TransferArm { get; set; } + /// + /// The set of TransferPot components on the device. + /// Leaf Component that is a Pot for a tool that is awaiting transfer from a ToolMagazine to spindle or Turret. + /// [JsonPropertyName("TransferPot")] public IEnumerable TransferPot { get; set; } + /// + /// The set of Transformer components on the device. + /// Leaf Component that transforms electric energy from a source to a secondary circuit. + /// [JsonPropertyName("Transformer")] public IEnumerable Transformer { get; set; } + /// + /// The set of Turret components on the device. + /// ToolingDelivery composed of a tool mounting mechanism that holds any number of tools. + /// [JsonPropertyName("Turret")] public IEnumerable Turret { get; set; } + /// + /// The set of Vacuum components on the device. + /// System that evacuates gases and liquids from an enclosed and sealed space to a controlled negative pressure or a molecular density below the prevailing atmospheric level. + /// [JsonPropertyName("Vacuum")] public IEnumerable Vacuum { get; set; } + /// + /// The set of Valve components on the device. + /// Leaf Component that halts or controls the flow of a liquid, gas, or other material through a passage, pipe, inlet, or outlet. + /// [JsonPropertyName("Valve")] public IEnumerable Valve { get; set; } + /// + /// The set of Vat components on the device. + /// Leaf Component generally composed of an open container. + /// [JsonPropertyName("Vat")] public IEnumerable Vat { get; set; } + /// + /// The set of Vibration components on the device. + /// Component composed of a sensor or an instrument that measures the amount and/or frequency of vibration within a system.Vibration was **DEPRECATED** in *MTConnect Version 1.2* and was replaced by Displacement, Frequency etc. + /// [JsonPropertyName("Vibration")] public IEnumerable Vibration { get; set; } + /// + /// The set of WasteDisposal components on the device. + /// Auxiliary that removes manufacturing byproducts from a piece of equipment. + /// [JsonPropertyName("WasteDisposal")] public IEnumerable WasteDisposal { get; set; } + /// + /// The set of Water components on the device. + /// Leaf Component composed of $$H_2 O$$. + /// [JsonPropertyName("Water")] public IEnumerable Water { get; set; } + /// + /// The set of Wire components on the device. + /// Leaf Component composed of a string like piece or filament of relatively rigid or flexible material provided in a variety of diameters. + /// [JsonPropertyName("Wire")] public IEnumerable Wire { get; set; } + /// + /// The set of WorkEnvelope components on the device. + /// System composed of the physical process execution space within a piece of equipment. + /// [JsonPropertyName("WorkEnvelope")] public IEnumerable WorkEnvelope { get; set; } + /// + /// The set of Workpiece components on the device. + /// Leaf Component composed of an object or material on which a form of work is performed. + /// [JsonPropertyName("Workpiece")] public IEnumerable Workpiece { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonComponents() { } + /// + /// Initializes a new instance from a flat sequence of , + /// bucketing each one into the typed collection that matches its MTConnect type. + /// public JsonComponents(IEnumerable components) { if (!components.IsNullOrEmpty()) @@ -751,6 +1240,10 @@ private IEnumerable GetComponents(IEnumerable compone } + /// + /// Flattens every typed component collection back into a single + /// sequence, restoring each item's MTConnect type. + /// public IEnumerable ToComponents() { var components = new List(); @@ -996,4 +1489,4 @@ public IEnumerable ToComponents() return components; } } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonComposition.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonComposition.cs index 5687f5886..bd6d6e30d 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonComposition.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonComposition.cs @@ -7,48 +7,101 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for an MTConnect Composition in the + /// cppagent-compatible shape. Converts to and from the strongly-typed + /// model. + /// public class JsonComposition { + /// + /// The unique id of the composition. + /// [JsonPropertyName("id")] public string Id { get; set; } + /// + /// The MTConnect composition type. + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The optional human-readable name of the composition. + /// Omitted from the JSON output when not set. + /// [JsonPropertyName("name")] [JsonIgnore(Condition = JsonIgnoreCondition.WhenWritingNull)] public string Name { get; set; } + /// + /// The name the composition is known by in the native data source. + /// [JsonPropertyName("nativeName")] public string NativeName { get; set; } + /// + /// The interval, in milliseconds, between samples of the composition's + /// data, when reported. + /// [JsonPropertyName("sampleInterval")] public double? SampleInterval { get; set; } + /// + /// The rate, in samples per second, at which the composition's data is + /// sampled, when reported. + /// [JsonPropertyName("sampleRate")] public double? SampleRate { get; set; } + /// + /// The universally unique identifier of the composition instance. + /// [JsonPropertyName("uuid")] public string Uuid { get; set; } + /// + /// Reference to the id of a CoordinateSystem the composition's + /// values are expressed relative to. + /// [JsonPropertyName("coordinateSystemIdRef")] public string CoordinateSystemIdRef { get; set; } + /// + /// The descriptive metadata for the composition. + /// [JsonPropertyName("description")] public JsonDescription Description { get; set; } + /// + /// The configuration of the composition. + /// [JsonPropertyName("configuration")] public JsonConfiguration Configuration { get; set; } + /// + /// The data items reported directly by the composition. + /// [JsonPropertyName("dataItems")] public IEnumerable DataItems { get; set; } + /// + /// The references from the composition to other components and data + /// items. + /// [JsonPropertyName("references")] public JsonReferenceContainer References { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonComposition() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonComposition(IComposition composition) { if (composition != null) @@ -82,8 +135,15 @@ public JsonComposition(IComposition composition) } + /// + /// Returns the JSON representation of this surrogate. + /// public override string ToString() => JsonFunctions.Convert(this); + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public Composition ToComposition() { var composition = new Composition(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonCompositions.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonCompositions.cs index 424ac5b56..ab10561fd 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonCompositions.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonCompositions.cs @@ -6,14 +6,28 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a typed container of + /// items, keyed by the singular + /// cppagent element name Composition. + /// public class JsonCompositions { + /// + /// The compositions in the container. + /// [JsonPropertyName("Composition")] public IEnumerable Compositions { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCompositions() { } + /// + /// Initializes the container from a composition sequence. + /// public JsonCompositions(IEnumerable dataItems) { if (!dataItems.IsNullOrEmpty()) @@ -27,6 +41,10 @@ public JsonCompositions(IEnumerable dataItems) } + /// + /// Flattens the container back into a uniform + /// sequence. + /// public IEnumerable ToCompositions() { var dataItems = new List(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonConfiguration.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonConfiguration.cs index 39b5ebf21..3affcef78 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonConfiguration.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonConfiguration.cs @@ -7,29 +7,70 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a Configuration in the + /// cppagent-compatible shape. Aggregates the optional configuration + /// sub-elements (coordinate systems, motion, relationships, sensor + /// configuration, solid model, specifications), each emitted only + /// when present. Relationships and specifications are routed through + /// their typed sub-containers so that + /// ComponentRelationship/DeviceRelationship and + /// Specification/ProcessSpecification are kept in + /// separate JSON sibling arrays. Converts to and from the + /// strongly-typed model. + /// public class JsonConfiguration { + /// + /// The coordinate systems defined for the component. + /// [JsonPropertyName("CoordinateSystems")] public JsonCoordinateSystems CoordinateSystems { get; set; } + /// + /// The motion definition for the component. + /// [JsonPropertyName("Motion")] public JsonMotion Motion { get; set; } + /// + /// Relationships to other components, devices, or assets, + /// partitioned by relationship kind in the surrogate container. + /// [JsonPropertyName("Relationships")] public JsonRelationshipContainer Relationships { get; set; } + /// + /// The sensor configuration definition for the component. + /// [JsonPropertyName("SensorConfiguration")] public JsonSensorConfiguration SensorConfiguration { get; set; } + /// + /// The solid model reference for the component. + /// [JsonPropertyName("SolidModel")] public JsonSolidModel SolidModel { get; set; } + /// + /// Specifications constraining the component, partitioned into + /// scalar specifications and process specifications. + /// [JsonPropertyName("Specifications")] public JsonSpecificationContainer Specifications { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonConfiguration() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , partitioning relationships into + /// component versus device kinds and specifications into scalar + /// versus process kinds for serialization. + /// public JsonConfiguration(IConfiguration configuration) { if (configuration != null) @@ -107,10 +148,16 @@ public JsonConfiguration(IConfiguration configuration) } + /// + /// Converts this surrogate to a strongly-typed + /// , flattening the typed + /// relationship and specification sub-containers back into the + /// uniform model collections. + /// public IConfiguration ToConfiguration() { var configuration = new Configuration(); - + // Coordinate Systems if (CoordinateSystems != null) { diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonConstraints.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonConstraints.cs index 7de717ace..bc7ecf20e 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonConstraints.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonConstraints.cs @@ -6,26 +6,58 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a data-item + /// Constraints in the cppagent-compatible shape. Restricts + /// the allowed value space of a data item via numeric bounds, a + /// nominal value, an enumeration of permitted literal values, and an + /// optional change filter. Converts to and from the strongly-typed + /// model. + /// public class JsonConstraints { + /// + /// Upper numeric bound that values must not exceed. + /// [JsonPropertyName("Maximum")] public double? Maximum { get; set; } + /// + /// Lower numeric bound that values must not fall below. + /// [JsonPropertyName("Minimum")] public double? Minimum { get; set; } + /// + /// Nominal (target) value of the data item. + /// [JsonPropertyName("Nominal")] public double? Nominal { get; set; } + /// + /// Enumeration of permitted literal values, when the data item + /// is restricted to a discrete set. + /// [JsonPropertyName("Value")] public List Values { get; set; } + /// + /// Optional change filter applied to the data item. + /// [JsonPropertyName("Filter")] public JsonFilter Filter { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonConstraints() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , projecting each permitted value + /// into a . + /// public JsonConstraints(IConstraints constraints) { if (constraints != null) @@ -47,6 +79,11 @@ public JsonConstraints(IConstraints constraints) } + /// + /// Converts this surrogate to a strongly-typed + /// , flattening the permitted-value + /// projections back into plain strings. + /// public IConstraints ToConstraints() { var constraints = new Constraints(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonConstraintsValue.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonConstraintsValue.cs index fb22538ef..764226320 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonConstraintsValue.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonConstraintsValue.cs @@ -5,20 +5,38 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a single permitted-value entry + /// inside a data-item Constraints.Value list. Wraps a plain + /// string in an object so the cppagent shape can carry each value + /// as a discrete object rather than a bare string. + /// public class JsonConstraintsValue { + /// + /// The permitted literal value. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonConstraintsValue() { } + /// + /// Initializes the surrogate from a plain string value. + /// public JsonConstraintsValue(string value) { Value = value; } + /// + /// Returns the underlying string value. + /// public string ToValue() { return Value; diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonControlLimits.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonControlLimits.cs index a09c57050..53169acf6 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonControlLimits.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonControlLimits.cs @@ -6,26 +6,56 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for the ControlLimits + /// sub-element of a ProcessSpecification in the + /// cppagent-compatible shape. Carries the engineering limits the + /// process should be held within and the early-warning thresholds + /// before each limit. Converts to and from the strongly-typed + /// model. + /// public class JsonControlLimits { + /// + /// The upper engineering limit of the controlled process. + /// [JsonPropertyName("UpperLimit")] public double? UpperLimit { get; set; } + /// + /// The upper warning threshold before the upper limit. + /// [JsonPropertyName("UpperWarning")] public double? UpperWarning { get; set; } + /// + /// The nominal (target) value of the controlled process. + /// [JsonPropertyName("Nominal")] public double? Nominal { get; set; } + /// + /// The lower engineering limit of the controlled process. + /// [JsonPropertyName("LowerLimit")] public double? LowerLimit { get; set; } + /// + /// The lower warning threshold before the lower limit. + /// [JsonPropertyName("LowerWarning")] public double? LowerWarning { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonControlLimits() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonControlLimits(IControlLimits controlLimits) { if (controlLimits != null) @@ -39,6 +69,10 @@ public JsonControlLimits(IControlLimits controlLimits) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IControlLimits ToControlLimits() { var controlLimits = new ControlLimits(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonCoordinateSystem.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonCoordinateSystem.cs index 8b2298c2b..78c12d7df 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonCoordinateSystem.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonCoordinateSystem.cs @@ -7,38 +7,85 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a Configuration + /// CoordinateSystem in the cppagent-compatible shape. The origin + /// is emitted inline as a numeric JSON array when expressed as a literal + /// point, or by reference as an OriginDataSet. Converts to and + /// from the strongly-typed model. + /// public class JsonCoordinateSystem { + /// + /// The unique id of the coordinate system. + /// [JsonPropertyName("id")] public string Id { get; set; } + /// + /// The descriptive name of the coordinate system. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The native name of the coordinate system used on the equipment. + /// [JsonPropertyName("nativeName")] public string NativeName { get; set; } + /// + /// Reference to the id of the parent coordinate system this + /// one is defined relative to. + /// [JsonPropertyName("parentIdRef")] public string ParentIdRef { get; set; } + /// + /// The kind of coordinate system (for example WORLD, BASE, + /// MACHINE). + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The origin of the coordinate system as a numeric JSON array, + /// when expressed inline. + /// [JsonPropertyName("Origin")] public IEnumerable Origin { get; set; } + /// + /// The origin of the coordinate system as a data set, when + /// expressed by reference. + /// [JsonPropertyName("OriginDataSet")] public JsonOriginDataSet OriginDataSet { get; set; } + /// + /// The translation and rotation relating the coordinate system to + /// its parent. + /// [JsonPropertyName("Transformation")] public JsonTransformation Transformation { get; set; } + /// + /// Free-form description of the coordinate system. + /// [JsonPropertyName("description")] public string Description { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCoordinateSystem() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , selecting the inline numeric + /// array or data-set representation for the origin. + /// public JsonCoordinateSystem(ICoordinateSystem coordinateSystem) { if (coordinateSystem != null) @@ -56,6 +103,12 @@ public JsonCoordinateSystem(ICoordinateSystem coordinateSystem) } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing the type enumeration + /// and preferring the data-set representation of the origin when + /// present. + /// public ICoordinateSystem ToCoordinateSystem() { var coordinateSystem = new CoordinateSystem(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonCoordinateSystems.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonCoordinateSystems.cs index e3c162eb6..28ae88bd8 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonCoordinateSystems.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonCoordinateSystems.cs @@ -7,14 +7,29 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a typed container of + /// items, keyed by the singular + /// cppagent element name CoordinateSystem. + /// public class JsonCoordinateSystems { + /// + /// The coordinate systems in the container. + /// [JsonPropertyName("CoordinateSystem")] public IEnumerable CoordinateSystems { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCoordinateSystems() { } + /// + /// Initializes the container from a coordinate-system + /// sequence. + /// public JsonCoordinateSystems(IEnumerable coordinateSystems) { if (!coordinateSystems.IsNullOrEmpty()) @@ -28,6 +43,10 @@ public JsonCoordinateSystems(IEnumerable coordinateSystems) } + /// + /// Flattens the container back into a uniform + /// sequence. + /// public IEnumerable ToCoordinateSystems() { var coordinateSystems = new List(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDataItem.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDataItem.cs index ba9a038a8..1e9f29820 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDataItem.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDataItem.cs @@ -7,78 +7,179 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for an MTConnect DataItem in the + /// cppagent-compatible JSON shape. Mirrors a DataItem element so the JSON + /// serializer can read and write the on-the-wire shape, then converts to + /// and from the strongly-typed model. Properties + /// that match the MTConnect default are omitted on write and restored on + /// read. + /// public class JsonDataItem { + /// + /// The category classifying the data item as SAMPLE, EVENT, or + /// CONDITION. + /// [JsonPropertyName("category")] public string DataItemCategory { get; set; } + /// + /// The unique id of the data item within the device. + /// [JsonPropertyName("id")] public string Id { get; set; } + /// + /// The MTConnect type identifying the kind of data reported. + /// [JsonPropertyName("type")] - public string Type { get; set; } + public string Type { get; set; } + /// + /// The coordinate system the reported values are expressed in. Omitted + /// when the default MACHINE coordinate system applies. + /// [JsonPropertyName("coordinateSystem")] public string CoordinateSystem { get; set; } + /// + /// Reference to the id of a CoordinateSystem the values are + /// expressed relative to. + /// [JsonPropertyName("coordinateSystemIdRef")] public string CoordinateSystemIdRef { get; set; } + /// + /// The optional human-readable name of the data item. Omitted + /// from the JSON output when not set. + /// [JsonPropertyName("name")] [JsonIgnore(Condition = JsonIgnoreCondition.WhenWritingNull)] public string Name { get; set; } + /// + /// The power-of-ten scaling applied to native values before conversion + /// to the reported units. Omitted when zero. + /// [JsonPropertyName("nativeScale")] public double? NativeScale { get; set; } + /// + /// The units the data source natively reports values in, prior to + /// conversion to . + /// [JsonPropertyName("nativeUnits")] public string NativeUnits { get; set; } + /// + /// The optional subType further qualifying . + /// [JsonPropertyName("subType")] public string SubType { get; set; } + /// + /// The statistical operation (for example AVERAGE or MAXIMUM) applied + /// to the reported values. + /// [JsonPropertyName("statistic")] public string Statistic { get; set; } + /// + /// The engineering units the reported values are expressed in. + /// [JsonPropertyName("units")] public string Units { get; set; } + /// + /// The rate, in samples per second, at which the data source samples + /// values for a TIME_SERIES representation. Omitted when zero. + /// [JsonPropertyName("sampleRate")] public double? SampleRate { get; set; } + /// + /// Indicates whether the reported values are discrete events rather + /// than a continuously varying signal. Omitted when false. + /// [JsonPropertyName("discrete")] public bool? Discrete { get; set; } + /// + /// The data item's representation (for example DATA_SET, TABLE, + /// or TIME_SERIES). Omitted when the default VALUE representation + /// applies. + /// [JsonPropertyName("representation")] public string Representation { get; set; } + /// + /// The number of significant digits in the reported values. Omitted + /// when zero. + /// [JsonPropertyName("significantDigits")] public int? SignificantDigits { get; set; } + /// + /// The source (component, composition, or data item) the data item's + /// values originate from. + /// [JsonPropertyName("Source")] public JsonSource Source { get; set; } + /// + /// The constraints (limits or enumerated values) bounding the reported + /// values. + /// [JsonPropertyName("Constraints")] public JsonConstraints Constraints { get; set; } + /// + /// The filters (minimum delta or period) applied to the reported + /// values. + /// [JsonPropertyName("Filters")] public JsonFilters Filters { get; set; } + /// + /// The value reported for the data item before its first observation. + /// [JsonPropertyName("initialValue")] public string InitialValue { get; set; } + /// + /// The condition under which a resettable data item's accumulated + /// value is reset. + /// [JsonPropertyName("resetTrigger")] public string ResetTrigger { get; set; } + /// + /// The definition describing the structure of cell or entry values for + /// a DATA_SET or TABLE representation. + /// [JsonPropertyName("Definition")] public JsonDataItemDefinition Definition { get; set; } + /// + /// The relationships from the data item to other data items and + /// specifications, grouped by relationship kind. + /// [JsonPropertyName("Relationships")] public JsonRelationshipContainer Relationships { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDataItem() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , omitting properties whose values equal the + /// MTConnect default and grouping relationships by their concrete + /// relationship interface. + /// public JsonDataItem(IDataItem dataItem) { if (dataItem != null) @@ -138,8 +239,17 @@ public JsonDataItem(IDataItem dataItem) } + /// + /// Returns the JSON representation of this surrogate. + /// public override string ToString() => JsonFunctions.Convert(this); + /// + /// Converts this surrogate to a strongly-typed , + /// instantiating the concrete data item subtype for , + /// restoring omitted properties to their MTConnect defaults, and + /// flattening the grouped relationships back into a single collection. + /// public DataItem ToDataItem() { var dataItem = DataItem.Create(Type); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDataItemDefinition.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDataItemDefinition.cs index a566b0768..c6ed7595c 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDataItemDefinition.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDataItemDefinition.cs @@ -5,20 +5,44 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a DataItemDefinition in + /// the cppagent-compatible shape. Carries the per-entry and + /// per-cell schema for DATA_SET and TABLE data items, plus the + /// free-form description text. Converts to and from the + /// strongly-typed model. + /// public class JsonDataItemDefinition { + /// + /// Free-form description of the data item. + /// [JsonPropertyName("Description")] public string Description { get; set; } + /// + /// Per-entry schema for a DATA_SET or TABLE data item. + /// [JsonPropertyName("EntryDefinitions")] public JsonEntryDefinitions EntryDefinitions { get; set; } + /// + /// Per-cell schema for a TABLE data item. + /// [JsonPropertyName("CellDefinitions")] public JsonCellDefinitions CellDefinitions { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDataItemDefinition() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , suppressing the entry and + /// cell containers when their source collections are empty. + /// public JsonDataItemDefinition(IDataItemDefinition definition) { if (definition != null) @@ -45,6 +69,10 @@ public JsonDataItemDefinition(IDataItemDefinition definition) + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IDataItemDefinition ToDefinition() { var definition = new DataItemDefinition(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDataItemReference.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDataItemReference.cs index f4c21c284..ff229d77a 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDataItemReference.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDataItemReference.cs @@ -6,17 +6,35 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a DataItemReference in + /// the cppagent-compatible shape, pointing at a data item by its + /// id with an optional display name. + /// public class JsonDataItemReference { + /// + /// Reference to the id of the target data item. + /// [JsonPropertyName("idRef")] public string IdRef { get; set; } + /// + /// Optional display name for the reference. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDataItemReference() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonDataItemReference(IDataItemReference reference) { if (reference != null) @@ -27,6 +45,10 @@ public JsonDataItemReference(IDataItemReference reference) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public virtual IReference ToReference() { var reference = new DataItemReference(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDataItems.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDataItems.cs index 0636f8170..e6d582e2f 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDataItems.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDataItems.cs @@ -6,14 +6,28 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a typed container of + /// items, keyed by the singular cppagent + /// element name DataItem. + /// public class JsonDataItems { + /// + /// The data items in the container. + /// [JsonPropertyName("DataItem")] public IEnumerable DataItems { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDataItems() { } + /// + /// Initializes the container from a data-item sequence. + /// public JsonDataItems(IEnumerable dataItems) { if (!dataItems.IsNullOrEmpty()) @@ -27,6 +41,10 @@ public JsonDataItems(IEnumerable dataItems) } + /// + /// Flattens the container back into a uniform + /// sequence. + /// public IEnumerable ToDataItems() { var dataItems = new List(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDescription.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDescription.cs index d7fb87cf1..e4f047d50 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDescription.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDescription.cs @@ -5,26 +5,56 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a Description in the + /// cppagent-compatible shape. Carries the descriptive metadata + /// (manufacturer, model, serial number, station) plus the free-form + /// description text. Converts to and from the strongly-typed + /// model. + /// public class JsonDescription { + /// + /// The manufacturer of the component or device. + /// [JsonPropertyName("manufacturer")] public string Manufacturer { get; set; } + /// + /// The model designation of the component or device. + /// [JsonPropertyName("model")] public string Model { get; set; } + /// + /// The serial number of the component or device. + /// [JsonPropertyName("serialNumber")] public string SerialNumber { get; set; } + /// + /// The station identifier of the component within a multi-station + /// device. + /// [JsonPropertyName("station")] public string Station { get; set; } + /// + /// The free-form description text. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDescription() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonDescription(IDescription description) { if (description != null) @@ -38,6 +68,10 @@ public JsonDescription(IDescription description) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IDescription ToDescription() { var description = new Description(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDevice.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDevice.cs index 8203912f1..2f2d544ba 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDevice.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDevice.cs @@ -7,59 +7,128 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for an MTConnect Device in the + /// cppagent-compatible JSON shape. Mirrors the on-the-wire layout, which + /// wraps child collections in counted container objects, then converts to + /// and from the strongly-typed model. + /// public class JsonDevice { + /// + /// The unique id of the device. + /// [JsonPropertyName("id")] public string Id { get; set; } + /// + /// The human-readable name of the device. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The universally unique identifier of the device. + /// [JsonPropertyName("uuid")] public string Uuid { get; set; } + /// + /// The hash uniquely identifying the device's current configuration. + /// [JsonPropertyName("hash")] public string Hash { get; set; } + /// + /// The ISO 841 classification of the device. + /// [JsonPropertyName("iso841Class")] public string Iso841Class { get; set; } + /// + /// The name the device is known by in the native data source, when it + /// differs from . + /// [JsonPropertyName("nativeName")] public string NativeName { get; set; } + /// + /// The interval, in milliseconds, between samples of the device's + /// data, when reported. + /// [JsonPropertyName("sampleInterval")] public double? SampleInterval { get; set; } + /// + /// The rate, in samples per second, at which the device's data is + /// sampled, when reported. + /// [JsonPropertyName("sampleRate")] public double? SampleRate { get; set; } + /// + /// Reference to the id of a CoordinateSystem the device's + /// values are expressed relative to. + /// [JsonPropertyName("coordinateSystemIdRef")] public string CoordinateSystemIdRef { get; set; } + /// + /// The MTConnect schema version the device definition conforms to. + /// [JsonPropertyName("mtconnectVersion")] public string MTConnectVersion { get; set; } + /// + /// The descriptive metadata (manufacturer, model, serial number) for + /// the device. + /// [JsonPropertyName("Description")] public JsonDescription Description { get; set; } + /// + /// The configuration (coordinate systems, motion, relationships, + /// specifications) of the device. + /// [JsonPropertyName("Configuration")] public JsonConfiguration Configuration { get; set; } + /// + /// The data items reported directly by the device, wrapped in a + /// counted container. + /// [JsonPropertyName("DataItems")] public JsonDataItems DataItems { get; set; } + /// + /// The compositions of the device, wrapped in a counted container. + /// [JsonPropertyName("Compositions")] public JsonCompositions Compositions { get; set; } + /// + /// The child components of the device, wrapped in a counted container. + /// [JsonPropertyName("Components")] public JsonComponents Components { get; set; } + /// + /// The references from the device to other components and data items. + /// [JsonPropertyName("References")] public JsonReferenceContainer References { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDevice() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , wrapping the child collections in their + /// counted container types. + /// public JsonDevice(IDevice device) { if (device != null) @@ -103,10 +172,28 @@ public JsonDevice(IDevice device) } + /// + /// Returns the JSON representation of this surrogate, optionally + /// indented for readability. + /// public string ToString(bool indent = false) => JsonFunctions.Convert(this, indented: indent); + + /// + /// Returns the UTF-8 encoded JSON bytes of this surrogate, optionally + /// indented for readability. + /// public byte[] ToBytes(bool indent = false) => JsonFunctions.ConvertBytes(this, indented: indent); + + /// + /// Returns a stream over the JSON representation of this surrogate, + /// optionally indented for readability. + /// public Stream ToStream(bool indent = false) => JsonFunctions.ConvertStream(this, indented: indent); + /// + /// Converts this surrogate to a strongly-typed , + /// unwrapping each child container and parsing the MTConnect version. + /// public Device ToDevice() { var device = new Device(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDeviceContainer.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDeviceContainer.cs index 44670b7b6..aadb8099a 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDeviceContainer.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDeviceContainer.cs @@ -5,24 +5,46 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate that wraps a single device of + /// either kind (Agent or Device) in the cppagent-compatible shape. + /// Mirrors but for the entity-level MQTT + /// payload where each retained topic carries exactly one device. + /// public class JsonDeviceContainer { + /// + /// The wrapped agent-self device, when the container holds + /// one. + /// [JsonPropertyName("Agent")] public JsonDevice Agent { get; set; } + /// + /// The wrapped real-equipment device, when the container holds + /// one. + /// [JsonPropertyName("Device")] public JsonDevice Device { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDeviceContainer() { } + /// + /// Initializes the container from a single + /// , dispatching to the appropriate typed + /// property by the device's TypeId. + /// public JsonDeviceContainer(IDevice device) { if (device != null) { switch (device.Type) { - case Devices.Agent.TypeId: + case Devices.Agent.TypeId: Agent = new JsonDevice(device); break; @@ -34,6 +56,10 @@ public JsonDeviceContainer(IDevice device) } + /// + /// Returns the contained device by inspecting the populated + /// property, returning null when neither is populated. + /// public IDevice ToDevice() { if (Agent != null) diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDevices.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDevices.cs index b524c96b3..ce313051f 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDevices.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDevices.cs @@ -6,17 +6,40 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate that partitions a probe document's + /// devices into the agent-self device and the real-equipment + /// devices into separate typed lists. The cppagent shape keys each + /// list by element name (Agent, Device), so this + /// container exposes one list per kind and only the lists with + /// content are populated. + /// public class JsonDevices { + /// + /// Devices of type Agent (the agent-self device). + /// [JsonPropertyName("Agent")] public IEnumerable Agents { get; set; } + /// + /// Devices of any non-Agent type (real equipment devices). + /// [JsonPropertyName("Device")] public IEnumerable Devices { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDevices() { } + /// + /// Initializes the container from a Devices response document, + /// routing the agent-self device into and + /// every other device into ; either list + /// is suppressed when its partition is empty. + /// public JsonDevices(IDevicesResponseDocument document) { if (document != null) @@ -39,6 +62,10 @@ public JsonDevices(IDevicesResponseDocument document) } + /// + /// Flattens the typed device lists back into a uniform + /// collection in Agent-then-Device order. + /// public IEnumerable ToDevices() { var devices = new List(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDevicesHeader.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDevicesHeader.cs index 208ad1332..e29edf8f2 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDevicesHeader.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDevicesHeader.cs @@ -7,11 +7,22 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for the Header of an + /// MTConnectDevices document in the cppagent-compatible shape. + /// public class JsonDevicesHeader { + /// + /// The instance identifier of the agent, which changes whenever the + /// agent's buffer is cleared. + /// [JsonPropertyName("instanceId")] public ulong InstanceId { get; set; } + /// + /// The agent's version. + /// [JsonPropertyName("version")] public string Version { get; set; } @@ -26,21 +37,40 @@ public class JsonDevicesHeader [JsonPropertyName("schemaVersion")] public string SchemaVersion { get; set; } + /// + /// The identifier of the agent that produced the document. + /// [JsonPropertyName("sender")] public string Sender { get; set; } + /// + /// The maximum number of observations the agent's buffer can hold. + /// [JsonPropertyName("bufferSize")] public ulong BufferSize { get; set; } + /// + /// The maximum number of assets the agent can store. + /// [JsonPropertyName("assetBufferSize")] public ulong AssetBufferSize { get; set; } + /// + /// The number of assets currently stored by the agent. + /// [JsonPropertyName("assetCount")] public ulong AssetCount { get; set; } + /// + /// The timestamp of the most recent change to the device model. + /// [JsonPropertyName("deviceModelChangeTime")] public string DeviceModelChangeTime { get; set; } + /// + /// Whether the document was produced for testing rather than + /// production use. + /// [JsonPropertyName("testIndicator")] public bool TestIndicator { get; set; } @@ -51,12 +81,22 @@ public class JsonDevicesHeader [JsonPropertyName("validation")] public bool Validation { get; set; } + /// + /// The time the document was created. + /// [JsonPropertyName("creationTime")] public DateTime CreationTime { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDevicesHeader() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonDevicesHeader(IMTConnectDevicesHeader header) { if (header != null) @@ -76,6 +116,10 @@ public JsonDevicesHeader(IMTConnectDevicesHeader header) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IMTConnectDevicesHeader ToDevicesHeader() { var header = new MTConnectDevicesHeader(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDevicesResponseDocument.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDevicesResponseDocument.cs index a4ae495ad..3224c5a10 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDevicesResponseDocument.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonDevicesResponseDocument.cs @@ -5,14 +5,30 @@ namespace MTConnect.Devices.Json { + /// + /// Outer JSON envelope for a Probe/Devices response document in + /// the cppagent-compatible shape, with the actual content wrapped + /// in a single MTConnectDevices property to mirror the XML + /// root element name. + /// public class JsonDevicesResponseDocument { + /// + /// The wrapped devices document. + /// [JsonPropertyName("MTConnectDevices")] public JsonMTConnectDevices MTConnectDevices { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDevicesResponseDocument() { } + /// + /// Initializes the envelope from a strongly-typed devices + /// document. + /// public JsonDevicesResponseDocument(IDevicesResponseDocument document) { if (document != null) @@ -22,6 +38,11 @@ public JsonDevicesResponseDocument(IDevicesResponseDocument document) } + /// + /// Unwraps the envelope and converts it to a strongly-typed + /// devices document, returning null when the envelope is + /// empty. + /// public IDevicesResponseDocument ToDocument() { if (MTConnectDevices != null) diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonEntryDefinition.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonEntryDefinition.cs index 59c28a374..838c7189b 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonEntryDefinition.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonEntryDefinition.cs @@ -7,32 +7,71 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for an EntryDefinition in the + /// cppagent-compatible shape. Describes a single named entry within a + /// DATA_SET or TABLE data-item definition, including its expected + /// units, type/sub-type, and (for tables) the per-cell schema. + /// Converts to and from the strongly-typed + /// model. + /// public class JsonEntryDefinition { + /// + /// The dictionary key the entry is keyed on at runtime. + /// [JsonPropertyName("key")] public string Key { get; set; } + /// + /// The semantic type of the key (for example a controlled + /// vocabulary identifier). + /// [JsonPropertyName("keyType")] public string KeyType { get; set; } + /// + /// Engineering units of the entry's value. + /// [JsonPropertyName("units")] public string Units { get; set; } + /// + /// The MTConnect type of the entry's value. + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// Optional sub-type qualifier of the entry's value. + /// [JsonPropertyName("subType")] public string SubType { get; set; } + /// + /// Free-form description of the entry. + /// [JsonPropertyName("Description")] public string Description { get; set; } + /// + /// Per-cell schema, populated only when the parent definition + /// describes a TABLE data item. + /// [JsonPropertyName("CellDefinitions")] public JsonCellDefinitions CellDefinitions { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonEntryDefinition() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , suppressing the cell-definition + /// container when the source has none. + /// public JsonEntryDefinition(IEntryDefinition definition) { if (definition != null) @@ -58,6 +97,10 @@ public JsonEntryDefinition(IEntryDefinition definition) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IEntryDefinition ToEntryDefinition() { var definition = new EntryDefinition(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonEntryDefinitions.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonEntryDefinitions.cs index b02422b10..9a77b7bba 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonEntryDefinitions.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonEntryDefinitions.cs @@ -6,14 +6,29 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a typed container of + /// items, keyed by the singular + /// cppagent element name EntryDefinition. + /// public class JsonEntryDefinitions { + /// + /// The entry definitions in the container. + /// [JsonPropertyName("EntryDefinition")] public IEnumerable EntryDefinitions { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonEntryDefinitions() { } + /// + /// Initializes the container from an entry-definition + /// sequence. + /// public JsonEntryDefinitions(IEnumerable entryDefinitions) { if (!entryDefinitions.IsNullOrEmpty()) @@ -27,6 +42,10 @@ public JsonEntryDefinitions(IEnumerable entryDefinitions) } + /// + /// Flattens the container back into a uniform + /// sequence. + /// public IEnumerable ToEntryDefinitions() { var entryDefinitions = new List(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonFilter.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonFilter.cs index eee552983..22ff451d5 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonFilter.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonFilter.cs @@ -5,17 +5,40 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a data-item Filter in + /// the cppagent-compatible shape. Describes a change-detection + /// filter (typically MINIMUM_DELTA or PERIOD) applied + /// to the data item. Converts to and from the strongly-typed + /// model. + /// public class JsonFilter { + /// + /// The kind of filter applied (for example MINIMUM_DELTA, + /// PERIOD). + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The filter threshold value in the data item's engineering + /// units. + /// [JsonPropertyName("value")] public double Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonFilter() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , serializing the filter type to its + /// enumeration name. + /// public JsonFilter(IFilter filter) { if (filter != null) @@ -26,6 +49,11 @@ public JsonFilter(IFilter filter) } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing the type enumeration from its + /// serialized form. + /// public IFilter ToFilter() { var filter = new Filter(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonFilters.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonFilters.cs index 6d49b2b51..e35b48ee6 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonFilters.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonFilters.cs @@ -6,14 +6,28 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a typed container of + /// items, keyed by the singular cppagent + /// element name Filter. + /// public class JsonFilters { + /// + /// The data-item filters in the container. + /// [JsonPropertyName("Filter")] public IEnumerable Filters { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonFilters() { } + /// + /// Initializes the container from a filter sequence. + /// public JsonFilters(IEnumerable filters) { if (!filters.IsNullOrEmpty()) @@ -27,6 +41,10 @@ public JsonFilters(IEnumerable filters) } + /// + /// Flattens the container back into a uniform + /// sequence. + /// public IEnumerable ToFilters() { var filters = new List(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonMTConnectDevices.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonMTConnectDevices.cs index 8de189687..e518d2435 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonMTConnectDevices.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonMTConnectDevices.cs @@ -5,8 +5,20 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for the top-level + /// MTConnectDevices document in the cppagent-compatible + /// shape. Sits inside a + /// envelope and carries the wire-format version, the agent header, + /// and the document's devices. Converts to and from the + /// strongly-typed model. + /// public class JsonMTConnectDevices { + /// + /// The wire-format version of the cppagent JSON envelope + /// emitted by this producer. + /// [JsonPropertyName("jsonVersion")] public int JsonVersion { get; set; } @@ -21,9 +33,17 @@ public class JsonMTConnectDevices [JsonPropertyName("schemaVersion")] public string SchemaVersion { get; set; } + /// + /// The MTConnect Agent header (instance id, creation time, + /// version, etc.). + /// [JsonPropertyName("Header")] public JsonDevicesHeader Header { get; set; } + /// + /// The keyed device container holding every device in the + /// document. + /// [JsonPropertyName("Devices")] public JsonDevices Devices { get; set; } @@ -31,11 +51,21 @@ public class JsonMTConnectDevices //public IEnumerable Interfaces { get; set; } + /// + /// Initializes a fresh container, defaulting + /// to the current emitter version. + /// public JsonMTConnectDevices() { JsonVersion = 2; } + /// + /// Initializes the container from a strongly-typed + /// , capturing the agent + /// schema version (note that this is the agent's standard + /// release, distinct from above). + /// public JsonMTConnectDevices(IDevicesResponseDocument document) { JsonVersion = 2; @@ -53,6 +83,10 @@ public JsonMTConnectDevices(IDevicesResponseDocument document) } + /// + /// Converts the container to a strongly-typed + /// . + /// public DevicesResponseDocument ToDocument() { var document = new DevicesResponseDocument(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonMotion.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonMotion.cs index 3b71c7839..afb4cf2e3 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonMotion.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonMotion.cs @@ -7,44 +7,96 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a Configuration Motion in the + /// cppagent-compatible shape. Inline coordinates are emitted as JSON + /// arrays rather than space-separated strings. Converts to and from the + /// strongly-typed model. + /// public class JsonMotion { + /// + /// The unique id of the motion definition. + /// [JsonPropertyName("id")] public string Id { get; set; } + /// + /// Reference to the id of the parent motion this motion is + /// defined relative to. + /// [JsonPropertyName("parentIdRef")] public string ParentIdRef { get; set; } + /// + /// Reference to the id of the coordinate system the motion is + /// expressed in. + /// [JsonPropertyName("coordinateSystemIdRef")] public string CoordinateSystemIdRef { get; set; } + /// + /// The kind of motion (for example REVOLUTE or PRISMATIC). + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// How the motion is actuated. + /// [JsonPropertyName("actuation")] public string Actuation { get; set; } + /// + /// The free-form description of the motion. + /// [JsonPropertyName("Description")] public string Description { get; set; } + /// + /// The origin of the motion as a numeric JSON array, when expressed + /// inline. + /// [JsonPropertyName("Origin")] public IEnumerable Origin { get; set; } + /// + /// The origin of the motion as a data set, when expressed by + /// reference. + /// [JsonPropertyName("OriginDataSet")] public JsonOriginDataSet OriginDataSet { get; set; } + /// + /// The translation and rotation relating the motion to its parent. + /// [JsonPropertyName("Transformation")] public JsonTransformation Transformation { get; set; } + /// + /// The axis of the motion as a numeric JSON array, when expressed + /// inline. + /// [JsonPropertyName("Axis")] public IEnumerable Axis { get; set; } + /// + /// The axis of the motion as a data set, when expressed by reference. + /// [JsonPropertyName("AxisDataSet")] public JsonAxisDataSet AxisDataSet { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonMotion() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , selecting the inline numeric-array or + /// data-set representation for the origin and axis. + /// public JsonMotion(IMotion motion) { if (motion != null) @@ -68,6 +120,11 @@ public JsonMotion(IMotion motion) } + /// + /// Converts this surrogate to a strongly-typed , + /// parsing the type and actuation enumerations and preferring the + /// data-set representation of the origin and axis when present. + /// public IMotion ToMotion() { var motion = new Motion(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonOriginDataSet.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonOriginDataSet.cs index 5ba143d30..09b1033b5 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonOriginDataSet.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonOriginDataSet.cs @@ -12,20 +12,45 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a Configuration Origin + /// expressed as a data set in the cppagent-compatible shape. The + /// flat {"X": v, "Y": v, "Z": v} PascalCase object encoding + /// matches the cppagent v2 DataSet convention; the values are + /// serialized as strings to round-trip equipment-native formatting. + /// Converts to and from the strongly-typed + /// model. + /// public class JsonOriginDataSet { + /// + /// Component of the origin along the X direction. + /// [JsonPropertyName("X")] public string X { get; set; } + /// + /// Component of the origin along the Y direction. + /// [JsonPropertyName("Y")] public string Y { get; set; } + /// + /// Component of the origin along the Z direction. + /// [JsonPropertyName("Z")] public string Z { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonOriginDataSet() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonOriginDataSet(IOriginDataSet dataSet) { if (dataSet != null) @@ -37,6 +62,10 @@ public JsonOriginDataSet(IOriginDataSet dataSet) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IOriginDataSet ToOriginDataSet() { var dataSet = new OriginDataSet(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonProcessSpecification.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonProcessSpecification.cs index 206577261..8b98520f7 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonProcessSpecification.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonProcessSpecification.cs @@ -6,20 +6,46 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a + /// ProcessSpecification in the cppagent-compatible shape, + /// extending the shared + /// envelope with separate sub-objects for control, specification, + /// and alarm limits. Converts to and from the strongly-typed + /// model. + /// public class JsonProcessSpecification : JsonAbstractSpecification { + /// + /// Control limits that the process should be operated within. + /// [JsonPropertyName("controlLimits")] public JsonControlLimits ControlLimits { get; set; } + /// + /// Specification limits the process must remain inside to be + /// conforming. + /// [JsonPropertyName("specificationLimits")] public JsonSpecificationLimits SpecificationLimits { get; set; } + /// + /// Alarm limits whose breach should raise an alarm condition. + /// [JsonPropertyName("alarmLimits")] public JsonAlarmLimits AlarmLimits { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonProcessSpecification() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , suppressing any limit + /// sub-object when the source has none. + /// public JsonProcessSpecification(IProcessSpecification specification) : base(specification) { if (specification != null) @@ -31,6 +57,12 @@ public JsonProcessSpecification(IProcessSpecification specification) : base(spec } + /// + /// Converts this surrogate to a strongly-typed + /// , applying the limit + /// sub-objects in addition to the shared attributes parsed from + /// the base. + /// public override ISpecification ToSpecification() { var specification = new ProcessSpecification(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonReferenceContainer.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonReferenceContainer.cs index 85c7d620c..57a4dd062 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonReferenceContainer.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonReferenceContainer.cs @@ -7,17 +7,38 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate that partitions a component's + /// references by kind into typed sibling lists, keyed by element + /// name (ComponentReference, DataItemReference) per + /// the cppagent shape. Converts to and from a uniform + /// collection. + /// public class JsonReferenceContainer { + /// + /// References to other components. + /// [JsonPropertyName("ComponentReference")] public List ComponentReferences { get; set; } + /// + /// References to data items. + /// [JsonPropertyName("DataItemReference")] public List DataItemReferences { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonReferenceContainer() { } + /// + /// Initializes the container from a uniform reference + /// collection, partitioning each reference into the typed list + /// matching its concrete interface. + /// public JsonReferenceContainer(IEnumerable references) { if (!references.IsNullOrEmpty()) @@ -42,6 +63,10 @@ public JsonReferenceContainer(IEnumerable references) } } + /// + /// Flattens the typed reference lists back into a uniform + /// collection. + /// public IEnumerable ToReferences() { var references = new List(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonRelationship.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonRelationship.cs index 91ad838e9..d30a69bb2 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonRelationship.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonRelationship.cs @@ -6,44 +6,95 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a Configuration Relationship in + /// the cppagent-compatible shape. A single surrogate shape carries every + /// relationship kind; only the properties relevant to the originating + /// kind are populated, and the corresponding ToXxxRelationship + /// method reconstructs the concrete strongly-typed relationship. + /// public class JsonRelationship { + /// + /// The unique id of the relationship. + /// [JsonPropertyName("id")] public string Id { get; set; } + /// + /// The human-readable name of the relationship. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The relationship type, interpreted as the relevant + /// relationship-type enumeration for the originating kind. + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The criticality (CRITICAL or NONCRITICAL) of the relationship. + /// [JsonPropertyName("criticality")] public string Criticality { get; set; } + /// + /// Reference to the id of the related component, data item, or + /// specification. + /// [JsonPropertyName("idRef")] public string IdRef { get; set; } + /// + /// Reference to the UUID of the related device, for a device + /// relationship. + /// [JsonPropertyName("deviceUuidRef")] public string DeviceUuidRef { get; set; } + /// + /// Reference to the assetId of the related asset, for an asset + /// relationship. + /// [JsonPropertyName("assetIdRef")] public string AssetIdRef { get; set; } + /// + /// The type of the related asset, for an asset relationship. + /// [JsonPropertyName("assetType")] public string AssetType { get; set; } + /// + /// The role the related device plays, for a device relationship. + /// [JsonPropertyName("role")] public string Role { get; set; } + /// + /// The hyperlink reference to the related entity. + /// [JsonPropertyName("href")] public string Href { get; set; } + /// + /// The XLink type of the reference. + /// [JsonPropertyName("xLinkType")] public string XLinkType { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonRelationship() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonRelationship(IAssetRelationship relationship) { if (relationship != null) @@ -57,6 +108,10 @@ public JsonRelationship(IAssetRelationship relationship) } } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonRelationship(IComponentRelationship relationship) { if (relationship != null) @@ -69,6 +124,10 @@ public JsonRelationship(IComponentRelationship relationship) } } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonRelationship(IDataItemRelationship relationship) { if (relationship != null) @@ -79,6 +138,10 @@ public JsonRelationship(IDataItemRelationship relationship) } } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonRelationship(IDeviceRelationship relationship) { if (relationship != null) @@ -94,6 +157,10 @@ public JsonRelationship(IDeviceRelationship relationship) } } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonRelationship(ISpecificationRelationship relationship) { if (relationship != null) @@ -105,6 +172,10 @@ public JsonRelationship(ISpecificationRelationship relationship) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public virtual IAssetRelationship ToAssetRelationship() { var relationship = new AssetRelationship(); @@ -118,6 +189,10 @@ public virtual IAssetRelationship ToAssetRelationship() return relationship; } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public virtual IComponentRelationship ToComponentRelationship() { var relationship = new ComponentRelationship(); @@ -129,6 +204,10 @@ public virtual IComponentRelationship ToComponentRelationship() return relationship; } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public virtual IDataItemRelationship ToDataItemRelationship() { var relationship = new DataItemRelationship(); @@ -138,6 +217,10 @@ public virtual IDataItemRelationship ToDataItemRelationship() return relationship; } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public virtual IDeviceRelationship ToDeviceRelationship() { var relationship = new DeviceRelationship(); @@ -148,6 +231,10 @@ public virtual IDeviceRelationship ToDeviceRelationship() return relationship; } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public virtual ISpecificationRelationship ToSpecificationRelationship() { var relationship = new SpecificationRelationship(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonRelationshipContainer.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonRelationshipContainer.cs index f5fb6159f..9adfea1da 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonRelationshipContainer.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonRelationshipContainer.cs @@ -6,20 +6,44 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate that partitions a component's + /// configuration relationships by kind into typed sibling lists. + /// The cppagent shape keys each list by the relationship element + /// name (AssetRelationship, DataItemRelationship, + /// ComponentRelationship, DeviceRelationship, + /// SpecificationRelationship), so this container exposes one + /// list per kind and only the lists with content are populated. + /// public class JsonRelationshipContainer { + /// + /// Relationships to assets. + /// [JsonPropertyName("AssetRelationship")] public List AssetRelationships { get; set; } + /// + /// Relationships to data items. + /// [JsonPropertyName("DataItemRelationship")] public List DataItemRelationships { get; set; } + /// + /// Relationships to other components. + /// [JsonPropertyName("ComponentRelationship")] public List ComponentRelationships { get; set; } + /// + /// Relationships to other devices. + /// [JsonPropertyName("DeviceRelationship")] public List DeviceRelationships { get; set; } + /// + /// Relationships to specifications. + /// [JsonPropertyName("SpecificationRelationship")] public List SpecificationRelationships { get; set; } } diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonRotationDataSet.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonRotationDataSet.cs index b5e170eda..584dd6d46 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonRotationDataSet.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonRotationDataSet.cs @@ -12,20 +12,45 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a Configuration Rotation + /// expressed as a data set in the cppagent-compatible shape. The + /// flat {"A": v, "B": v, "C": v} PascalCase object encoding + /// matches the cppagent v2 DataSet convention; the angular values + /// are serialized as strings to round-trip equipment-native + /// formatting. Converts to and from the strongly-typed + /// model. + /// public class JsonRotationDataSet { + /// + /// Rotation around the A axis. + /// [JsonPropertyName("A")] public string A { get; set; } + /// + /// Rotation around the B axis. + /// [JsonPropertyName("B")] public string B { get; set; } + /// + /// Rotation around the C axis. + /// [JsonPropertyName("C")] public string C { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonRotationDataSet() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonRotationDataSet(IRotationDataSet dataSet) { if (dataSet != null) @@ -37,6 +62,10 @@ public JsonRotationDataSet(IRotationDataSet dataSet) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IRotationDataSet ToRotationDataSet() { var dataSet = new RotationDataSet(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonScaleDataSet.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonScaleDataSet.cs index 7e3cf99c5..13e39fc85 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonScaleDataSet.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonScaleDataSet.cs @@ -12,20 +12,44 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a Configuration + /// SolidModel.Scale expressed as a data set in the + /// cppagent-compatible shape. The flat + /// {"X": v, "Y": v, "Z": v} PascalCase object encoding + /// matches the cppagent v2 DataSet convention. Converts to and from + /// the strongly-typed model. + /// public class JsonScaleDataSet { + /// + /// Scale factor along the X axis. + /// [JsonPropertyName("X")] public double X { get; set; } + /// + /// Scale factor along the Y axis. + /// [JsonPropertyName("Y")] public double Y { get; set; } + /// + /// Scale factor along the Z axis. + /// [JsonPropertyName("Z")] public double Z { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonScaleDataSet() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonScaleDataSet(IScaleDataSet dataSet) { if (dataSet != null) @@ -37,6 +61,10 @@ public JsonScaleDataSet(IScaleDataSet dataSet) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IScaleDataSet ToScaleDataSet() { var dataSet = new ScaleDataSet(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSensorConfiguration.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSensorConfiguration.cs index 582db943c..49b335c59 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSensorConfiguration.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSensorConfiguration.cs @@ -8,26 +8,58 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a + /// SensorConfiguration in the cppagent-compatible shape. + /// Carries the sensor firmware revision and calibration history plus + /// a typed container of channel definitions. Converts to and from + /// the strongly-typed model. + /// public class JsonSensorConfiguration { + /// + /// The firmware version of the sensor. + /// [JsonPropertyName("FirmwareVersion")] public string FirmwareVersion { get; set; } + /// + /// Date of the last sensor-level calibration. + /// [JsonPropertyName("CalibrationDate")] public DateTime? CalibrationDate { get; set; } + /// + /// Date of the next scheduled sensor-level calibration. + /// [JsonPropertyName("NextCalibrationDate")] public DateTime? NextCalibrationDate { get; set; } + /// + /// Initials of the technician who performed the most recent + /// sensor-level calibration. + /// [JsonPropertyName("CalibrationInitials")] public string CalibrationInitials { get; set; } + /// + /// Per-channel calibration data carried inside a typed + /// channel container. + /// [JsonPropertyName("Channels")] public JsonChannels Channels { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonSensorConfiguration() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , suppressing the channel + /// container when the source has no channels. + /// public JsonSensorConfiguration(ISensorConfiguration configuration) { if (configuration != null) @@ -46,6 +78,11 @@ public JsonSensorConfiguration(ISensorConfiguration configuration) } + /// + /// Converts this surrogate to a strongly-typed + /// , flattening the typed + /// channel container back into a uniform channel list. + /// public ISensorConfiguration ToSensorConfiguration() { var sensorConfiguration = new SensorConfiguration(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSolidModel.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSolidModel.cs index 91c9a5685..6c521a4ed 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSolidModel.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSolidModel.cs @@ -7,38 +7,86 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a Configuration SolidModel in + /// the cppagent-compatible shape. References to an external 3D model file + /// are emitted as scalar properties, while the inline scale is emitted as + /// a numeric JSON array rather than a space-separated string. Converts to + /// and from the strongly-typed model. + /// public class JsonSolidModel { + /// + /// The unique id of the solid model. + /// [JsonPropertyName("id")] public string Id { get; set; } + /// + /// Reference to the id of another SolidModel this one + /// derives from. + /// [JsonPropertyName("solidModelIdRef")] public string SolidModelIdRef { get; set; } + /// + /// URL pointing at the external 3D model resource. + /// [JsonPropertyName("href")] public string Href { get; set; } + /// + /// Reference to an item inside the external solid-model resource. + /// [JsonPropertyName("itemRef")] public string ItemRef { get; set; } + /// + /// IANA media type of the referenced 3D model resource (for example + /// STEP, STL, GLTF). + /// [JsonPropertyName("mediaType")] public string MediaType { get; set; } + /// + /// Reference to the id of the coordinate system the solid + /// model is expressed in. + /// [JsonPropertyName("coordinateSystemIdRef")] public string CoordinateSystemIdRef { get; set; } + /// + /// The translation and rotation relating the solid model to its + /// parent coordinate system. + /// [JsonPropertyName("Transformation")] public JsonTransformation Transformation { get; set; } + /// + /// The scale of the solid model as a numeric JSON array, when + /// expressed inline. + /// [JsonPropertyName("Scale")] public IEnumerable Scale { get; set; } + /// + /// The scale of the solid model as a data set, when expressed by + /// reference. + /// [JsonPropertyName("ScaleDataSet")] public JsonScaleDataSet ScaleDataSet { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonSolidModel() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , selecting the inline numeric-array or + /// data-set representation for the scale. + /// public JsonSolidModel(ISolidModel solidModel) { if (solidModel != null) @@ -55,6 +103,11 @@ public JsonSolidModel(ISolidModel solidModel) } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing the media-type enumeration and + /// preferring the data-set representation of the scale when present. + /// public ISolidModel ToSolidModel() { var solidModel = new SolidModel(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSource.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSource.cs index 8a5b7ad4e..da87637b7 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSource.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSource.cs @@ -6,23 +6,50 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a data-item Source in + /// the cppagent-compatible shape. Identifies the originating + /// component, data item, or composition that backs the data item, + /// optionally with a literal source value. Converts to and from the + /// strongly-typed model. + /// public class JsonSource { + /// + /// Reference to the id of the originating component. + /// [JsonPropertyName("componentId")] public string ComponentId { get; set; } + /// + /// Reference to the id of the originating data item. + /// [JsonPropertyName("dataItemId")] public string DataItemId { get; set; } + /// + /// Reference to the id of the originating composition. + /// [JsonPropertyName("compositionId")] public string CompositionId { get; set; } + /// + /// The literal source value, when the source is itself a + /// concrete identifier rather than a reference. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonSource() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonSource(ISource source) { if (source != null) @@ -35,6 +62,10 @@ public JsonSource(ISource source) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public ISource ToSource() { var source = new Source(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSpecification.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSpecification.cs index 32b2a272d..9a212327a 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSpecification.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSpecification.cs @@ -6,32 +6,75 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a scalar + /// Specification in the cppagent-compatible shape, adding the + /// numeric limit bands (absolute and warning tiers, nominal value) on + /// top of the shared + /// attributes. Converts to and from the strongly-typed + /// model. + /// public class JsonSpecification : JsonAbstractSpecification { + /// + /// The absolute upper bound; values above this are out of + /// specification. + /// [JsonPropertyName("Maximum")] public double? Maximum { get; set; } + /// + /// The upper engineering limit; the largest value still + /// considered conforming. + /// [JsonPropertyName("UpperLimit")] public double? UpperLimit { get; set; } + /// + /// The upper warning threshold; values above this should raise + /// an early-warning signal. + /// [JsonPropertyName("UpperWarning")] public double? UpperWarning { get; set; } + /// + /// The nominal (target) value. + /// [JsonPropertyName("Nominal")] public double? Nominal { get; set; } + /// + /// The lower engineering limit; the smallest value still + /// considered conforming. + /// [JsonPropertyName("LowerLimit")] public double? LowerLimit { get; set; } + /// + /// The lower warning threshold; values below this should raise + /// an early-warning signal. + /// [JsonPropertyName("LowerWarning")] public double? LowerWarning { get; set; } + /// + /// The absolute lower bound; values below this are out of + /// specification. + /// [JsonPropertyName("Minimum")] public double? Minimum { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonSpecification() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , delegating the shared attributes + /// to . + /// public JsonSpecification(ISpecification specification) : base(specification) { if (specification != null) @@ -47,6 +90,11 @@ public JsonSpecification(ISpecification specification) : base(specification) } + /// + /// Converts this surrogate to a strongly-typed + /// , applying the scalar limit bands + /// in addition to the shared attributes parsed from the base. + /// public override ISpecification ToSpecification() { var specification = new Specification(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSpecificationContainer.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSpecificationContainer.cs index d20eeec10..7a9a96f00 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSpecificationContainer.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSpecificationContainer.cs @@ -6,11 +6,24 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate that partitions a component's + /// configuration specifications by kind into typed sibling lists, + /// keyed by element name (Specification, + /// ProcessSpecification) per the cppagent shape. Either list + /// is suppressed when its partition is empty. + /// public class JsonSpecificationContainer { + /// + /// Scalar specifications in the container. + /// [JsonPropertyName("Specification")] public List Specifications { get; set; } + /// + /// Process specifications in the container. + /// [JsonPropertyName("ProcessSpecification")] public List ProcessSpecifications { get; set; } } diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSpecificationLimits.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSpecificationLimits.cs index c137df494..f01b67688 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSpecificationLimits.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonSpecificationLimits.cs @@ -6,20 +6,45 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for the SpecificationLimits + /// sub-element of a ProcessSpecification in the + /// cppagent-compatible shape. Carries the absolute conformance + /// bounds plus the nominal target value. Converts to and from the + /// strongly-typed model. + /// public class JsonSpecificationLimits { + /// + /// The upper specification limit; values above this are + /// non-conforming. + /// [JsonPropertyName("UpperLimit")] public double? UpperLimit { get; set; } + /// + /// The nominal (target) value of the specification. + /// [JsonPropertyName("Nominal")] public double? Nominal { get; set; } + /// + /// The lower specification limit; values below this are + /// non-conforming. + /// [JsonPropertyName("LowerLimit")] public double? LowerLimit { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonSpecificationLimits() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonSpecificationLimits(ISpecificationLimits specificationLimits) { if (specificationLimits != null) @@ -31,6 +56,10 @@ public JsonSpecificationLimits(ISpecificationLimits specificationLimits) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public ISpecificationLimits ToSpecificationLimits() { var specificationLimits = new SpecificationLimits(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonTransformation.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonTransformation.cs index 7672bc2fe..0c6ee0ffb 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonTransformation.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonTransformation.cs @@ -7,23 +7,54 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a coordinate + /// Transformation in the cppagent-compatible shape, made up + /// of a translation and a rotation. Each component is emitted either + /// inline as a numeric JSON array (when expressed as a literal + /// vector) or by reference as a data set. Converts to and from the + /// strongly-typed model. + /// public class JsonTransformation { + /// + /// The translation vector as a numeric JSON array, when + /// expressed inline. + /// [JsonPropertyName("Translation")] public IEnumerable Translation { get; set; } + /// + /// The translation expressed by reference as a data set. + /// [JsonPropertyName("TranslationDataSet")] public JsonTranslationDataSet TranslationDataSet { get; set; } + /// + /// The rotation vector as a numeric JSON array, when expressed + /// inline. + /// [JsonPropertyName("Rotation")] public IEnumerable Rotation { get; set; } + /// + /// The rotation expressed by reference as a data set. + /// [JsonPropertyName("RotationDataSet")] public JsonRotationDataSet RotationDataSet { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonTransformation() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , selecting the inline numeric + /// array or data-set representation independently for the + /// translation and rotation. + /// public JsonTransformation(ITransformation transformation) { if (transformation != null) @@ -36,6 +67,11 @@ public JsonTransformation(ITransformation transformation) } + /// + /// Converts this surrogate to a strongly-typed + /// , preferring the data-set + /// representation of each component when present. + /// public ITransformation ToTransformation() { var transformation = new Transformation(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonTranslationDataSet.cs b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonTranslationDataSet.cs index ec5652feb..2670b1997 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonTranslationDataSet.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Devices/JsonTranslationDataSet.cs @@ -12,20 +12,46 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a Configuration + /// Translation expressed as a data set in the + /// cppagent-compatible shape. The flat + /// {"X": v, "Y": v, "Z": v} PascalCase object encoding + /// matches the cppagent v2 DataSet convention; the values are + /// serialized as strings to round-trip equipment-native formatting. + /// Converts to and from the strongly-typed + /// model. + /// public class JsonTranslationDataSet { + /// + /// Translation along the X direction. + /// [JsonPropertyName("X")] public string X { get; set; } + /// + /// Translation along the Y direction. + /// [JsonPropertyName("Y")] public string Y { get; set; } + /// + /// Translation along the Z direction. + /// [JsonPropertyName("Z")] public string Z { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonTranslationDataSet() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonTranslationDataSet(ITranslationDataSet dataSet) { if (dataSet != null) @@ -37,6 +63,10 @@ public JsonTranslationDataSet(ITranslationDataSet dataSet) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public ITranslationDataSet ToTranslationDataSet() { var dataSet = new TranslationDataSet(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Formatters/JsonHttpEntityFormatter.cs b/libraries/MTConnect.NET-JSON-cppagent/Formatters/JsonHttpEntityFormatter.cs index 181febca6..7c0b42347 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Formatters/JsonHttpEntityFormatter.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Formatters/JsonHttpEntityFormatter.cs @@ -22,13 +22,33 @@ namespace MTConnect.Formatters { + /// + /// HTTP entity formatter that serializes and deserializes individual + /// MTConnect entities (Device, Asset, Composition, DataItem) using the + /// cppagent-compatible JSON shape. Used by the PUT/POST entity-level + /// endpoints that operate on a single entity rather than a full + /// response document. + /// public class JsonHttpEntityFormatter : IEntityFormatter { + /// + /// The formatter identifier exposed to the agent's content-type + /// negotiation, distinguishing this formatter from the plain + /// MTConnect JSON formatter. + /// public virtual string Id => "JSON-cppagent"; + /// + /// The HTTP Content-Type emitted by this formatter. + /// public virtual string ContentType => "application/json"; + /// + /// Serializes a single device using the cppagent-compatible + /// surrogate, honouring the + /// indentOutput option. + /// public FormatWriteResult Format(IDevice device, IEnumerable> options = null) { if (device != null) @@ -45,16 +65,32 @@ public FormatWriteResult Format(IDevice device, IEnumerable + /// Single-observation serialization is not part of the cppagent + /// entity surface, so this overload always returns an error + /// result. + /// public FormatWriteResult Format(IObservation observation, IEnumerable> options = null) { return FormatWriteResult.Error(); } + /// + /// Bulk-observation serialization is not part of the cppagent + /// entity surface, so this overload always returns an error + /// result. + /// public FormatWriteResult Format(IEnumerable observations, IEnumerable> options = null) { return FormatWriteResult.Error(); } + /// + /// Serializes a single asset by wrapping it in a one-element + /// container and dispatching to the + /// appropriate cppagent asset surrogate + /// (CuttingTool, File, RawMaterial). + /// public FormatWriteResult Format(IAsset asset, IEnumerable> options = null) { if (asset != null) @@ -65,7 +101,7 @@ public FormatWriteResult Format(IAsset asset, IEnumerable(); - assets.CuttingTools.Add(new JsonCuttingToolAsset(asset as CuttingToolAsset)); + assets.CuttingTools.Add(new JsonCuttingToolAsset(asset as CuttingToolAsset)); break; case "File": @@ -84,9 +120,9 @@ public FormatWriteResult Format(IAsset asset, IEnumerable + /// Deserializes a single device from JSON via the + /// envelope and reconstructs the + /// strongly-typed model. + /// public FormatReadResult CreateDevice(Stream content, IEnumerable> options = null) { var messages = new List(); @@ -119,6 +160,10 @@ public FormatReadResult CreateDevice(Stream content, IEnumerable(); } + /// + /// Component-level deserialization is not yet implemented for the + /// cppagent shape; the method always returns an empty result. + /// public FormatReadResult CreateComponent(Stream content, IEnumerable> options = null) { var messages = new List(); @@ -138,6 +183,11 @@ public FormatReadResult CreateComponent(Stream content, IEnumerable< return new FormatReadResult(); } + /// + /// Deserializes a single composition from JSON via the + /// surrogate and reconstructs the + /// strongly-typed model. + /// public FormatReadResult CreateComposition(Stream content, IEnumerable> options = null) { var messages = new List(); @@ -157,6 +207,11 @@ public FormatReadResult CreateComposition(Stream content, IEnumera return new FormatReadResult(); } + /// + /// Deserializes a single data item from JSON via the + /// surrogate and reconstructs the + /// strongly-typed model. + /// public FormatReadResult CreateDataItem(Stream content, IEnumerable> options = null) { var messages = new List(); @@ -176,6 +231,14 @@ public FormatReadResult CreateDataItem(Stream content, IEnumerable(); } + /// + /// Deserializes a single asset from JSON, dispatching to the + /// appropriate cppagent asset surrogate + /// (CuttingTool, File, QIFDocumentWrapper, + /// RawMaterial) based on the supplied asset type + /// discriminator. Any deserialization exception is captured into + /// the errors list rather than propagated. + /// public FormatReadResult CreateAsset(string assetType, Stream content, IEnumerable> options = null) { var messages = new List(); @@ -202,7 +265,7 @@ public FormatReadResult CreateAsset(string assetType, Stream content, IE { switch (assetType) { - case "CuttingTool": + case "CuttingTool": asset = JsonSerializer.Deserialize(json).ToCuttingToolAsset(); break; diff --git a/libraries/MTConnect.NET-JSON-cppagent/Formatters/JsonHttpResponseDocumentFormatter.cs b/libraries/MTConnect.NET-JSON-cppagent/Formatters/JsonHttpResponseDocumentFormatter.cs index ef389e0ff..165add234 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Formatters/JsonHttpResponseDocumentFormatter.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Formatters/JsonHttpResponseDocumentFormatter.cs @@ -17,13 +17,33 @@ namespace MTConnect.Formatters { + /// + /// HTTP response document formatter that serializes and deserializes + /// MTConnect response documents using the cppagent-compatible JSON + /// shape. Routes each document family (Probe/Devices, Streams, Assets, + /// Error) through its dedicated surrogate model and obeys the + /// indentOutput formatter option to switch between compact and + /// pretty-printed output. + /// public class JsonHttpResponseDocumentFormatter : IResponseDocumentFormatter { + /// + /// The formatter identifier exposed to the agent's content-type + /// negotiation, distinguishing this formatter from the plain + /// MTConnect JSON formatter. + /// public virtual string Id => "JSON-cppagent"; + /// + /// The HTTP Content-Type emitted by this formatter. + /// public virtual string ContentType => "application/json"; + /// + /// Serializes a Probe/Devices response document using the + /// cppagent-compatible JSON surrogate. + /// public virtual FormatWriteResult Format(IDevicesResponseDocument document, IEnumerable> options = null) { // Read Indent Option passed to Formatter @@ -40,6 +60,12 @@ public virtual FormatWriteResult Format(IDevicesResponseDocument document, IEnum return FormatWriteResult.Error(); } + /// + /// Serializes a Streams response document using the + /// cppagent-compatible JSON surrogate. Accepts the output document + /// by reference to allow downstream consumers to mutate the source + /// without copying. + /// public virtual FormatWriteResult Format(ref IStreamsResponseOutputDocument document, IEnumerable> options = null) { // Read Indent Option passed to Formatter @@ -56,6 +82,10 @@ public virtual FormatWriteResult Format(ref IStreamsResponseOutputDocument docum return FormatWriteResult.Error(); } + /// + /// Serializes an Assets response document using the + /// cppagent-compatible JSON surrogate. + /// public virtual FormatWriteResult Format(IAssetsResponseDocument document, IEnumerable> options = null) { // Read Indent Option passed to Formatter @@ -72,6 +102,11 @@ public virtual FormatWriteResult Format(IAssetsResponseDocument document, IEnume return FormatWriteResult.Error(); } + /// + /// Serializes an Error response document as JSON. The error + /// document has no cppagent-specific surrogate shape so it is + /// written using its native model. + /// public FormatWriteResult Format(IErrorResponseDocument document, IEnumerable> options = null) { // Read Indent Option passed to Formatter @@ -89,6 +124,10 @@ public FormatWriteResult Format(IErrorResponseDocument document, IEnumerable + /// Deserializes a Probe/Devices response document from a JSON + /// stream and reconstructs the strongly-typed model. + /// public virtual FormatReadResult CreateDevicesResponseDocument(Stream content, IEnumerable> options = null) { // Read Document @@ -98,6 +137,10 @@ public virtual FormatReadResult CreateDevicesResponseD return new FormatReadResult(document.ToDocument(), success); } + /// + /// Deserializes a Streams response document from a JSON stream and + /// reconstructs the strongly-typed model. + /// public virtual FormatReadResult CreateStreamsResponseDocument(Stream content, IEnumerable> options = null) { // Read Document @@ -107,6 +150,10 @@ public virtual FormatReadResult CreateStreamsResponseD return new FormatReadResult(document.ToStreamsDocument(), success); } + /// + /// Deserializes an Assets response document from a JSON stream and + /// reconstructs the strongly-typed model. + /// public virtual FormatReadResult CreateAssetsResponseDocument(Stream content, IEnumerable> options = null) { // Read Document @@ -116,6 +163,10 @@ public virtual FormatReadResult CreateAssetsResponseDoc return new FormatReadResult(document.ToAssetsDocument(), success); } + /// + /// Deserializes an Error response document from a JSON stream using + /// the native error model. + /// public FormatReadResult CreateErrorResponseDocument(Stream content, IEnumerable> options = null) { // Read Document @@ -126,6 +177,11 @@ public FormatReadResult CreateErrorResponseDocument(Stre } + /// + /// Reads a single scalar formatter option by key and converts it to + /// the requested type, returning default(T) on absence or + /// conversion failure. + /// protected static T GetFormatterOption(IEnumerable> options, string key) { if (!options.IsNullOrEmpty()) @@ -144,6 +200,11 @@ protected static T GetFormatterOption(IEnumerable + /// Reads every occurrence of a multi-valued formatter option by key + /// and converts each value to the requested type, skipping any + /// value that fails conversion. + /// protected static IEnumerable GetFormatterOptions(IEnumerable> options, string key) { var l = new List(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Formatters/JsonMqttEntityFormatter.cs b/libraries/MTConnect.NET-JSON-cppagent/Formatters/JsonMqttEntityFormatter.cs index a0dd7c231..48b2017b2 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Formatters/JsonMqttEntityFormatter.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Formatters/JsonMqttEntityFormatter.cs @@ -3,8 +3,18 @@ namespace MTConnect.Formatters { + /// + /// MQTT entity formatter that reuses the + /// cppagent serialization + /// behaviour and only overrides the formatter identifier so the + /// MQTT publishing layer can distinguish the two transports. + /// public class JsonMqttEntityFormatter : JsonHttpEntityFormatter { + /// + /// The formatter identifier exposed to the MQTT publishing + /// layer. + /// public override string Id => "JSON-cppagent-mqtt"; } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-JSON-cppagent/Formatters/JsonMqttResponseDocumentFormatter.cs b/libraries/MTConnect.NET-JSON-cppagent/Formatters/JsonMqttResponseDocumentFormatter.cs index 394bc60c8..92b9b5e1a 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Formatters/JsonMqttResponseDocumentFormatter.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Formatters/JsonMqttResponseDocumentFormatter.cs @@ -13,13 +13,35 @@ namespace MTConnect.Formatters { + /// + /// MQTT response document formatter that emits one entity per MQTT + /// retained payload using the cppagent-compatible JSON shape. + /// Unlike the HTTP formatter, the Devices payload is reduced to the + /// first device in the document and the Assets payload is reduced + /// to a single-asset container so each MQTT topic carries one + /// entity. + /// public class JsonMqttResponseDocumentFormatter : JsonHttpResponseDocumentFormatter { + /// + /// The formatter identifier exposed to the MQTT publishing layer, + /// distinguishing it from the HTTP formatter. + /// public override string Id => "JSON-cppagent-mqtt"; + /// + /// The MQTT payload Content-Type emitted by this + /// formatter. + /// public override string ContentType => "application/json"; + /// + /// Serializes the first device of the Devices response document + /// as an individual MQTT payload using + /// ; returns an error result + /// when the document carries no devices. + /// public override FormatWriteResult Format(IDevicesResponseDocument document, IEnumerable> options = null) { // Read Indent Option passed to Formatter @@ -40,6 +62,10 @@ public override FormatWriteResult Format(IDevicesResponseDocument document, IEnu return FormatWriteResult.Error(); } + /// + /// Serializes the Assets response document as an MQTT payload + /// using the standard cppagent assets surrogate. + /// public override FormatWriteResult Format(IAssetsResponseDocument document, IEnumerable> options = null) { // Read Indent Option passed to Formatter @@ -57,6 +83,13 @@ public override FormatWriteResult Format(IAssetsResponseDocument document, IEnum } + /// + /// Deserializes a single device from an MQTT payload via + /// and wraps it in a + /// one-device Devices response document. Any deserialization + /// exception is captured into the result's errors collection + /// rather than propagated. + /// public override FormatReadResult CreateDevicesResponseDocument(Stream content, IEnumerable> options = null) { try @@ -83,6 +116,11 @@ public override FormatReadResult CreateDevicesResponse } } + /// + /// Deserializes a single asset from an MQTT payload via + /// and wraps it in a + /// one-asset Assets response document. + /// public override FormatReadResult CreateAssetsResponseDocument(Stream content, IEnumerable> options = null) { // Read Document diff --git a/libraries/MTConnect.NET-JSON-cppagent/JsonFunctions.cs b/libraries/MTConnect.NET-JSON-cppagent/JsonFunctions.cs index bdcaf9d01..046fd4f47 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/JsonFunctions.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/JsonFunctions.cs @@ -7,8 +7,23 @@ namespace MTConnect { + /// + /// Helpers for configuring the cppagent-compatible JSON serializer + /// (option sets and one-shot convert wrappers around + /// ). The shared option sets switch off + /// indentation by default, ignore properties with default values, + /// allow numbers to be read from strings (a common cppagent edge), + /// and keep property lookup case-insensitive to tolerate equipment + /// payload variation. + /// public static class JsonFunctions { + /// + /// Default serializer options used when no indentOutput + /// option is requested. Produces compact JSON, omits properties + /// at their default value, allows numbers to be read from + /// strings, and ignores property-name casing. + /// public static JsonSerializerOptions DefaultOptions { get @@ -26,6 +41,11 @@ public static JsonSerializerOptions DefaultOptions } } + /// + /// Pretty-printed serializer options used when the + /// indentOutput formatter option is enabled; otherwise + /// identical to . + /// public static JsonSerializerOptions IndentOptions { get @@ -44,6 +64,12 @@ public static JsonSerializerOptions IndentOptions } + /// + /// Serializes to a JSON string using the + /// cppagent option defaults, optionally with an extra converter + /// and pretty-printing. Returns null on any + /// serialization failure or when the input is null. + /// public static string Convert(object obj, JsonConverter converter = null, bool indented = false) { if (obj != null) @@ -71,6 +97,12 @@ public static string Convert(object obj, JsonConverter converter = null, bool in return null; } + /// + /// Serializes to a UTF-8 byte array + /// using the cppagent option defaults, optionally with an extra + /// converter and pretty-printing. Returns null on any + /// serialization failure or when the input is null. + /// public static byte[] ConvertBytes(object obj, JsonConverter converter = null, bool indented = false) { if (obj != null) @@ -98,6 +130,13 @@ public static byte[] ConvertBytes(object obj, JsonConverter converter = null, bo return null; } + /// + /// Serializes into a fresh + /// using the cppagent option + /// defaults, optionally with an extra converter and + /// pretty-printing. Returns null on any serialization + /// failure or when the input is null. + /// public static Stream ConvertStream(object obj, JsonConverter converter = null, bool indented = false) { if (obj != null) diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonCell.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonCell.cs index 03507ec64..fc77f137e 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonCell.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonCell.cs @@ -6,17 +6,37 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for a single cell of a table-entry + /// observation. Carried inside a 's cell + /// list when expressed as discrete cell objects, before the parent + /// converter collapses cells into + /// the row dictionary on emission. + /// public class JsonCell { + /// + /// The cell key. + /// [JsonPropertyName("key")] public string Key { get; set; } + /// + /// The cell value as a string. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCell() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonCell(ITableCell cell) { if (cell != null) diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonComponentStream.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonComponentStream.cs index 3bc7865fc..9bfad8724 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonComponentStream.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonComponentStream.cs @@ -9,23 +9,53 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for a ComponentStream in the + /// cppagent-compatible Streams shape. Observations belonging to the + /// component are partitioned into the three sibling containers + /// Samples, Events, and Condition by data-item + /// category and emitted as keyed dictionaries rather than the XML + /// element-array form. Converts to and from the strongly-typed + /// model. + /// public class JsonComponentStream { + /// + /// The element name of the component (for example + /// Axes, Controller). + /// [JsonPropertyName("component")] public string Component { get; set; } + /// + /// The unique id of the component this stream is reporting + /// observations for. + /// [JsonPropertyName("componentId")] public string ComponentId { get; set; } + /// + /// The descriptive name of the component. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The native name of the component as used on the equipment. + /// [JsonPropertyName("nativeName")] public string NativeName { get; set; } + /// + /// The UUID of the component. + /// [JsonPropertyName("uuid")] public string Uuid { get; set; } + /// + /// Aggregated view of every observation across the three category + /// containers; not serialized. + /// [JsonIgnore] public List Observations { @@ -52,18 +82,37 @@ public List Observations } } + /// + /// SAMPLE-category observations keyed by data-item identifier. + /// [JsonPropertyName("Samples")] public JsonSamples Samples { get; set; } + /// + /// EVENT-category observations keyed by data-item identifier. + /// [JsonPropertyName("Events")] public JsonEvents Events { get; set; } + /// + /// CONDITION-category observations keyed by data-item identifier + /// (note the singular JSON key Condition). + /// [JsonPropertyName("Condition")] public JsonConditions Conditions { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonComponentStream() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , partitioning the + /// observations into SAMPLE, EVENT, and CONDITION containers and + /// suppressing any container that has no observations. + /// public JsonComponentStream(IComponentStreamOutput componentStream) { if (componentStream != null) @@ -101,6 +150,11 @@ public JsonComponentStream(IComponentStreamOutput componentStream) } + /// + /// Converts this surrogate to a strongly-typed + /// , flattening the three category + /// containers back into a single observations list. + /// public ComponentStream ToComponentStream() { var componentStream = new ComponentStream(); @@ -134,5 +188,5 @@ public ComponentStream ToComponentStream() return componentStream; } - } + } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonCondition.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonCondition.cs index 5356018e2..738df8a90 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonCondition.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonCondition.cs @@ -8,29 +8,67 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for a CONDITION observation in the + /// cppagent-compatible Streams shape. Each entry in the parent + /// map carries the condition's type, + /// native severity/code, qualifier, and message. The condition level + /// (NORMAL/WARNING/FAULT/UNAVAILABLE) is represented by the parent + /// dictionary key rather than a field on this surrogate, so it is + /// supplied to . + /// public class JsonCondition : JsonObservation { + /// + /// The MTConnect type of the underlying data item (for example + /// ACTUATOR, SYSTEM). + /// [JsonPropertyName("type")] public string Type { get; set; } //[JsonPropertyName("level")] //public string Level { get; set; } + /// + /// Optional native severity reported by the equipment alongside + /// the native code. + /// [JsonPropertyName("nativeSeverity")] public string NativeSeverity { get; set; } + /// + /// Optional qualifier refining the condition (HIGH, LOW) when + /// not NOT_SPECIFIED. + /// [JsonPropertyName("qualifier")] public string Qualifier { get; set; } + /// + /// Optional statistic applied to the underlying data, mirroring + /// the SAMPLE statistic attribute. + /// [JsonPropertyName("statistic")] public string Statistic { get; set; } + /// + /// The free-form condition message text reported by the + /// equipment. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCondition() { } + /// + /// Initializes the surrogate from a strongly-typed condition + /// , optionally surfacing the category + /// and instance-id fields. The qualifier is suppressed when it + /// equals the implicit NOT_SPECIFIED default. + /// public JsonCondition(IObservation observation, bool categoryOutput = false, bool instanceIdOutput = false) { var condition = observation as ConditionObservation; @@ -54,6 +92,12 @@ public JsonCondition(IObservation observation, bool categoryOutput = false, bool } } + /// + /// Initializes the surrogate from a streaming + /// , pulling message, native + /// code, native severity, and qualifier from the observation's + /// value bag by key. + /// public JsonCondition(IObservationOutput condition) { if (condition != null) @@ -90,6 +134,12 @@ public JsonCondition(IObservationOutput condition) } + /// + /// Converts this surrogate to a strongly-typed + /// , restoring the condition + /// level from the parent dictionary key (passed in by the caller) + /// and parsing the qualifier enumeration from its serialized form. + /// public IConditionObservation ToCondition(ConditionLevel conditionLevel) { var condition = new ConditionObservation(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonConditions.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonConditions.cs index 8cfbb7f95..678f16357 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonConditions.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonConditions.cs @@ -9,8 +9,31 @@ namespace MTConnect.Streams.Json { + /// + /// Typed representation of a Condition list on a Component stream, + /// bucketed by Condition level (Fault, Warning, Normal, Unavailable). + /// + /// + /// Serialized via in the + /// cppagent JSON v2 wire shape: an array of single-key wrapper + /// objects, one per Condition entry + /// (e.g. [{"Normal": {...}}, {"Warning": {...}}]). + /// The level order on the wire is fixed at Fault, Warning, Normal, + /// Unavailable; mixed-level interleaving is not round-trip preserved + /// through this typed model. The legacy MTConnect JSON v1 + /// object-keyed shape ({"Fault": [...], "Warning": [...], ...}) + /// is still accepted on the read path for back-compat. + /// + [System.Text.Json.Serialization.JsonConverter(typeof(JsonConditionsConverter))] public class JsonConditions { + /// + /// Materializes every level bucket into a flat list of + /// instances, tagged with the + /// corresponding . Enumeration order + /// matches the wire-emission order: Fault, then Warning, then + /// Normal, then Unavailable. + /// [JsonIgnore] public List Observations { @@ -42,21 +65,54 @@ public List Observations } } + /// + /// Condition entries at FAULT level. Source order is + /// preserved within the bucket; entries are emitted on the wire + /// as {"Fault": {...}} wrapper objects, ahead of every + /// other level. + /// [JsonPropertyName("Fault")] public IEnumerable Fault { get; set; } + /// + /// Condition entries at WARNING level. Source order is + /// preserved within the bucket; entries are emitted on the wire + /// as {"Warning": {...}} wrapper objects, after Fault + /// and before Normal. + /// [JsonPropertyName("Warning")] public IEnumerable Warning { get; set; } + /// + /// Condition entries at NORMAL level. Source order is + /// preserved within the bucket; entries are emitted on the wire + /// as {"Normal": {...}} wrapper objects, after Warning + /// and before Unavailable. + /// [JsonPropertyName("Normal")] public IEnumerable Normal { get; set; } + /// + /// Condition entries at UNAVAILABLE level. Source order + /// is preserved within the bucket; entries are emitted on the + /// wire as {"Unavailable": {...}} wrapper objects, after + /// every other level. + /// [JsonPropertyName("Unavailable")] public IEnumerable Unavailable { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonConditions() { } + /// + /// Initializes the container from an observation-output + /// sequence, partitioning each observation into the + /// Fault/Warning/Normal/Unavailable bucket indicated by its + /// Level value-bag entry. + /// public JsonConditions(IEnumerable observations) { if (observations != null) @@ -113,5 +169,5 @@ public JsonConditions(IEnumerable observations) } } } - } -} \ No newline at end of file + } +} diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonConditionsConverter.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonConditionsConverter.cs new file mode 100644 index 000000000..668d6ae77 --- /dev/null +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonConditionsConverter.cs @@ -0,0 +1,208 @@ +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// TrakHound Inc. licenses this file to you under the MIT license. + +using System; +using System.Collections.Generic; +using System.Text.Json; +using System.Text.Json.Serialization; + +namespace MTConnect.Streams.Json +{ + // Serializes JsonConditions in the cppagent JSON v2 wire shape: an + // array of single-key wrapper objects, one per Condition entry + // (e.g. [{"Normal": {...}}, {"Warning": {...}}]). The XSD + // ConditionListType is + // of Normal|Warning|Fault|Unavailable. + // + // Ordering: the typed JsonConditions POCO buckets entries by level + // (Fault, Warning, Normal, Unavailable). The Write path always emits + // in that fixed level order (Fault first, then Warning, then Normal, + // then Unavailable), with source order preserved within each bucket. + // Mixed-level interleaving on the wire is therefore NOT round-trip + // preserved: reading [{Fault:f1},{Normal:n1},{Fault:f2}] yields + // Fault=[f1,f2], Normal=[n1] and re-serializes as + // [{Fault:f1},{Fault:f2},{Normal:n1}]. Round-trip byte-identity + // holds only when each level's entries are already contiguous on + // the input wire. + // + // The legacy MTConnect JSON v1 object-keyed shape + // ({"Fault": [...], "Warning": [...], ...}) is still accepted on the + // read path for back-compat. + internal sealed class JsonConditionsConverter : JsonConverter + { + private const string FaultLevel = "Fault"; + private const string WarningLevel = "Warning"; + private const string NormalLevel = "Normal"; + private const string UnavailableLevel = "Unavailable"; + + public override JsonConditions Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options) + { + switch (reader.TokenType) + { + case JsonTokenType.Null: + return null; + + case JsonTokenType.StartArray: + return ReadArrayShape(ref reader, options); + + case JsonTokenType.StartObject: + return ReadObjectShape(ref reader, options); + + default: + throw new JsonException( + $"Unexpected token '{reader.TokenType}' when reading JsonConditions; expected array, object, or null."); + } + } + + public override void Write(Utf8JsonWriter writer, JsonConditions value, JsonSerializerOptions options) + { + if (value == null) + { + writer.WriteNullValue(); + return; + } + + writer.WriteStartArray(); + + WriteLevel(writer, FaultLevel, value.Fault, options); + WriteLevel(writer, WarningLevel, value.Warning, options); + WriteLevel(writer, NormalLevel, value.Normal, options); + WriteLevel(writer, UnavailableLevel, value.Unavailable, options); + + writer.WriteEndArray(); + } + + private static void WriteLevel(Utf8JsonWriter writer, string levelName, IEnumerable entries, JsonSerializerOptions options) + { + if (entries == null) return; + + foreach (var entry in entries) + { + writer.WriteStartObject(); + writer.WritePropertyName(levelName); + JsonSerializer.Serialize(writer, entry, options); + writer.WriteEndObject(); + } + } + + private static JsonConditions ReadArrayShape(ref Utf8JsonReader reader, JsonSerializerOptions options) + { + var faults = new List(); + var warnings = new List(); + var normals = new List(); + var unavailables = new List(); + + while (reader.Read()) + { + if (reader.TokenType == JsonTokenType.EndArray) break; + + if (reader.TokenType != JsonTokenType.StartObject) + { + throw new JsonException( + $"Unexpected token '{reader.TokenType}' inside JsonConditions array; expected object wrapper."); + } + + if (!reader.Read() || reader.TokenType != JsonTokenType.PropertyName) + { + throw new JsonException("Expected property name inside JsonConditions wrapper object."); + } + + var levelName = reader.GetString(); + if (!reader.Read()) + { + throw new JsonException("Expected value after Condition level name in JsonConditions wrapper object."); + } + var entry = JsonSerializer.Deserialize(ref reader, options); + if (entry == null) + { + throw new JsonException("Null Condition entry value in JsonConditions wrapper."); + } + + if (!reader.Read() || reader.TokenType != JsonTokenType.EndObject) + { + throw new JsonException("Expected end of JsonConditions wrapper object after entry."); + } + + switch (levelName) + { + case FaultLevel: + faults.Add(entry); + break; + case WarningLevel: + warnings.Add(entry); + break; + case NormalLevel: + normals.Add(entry); + break; + case UnavailableLevel: + unavailables.Add(entry); + break; + default: + throw new JsonException( + $"Unknown Condition level '{levelName}' in JsonConditions array; expected Fault, Warning, Normal, or Unavailable."); + } + } + + return new JsonConditions + { + Fault = faults.Count > 0 ? faults : null, + Warning = warnings.Count > 0 ? warnings : null, + Normal = normals.Count > 0 ? normals : null, + Unavailable = unavailables.Count > 0 ? unavailables : null, + }; + } + + // Reads the legacy MTConnect JSON v1 object-keyed shape: + // {"Fault": [...], "Warning": [...], ...}. Duplicate level keys + // on the input (e.g. {"Fault":[a],"Fault":[b]}) are by-design + // last-write-wins: each occurrence overwrites the previous + // entry list. This is accepted asymmetry with the array path, + // which appends across all occurrences. Legacy producers that + // emit each level key exactly once are unaffected; the asymmetry + // only surfaces on malformed-or-duplicate legacy input, where + // last-write-wins is a deterministic, documented behavior. + private static JsonConditions ReadObjectShape(ref Utf8JsonReader reader, JsonSerializerOptions options) + { + var result = new JsonConditions(); + + while (reader.Read()) + { + if (reader.TokenType == JsonTokenType.EndObject) break; + + if (reader.TokenType != JsonTokenType.PropertyName) + { + throw new JsonException( + $"Unexpected token '{reader.TokenType}' inside JsonConditions object; expected property name."); + } + + var levelName = reader.GetString(); + if (!reader.Read()) + { + throw new JsonException("Expected value after Condition level name in JsonConditions wrapper object."); + } + var entries = JsonSerializer.Deserialize>(ref reader, options); + + switch (levelName) + { + case FaultLevel: + result.Fault = entries; + break; + case WarningLevel: + result.Warning = entries; + break; + case NormalLevel: + result.Normal = entries; + break; + case UnavailableLevel: + result.Unavailable = entries; + break; + default: + throw new JsonException( + $"Unknown Condition level '{levelName}' in JsonConditions object; expected Fault, Warning, Normal, or Unavailable."); + } + } + + return result; + } + } +} diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonDataSetEntries.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonDataSetEntries.cs index 0410f976b..fdf07b68e 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonDataSetEntries.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonDataSetEntries.cs @@ -12,36 +12,80 @@ namespace MTConnect.NET_JSON_cppagent.Streams { + /// + /// JSON serialization surrogate for the key/value entries carried by a + /// DATA_SET observation in the cppagent-compatible shape. Entries are + /// serialized as a JSON object keyed by entry name with numeric or + /// string values inferred per entry, and the unavailable state is + /// collapsed to the string UNAVAILABLE. + /// [JsonConverter(typeof(JsonDataSetEntriesConverter))] public class JsonDataSetEntries { + /// + /// The data-set entries keyed by entry name. + /// public Dictionary Entries { get; set; } + /// + /// The number of entries, captured at construction for round-trip + /// and inspection convenience. + /// public int Count { get; set; } + /// + /// True when the underlying data-set observation reported the + /// UNAVAILABLE sentinel rather than a set of entries. + /// public bool IsUnavailable { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDataSetEntries() { } - public JsonDataSetEntries(bool isUnavailable) + /// + /// Initializes an unavailable-marker instance that will be + /// serialized as the string UNAVAILABLE. + /// + public JsonDataSetEntries(bool isUnavailable) { IsUnavailable = isUnavailable; } + /// + /// Initializes the surrogate from a dictionary of entries, also + /// caching the entry count. + /// public JsonDataSetEntries(Dictionary entries) - { + { Entries = entries; Count = entries != null ? entries.Count : 0; } + /// + /// that reads and writes + /// as either a keyed JSON object + /// or the UNAVAILABLE string sentinel. + /// public class JsonDataSetEntriesConverter : JsonConverter { #if NET5_0_OR_GREATER + /// + /// Returns true so the converter is invoked for null + /// or unavailable JSON values. + /// public override bool HandleNull => true; #endif + /// + /// Reads a JSON object into a + /// , returning null + /// when the token is not an object (the unavailable sentinel + /// case). + /// public override JsonDataSetEntries Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options) { if (reader.TokenType == JsonTokenType.StartObject) @@ -60,6 +104,12 @@ public override JsonDataSetEntries Read(ref Utf8JsonReader reader, Type typeToCo return null; } + /// + /// Writes the surrogate as a JSON object whose value types + /// are inferred per entry (number vs. string), or as the + /// UNAVAILABLE string sentinel when no entries are + /// available. + /// public override void Write(Utf8JsonWriter writer, JsonDataSetEntries value, JsonSerializerOptions options) { if (value != null && !value.IsUnavailable) diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonDeviceStream.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonDeviceStream.cs index fb78826da..86461be8d 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonDeviceStream.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonDeviceStream.cs @@ -7,20 +7,46 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for a DeviceStream in the + /// cppagent-compatible Streams shape. Holds every component stream + /// for a single device in a flat ComponentStream array + /// (note the singular JSON key) and drops any component stream + /// whose observations list is empty after partitioning. Converts to + /// and from the strongly-typed model. + /// public class JsonDeviceStream { + /// + /// The descriptive name of the device. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The UUID of the device. + /// [JsonPropertyName("uuid")] public string Uuid { get; set; } + /// + /// The component streams of this device, each carrying the + /// observations for one MTConnect component. + /// [JsonPropertyName("ComponentStream")] public List ComponentStreams { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDeviceStream() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , skipping any component + /// stream whose observations list is empty after partitioning. + /// public JsonDeviceStream(IDeviceStreamOutput deviceStream) { if (deviceStream != null) @@ -43,6 +69,10 @@ public JsonDeviceStream(IDeviceStreamOutput deviceStream) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public DeviceStream ToDeviceStream() { var deviceStream = new DeviceStream(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonEntry.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonEntry.cs index 3eecb9a2e..fa103a54a 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonEntry.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonEntry.cs @@ -7,29 +7,62 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for a single entry of a DATA_SET or + /// TABLE observation. Carries the entry key, removed flag, a scalar + /// value (for data-set entries) or a list of cell values (for table + /// entries). The cppagent shape collapses these into keyed + /// dictionaries on the parent observation, so this type is also used + /// as a convenience constructor target. + /// public class JsonEntry { + /// + /// The entry key. + /// [JsonPropertyName("key")] public string Key { get; set; } + /// + /// True if the entry was removed in this observation rather than + /// updated. + /// [JsonPropertyName("removed")] public bool Removed { get; set; } + /// + /// The scalar value of a data-set entry, serialized as a string. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// The cell values of a table entry. + /// [JsonPropertyName("cells")] public IEnumerable Cells { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonEntry() { } + /// + /// Convenience constructor that captures a key/value pair from + /// the underlying value bag, coercing the value to its string + /// representation. + /// public JsonEntry(string key, object value) { Key = key; Value = value?.ToString(); } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonEntry(IDataSetEntry entry) { if (entry != null) @@ -40,6 +73,11 @@ public JsonEntry(IDataSetEntry entry) } } + /// + /// Initializes the surrogate from a strongly-typed + /// , projecting each cell into a + /// . + /// public JsonEntry(ITableEntry entry) { if (entry != null) diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonEventDataSet.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonEventDataSet.cs index 35a84ec98..775ddde44 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonEventDataSet.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonEventDataSet.cs @@ -9,17 +9,39 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for an EVENT observation carrying a + /// DATA_SET representation in the cppagent-compatible Streams shape. + /// Mirrors the SAMPLE data-set surrogate but emits under the EVENTS + /// branch of the parent ComponentStream. + /// public class JsonEventDataSet : JsonObservation { + /// + /// The keyed entries of the data set, emitted as a JSON object + /// or as the UNAVAILABLE string sentinel. + /// [JsonPropertyName("value")] public JsonDataSetEntries Entries { get; set; } + /// + /// The number of entries in the data set. + /// [JsonPropertyName("count")] public long? Count { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonEventDataSet() { } + /// + /// Initializes the surrogate from a strongly-typed data-set + /// event , optionally surfacing + /// category and instance-id. Emits an unavailable marker when + /// the source has no entries. + /// public JsonEventDataSet(IObservation observation, bool categoryOutput = false, bool instanceIdOutput = false) { if (observation != null) @@ -55,6 +77,11 @@ public JsonEventDataSet(IObservation observation, bool categoryOutput = false, b } } + /// + /// Initializes the surrogate from a streaming + /// , rehydrating the data-set + /// entries from the observation's value bag. + /// public JsonEventDataSet(IObservationOutput observation) { if (observation != null) @@ -90,6 +117,13 @@ public JsonEventDataSet(IObservationOutput observation) } } + /// + /// Converts this surrogate to a strongly-typed + /// , restoring the + /// data-item type from the supplied dictionary key, or emitting + /// the UNAVAILABLE result when the entries are marked + /// unavailable. + /// public IEventDataSetObservation ToObservation(string type) { var observation = new EventDataSetObservation(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonEventTable.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonEventTable.cs index 0bf6d721d..eb2869c89 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonEventTable.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonEventTable.cs @@ -9,17 +9,39 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for an EVENT observation carrying a + /// TABLE representation in the cppagent-compatible Streams shape. + /// Mirrors the SAMPLE table surrogate but emits under the EVENTS + /// branch of the parent ComponentStream. + /// public class JsonEventTable : JsonObservation { + /// + /// The keyed table rows, emitted as a nested JSON object or as + /// the UNAVAILABLE string sentinel. + /// [JsonPropertyName("value")] public JsonTableEntries Entries { get; set; } + /// + /// The number of rows in the table. + /// [JsonPropertyName("count")] public long? Count { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonEventTable() { } + /// + /// Initializes the surrogate from a strongly-typed table event + /// , optionally surfacing category + /// and instance-id. Emits an unavailable marker when the source + /// has no rows. + /// public JsonEventTable(IObservation observation, bool categoryOutput = false, bool instanceIdOutput = false) { if (observation != null) @@ -55,6 +77,11 @@ public JsonEventTable(IObservation observation, bool categoryOutput = false, boo } } + /// + /// Initializes the surrogate from a streaming + /// , rehydrating the table rows + /// from the observation's value bag. + /// public JsonEventTable(IObservationOutput observation) { if (observation != null) @@ -90,6 +117,13 @@ public JsonEventTable(IObservationOutput observation) } } + /// + /// Converts this surrogate to a strongly-typed + /// , restoring the + /// data-item type from the supplied dictionary key, or emitting + /// the UNAVAILABLE result when the rows are marked + /// unavailable. + /// public IEventTableObservation ToObservation(string type) { var observation = new EventTableObservation(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonEventValue.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonEventValue.cs index fb8aece5d..b4053edbd 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonEventValue.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonEventValue.cs @@ -8,14 +8,33 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for an EVENT observation carrying a + /// scalar value in the cppagent-compatible Streams shape. The + /// value is emitted under the value property as a free-form + /// JSON value (string, number, or boolean) to match cppagent's + /// loose event typing. + /// public class JsonEventValue : JsonObservation { + /// + /// The scalar value of the event. + /// [JsonPropertyName("value")] public object Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonEventValue() { } + /// + /// Initializes the surrogate from a strongly-typed event + /// , optionally surfacing category and + /// instance-id, and pulling the value, reset trigger, native + /// code, and asset type from the observation's value bag. + /// public JsonEventValue(IObservation observation, bool categoryOutput = false, bool instanceIdOutput = false) { if (observation != null) @@ -35,6 +54,11 @@ public JsonEventValue(IObservation observation, bool categoryOutput = false, boo } } + /// + /// Initializes the surrogate from a streaming + /// , pulling the same value-bag + /// fields as the model-level constructor. + /// public JsonEventValue(IObservationOutput observation) { if (observation != null) @@ -53,6 +77,11 @@ public JsonEventValue(IObservationOutput observation) } } + /// + /// Converts this surrogate to a strongly-typed + /// , restoring the data-item + /// type from the supplied dictionary key. + /// public IEventValueObservation ToObservation(string type) { var e = new EventValueObservation(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonEvents.g.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonEvents.g.cs index 93ae9c4bd..fa114e8d2 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonEvents.g.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonEvents.g.cs @@ -11,8 +11,18 @@ namespace MTConnect.Streams.Json { + /// + /// cppagent-style JSON representation of the EVENT-category observations in a + /// stream. Every MTConnect event type is exposed as three typed collections — + /// one each for the VALUE, DATA_SET, and TABLE representations — so the + /// serialized object shape matches the C++ reference agent's output. + /// public class JsonEvents { + /// + /// Materializes every typed collection into a single flat list of + /// , restoring each observation's MTConnect type. + /// [JsonIgnore] public List Observations { @@ -607,1469 +617,3229 @@ public List Observations return l; } } + /// + /// The ActivationCount events reported with the scalar VALUE representation. + /// Accumulation of the number of times a function has attempted to, or is planned to attempt to, activate or be performed. + /// [JsonPropertyName("ActivationCount")] public IEnumerable ActivationCount { get; set; } + /// + /// The ActivationCount events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ActivationCountDataSet")] public IEnumerable ActivationCountDataSet { get; set; } + /// + /// The ActivationCount events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ActivationCountTable")] public IEnumerable ActivationCountTable { get; set; } + /// + /// The ActiveAxes events reported with the scalar VALUE representation. + /// Set of axes currently associated with a Path or Controller. + /// [JsonPropertyName("ActiveAxes")] public IEnumerable ActiveAxes { get; set; } + /// + /// The ActiveAxes events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ActiveAxesDataSet")] public IEnumerable ActiveAxesDataSet { get; set; } + /// + /// The ActiveAxes events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ActiveAxesTable")] public IEnumerable ActiveAxesTable { get; set; } + /// + /// The ActivePowerSource events reported with the scalar VALUE representation. + /// Active energy source for the Component. + /// [JsonPropertyName("ActivePowerSource")] public IEnumerable ActivePowerSource { get; set; } + /// + /// The ActivePowerSource events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ActivePowerSourceDataSet")] public IEnumerable ActivePowerSourceDataSet { get; set; } + /// + /// The ActivePowerSource events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ActivePowerSourceTable")] public IEnumerable ActivePowerSourceTable { get; set; } + /// + /// The ActuatorState events reported with the scalar VALUE representation. + /// Operational state of an apparatus for moving or controlling a mechanism or system. + /// [JsonPropertyName("ActuatorState")] public IEnumerable ActuatorState { get; set; } + /// + /// The ActuatorState events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ActuatorStateDataSet")] public IEnumerable ActuatorStateDataSet { get; set; } + /// + /// The ActuatorState events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ActuatorStateTable")] public IEnumerable ActuatorStateTable { get; set; } + /// + /// The AdapterSoftwareVersion events reported with the scalar VALUE representation. + /// Originator’s software version of the adapter. + /// [JsonPropertyName("AdapterSoftwareVersion")] public IEnumerable AdapterSoftwareVersion { get; set; } + /// + /// The AdapterSoftwareVersion events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AdapterSoftwareVersionDataSet")] public IEnumerable AdapterSoftwareVersionDataSet { get; set; } + /// + /// The AdapterSoftwareVersion events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AdapterSoftwareVersionTable")] public IEnumerable AdapterSoftwareVersionTable { get; set; } + /// + /// The AdapterUri events reported with the scalar VALUE representation. + /// URI of the adapter. + /// [JsonPropertyName("AdapterUri")] public IEnumerable AdapterUri { get; set; } + /// + /// The AdapterUri events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AdapterUriDataSet")] public IEnumerable AdapterUriDataSet { get; set; } + /// + /// The AdapterUri events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AdapterUriTable")] public IEnumerable AdapterUriTable { get; set; } + /// + /// The Alarm events reported with the scalar VALUE representation. + /// **DEPRECATED:** Replaced with `CONDITION` category data items in Version 1.1.0. + /// [JsonPropertyName("Alarm")] public IEnumerable Alarm { get; set; } + /// + /// The Alarm events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AlarmDataSet")] public IEnumerable AlarmDataSet { get; set; } + /// + /// The Alarm events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AlarmTable")] public IEnumerable AlarmTable { get; set; } + /// + /// The AlarmLimit events reported with the scalar VALUE representation. + /// Set of limits used to trigger warning or alarm indicators.**DEPRECATED** in *Version 2.5*. Replaced by `ALARM_LIMITS`. + /// [JsonPropertyName("AlarmLimit")] public IEnumerable AlarmLimit { get; set; } + /// + /// The AlarmLimit events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AlarmLimitDataSet")] public IEnumerable AlarmLimitDataSet { get; set; } + /// + /// The AlarmLimit events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AlarmLimitTable")] public IEnumerable AlarmLimitTable { get; set; } + /// + /// The AlarmLimits events reported with the scalar VALUE representation. + /// Set of limits used to trigger warning or alarm indicators. + /// [JsonPropertyName("AlarmLimits")] public IEnumerable AlarmLimits { get; set; } + /// + /// The AlarmLimits events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AlarmLimitsDataSet")] public IEnumerable AlarmLimitsDataSet { get; set; } + /// + /// The AlarmLimits events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AlarmLimitsTable")] public IEnumerable AlarmLimitsTable { get; set; } + /// + /// The Application events reported with the scalar VALUE representation. + /// Application on a Component. + /// [JsonPropertyName("Application")] public IEnumerable Application { get; set; } + /// + /// The Application events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ApplicationDataSet")] public IEnumerable ApplicationDataSet { get; set; } + /// + /// The Application events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ApplicationTable")] public IEnumerable ApplicationTable { get; set; } + /// + /// The AssetAdded events reported with the scalar VALUE representation. + /// AssetId of the Asset that has been added. + /// [JsonPropertyName("AssetAdded")] public IEnumerable AssetAdded { get; set; } + /// + /// The AssetAdded events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AssetAddedDataSet")] public IEnumerable AssetAddedDataSet { get; set; } + /// + /// The AssetAdded events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AssetAddedTable")] public IEnumerable AssetAddedTable { get; set; } + /// + /// The AssetChanged events reported with the scalar VALUE representation. + /// AssetId of the Asset that has been changed. + /// [JsonPropertyName("AssetChanged")] public IEnumerable AssetChanged { get; set; } + /// + /// The AssetChanged events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AssetChangedDataSet")] public IEnumerable AssetChangedDataSet { get; set; } + /// + /// The AssetChanged events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AssetChangedTable")] public IEnumerable AssetChangedTable { get; set; } + /// + /// The AssetCount events reported with the scalar VALUE representation. + /// Data set of the number of Asset of a given type for a Device. + /// [JsonPropertyName("AssetCount")] public IEnumerable AssetCount { get; set; } + /// + /// The AssetCount events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AssetCountDataSet")] public IEnumerable AssetCountDataSet { get; set; } + /// + /// The AssetCount events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AssetCountTable")] public IEnumerable AssetCountTable { get; set; } + /// + /// The AssetRemoved events reported with the scalar VALUE representation. + /// AssetId of the Asset that has been removed. + /// [JsonPropertyName("AssetRemoved")] public IEnumerable AssetRemoved { get; set; } + /// + /// The AssetRemoved events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AssetRemovedDataSet")] public IEnumerable AssetRemovedDataSet { get; set; } + /// + /// The AssetRemoved events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AssetRemovedTable")] public IEnumerable AssetRemovedTable { get; set; } + /// + /// The AssociatedAssetId events reported with the scalar VALUE representation. + /// AssetId of the Assets associated with a Component. + /// [JsonPropertyName("AssociatedAssetId")] public IEnumerable AssociatedAssetId { get; set; } + /// + /// The AssociatedAssetId events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AssociatedAssetIdDataSet")] public IEnumerable AssociatedAssetIdDataSet { get; set; } + /// + /// The AssociatedAssetId events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AssociatedAssetIdTable")] public IEnumerable AssociatedAssetIdTable { get; set; } + /// + /// The Availability events reported with the scalar VALUE representation. + /// Agent's ability to communicate with the data source. + /// [JsonPropertyName("Availability")] public IEnumerable Availability { get; set; } + /// + /// The Availability events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AvailabilityDataSet")] public IEnumerable AvailabilityDataSet { get; set; } + /// + /// The Availability events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AvailabilityTable")] public IEnumerable AvailabilityTable { get; set; } + /// + /// The AxisCoupling events reported with the scalar VALUE representation. + /// Describes the way the axes will be associated to each other. This is used in conjunction with `COUPLED_AXES` to indicate the way they are interacting. + /// [JsonPropertyName("AxisCoupling")] public IEnumerable AxisCoupling { get; set; } + /// + /// The AxisCoupling events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AxisCouplingDataSet")] public IEnumerable AxisCouplingDataSet { get; set; } + /// + /// The AxisCoupling events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AxisCouplingTable")] public IEnumerable AxisCouplingTable { get; set; } + /// + /// The AxisFeedrateOverride events reported with the scalar VALUE representation. + /// Value of a signal or calculation issued to adjust the feedrate of an individual linear type axis. + /// [JsonPropertyName("AxisFeedrateOverride")] public IEnumerable AxisFeedrateOverride { get; set; } + /// + /// The AxisFeedrateOverride events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AxisFeedrateOverrideDataSet")] public IEnumerable AxisFeedrateOverrideDataSet { get; set; } + /// + /// The AxisFeedrateOverride events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AxisFeedrateOverrideTable")] public IEnumerable AxisFeedrateOverrideTable { get; set; } + /// + /// The AxisInterlock events reported with the scalar VALUE representation. + /// State of the axis lockout function when power has been removed and the axis is allowed to move freely. + /// [JsonPropertyName("AxisInterlock")] public IEnumerable AxisInterlock { get; set; } + /// + /// The AxisInterlock events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AxisInterlockDataSet")] public IEnumerable AxisInterlockDataSet { get; set; } + /// + /// The AxisInterlock events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AxisInterlockTable")] public IEnumerable AxisInterlockTable { get; set; } + /// + /// The AxisState events reported with the scalar VALUE representation. + /// State of a Linear or Rotary component representing an axis. + /// [JsonPropertyName("AxisState")] public IEnumerable AxisState { get; set; } + /// + /// The AxisState events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AxisStateDataSet")] public IEnumerable AxisStateDataSet { get; set; } + /// + /// The AxisState events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AxisStateTable")] public IEnumerable AxisStateTable { get; set; } + /// + /// The BatteryState events reported with the scalar VALUE representation. + /// Present status of the battery. + /// [JsonPropertyName("BatteryState")] public IEnumerable BatteryState { get; set; } + /// + /// The BatteryState events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("BatteryStateDataSet")] public IEnumerable BatteryStateDataSet { get; set; } + /// + /// The BatteryState events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("BatteryStateTable")] public IEnumerable BatteryStateTable { get; set; } + /// + /// The BindingState events reported with the scalar VALUE representation. + /// State of the binding process when Component participates in a task as a collaborator + /// [JsonPropertyName("BindingState")] public IEnumerable BindingState { get; set; } + /// + /// The BindingState events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("BindingStateDataSet")] public IEnumerable BindingStateDataSet { get; set; } + /// + /// The BindingState events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("BindingStateTable")] public IEnumerable BindingStateTable { get; set; } + /// + /// The Block events reported with the scalar VALUE representation. + /// Line of code or command being executed by a Controller entity. + /// [JsonPropertyName("Block")] public IEnumerable Block { get; set; } + /// + /// The Block events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("BlockDataSet")] public IEnumerable BlockDataSet { get; set; } + /// + /// The Block events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("BlockTable")] public IEnumerable BlockTable { get; set; } + /// + /// The BlockCount events reported with the scalar VALUE representation. + /// Total count of the number of blocks of program code that have been executed since execution started. + /// [JsonPropertyName("BlockCount")] public IEnumerable BlockCount { get; set; } + /// + /// The BlockCount events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("BlockCountDataSet")] public IEnumerable BlockCountDataSet { get; set; } + /// + /// The BlockCount events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("BlockCountTable")] public IEnumerable BlockCountTable { get; set; } + /// + /// The CharacteristicPersistentId events reported with the scalar VALUE representation. + /// UUID of the characteristic. + /// [JsonPropertyName("CharacteristicPersistentId")] public IEnumerable CharacteristicPersistentId { get; set; } + /// + /// The CharacteristicPersistentId events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("CharacteristicPersistentIdDataSet")] public IEnumerable CharacteristicPersistentIdDataSet { get; set; } + /// + /// The CharacteristicPersistentId events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("CharacteristicPersistentIdTable")] public IEnumerable CharacteristicPersistentIdTable { get; set; } + /// + /// The CharacteristicStatus events reported with the scalar VALUE representation. + /// Pass/fail result of the measurement. + /// [JsonPropertyName("CharacteristicStatus")] public IEnumerable CharacteristicStatus { get; set; } + /// + /// The CharacteristicStatus events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("CharacteristicStatusDataSet")] public IEnumerable CharacteristicStatusDataSet { get; set; } + /// + /// The CharacteristicStatus events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("CharacteristicStatusTable")] public IEnumerable CharacteristicStatusTable { get; set; } + /// + /// The ChuckInterlock events reported with the scalar VALUE representation. + /// State of an interlock function or control logic state intended to prevent the associated Chuck component from being operated. + /// [JsonPropertyName("ChuckInterlock")] public IEnumerable ChuckInterlock { get; set; } + /// + /// The ChuckInterlock events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ChuckInterlockDataSet")] public IEnumerable ChuckInterlockDataSet { get; set; } + /// + /// The ChuckInterlock events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ChuckInterlockTable")] public IEnumerable ChuckInterlockTable { get; set; } + /// + /// The ChuckState events reported with the scalar VALUE representation. + /// Operating state of a mechanism that holds a part or stock material during a manufacturing process. It may also represent a mechanism that holds any other mechanism in place within a piece of equipment. + /// [JsonPropertyName("ChuckState")] public IEnumerable ChuckState { get; set; } + /// + /// The ChuckState events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ChuckStateDataSet")] public IEnumerable ChuckStateDataSet { get; set; } + /// + /// The ChuckState events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ChuckStateTable")] public IEnumerable ChuckStateTable { get; set; } + /// + /// The ClockTime events reported with the scalar VALUE representation. + /// Time provided by a timing device at a specific point in time. + /// [JsonPropertyName("ClockTime")] public IEnumerable ClockTime { get; set; } + /// + /// The ClockTime events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ClockTimeDataSet")] public IEnumerable ClockTimeDataSet { get; set; } + /// + /// The ClockTime events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ClockTimeTable")] public IEnumerable ClockTimeTable { get; set; } + /// + /// The Code events reported with the scalar VALUE representation. + /// Programmatic code being executed.**DEPRECATED** in *Version 1.1*. + /// [JsonPropertyName("Code")] public IEnumerable Code { get; set; } + /// + /// The Code events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("CodeDataSet")] public IEnumerable CodeDataSet { get; set; } + /// + /// The Code events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("CodeTable")] public IEnumerable CodeTable { get; set; } + /// + /// The ComponentData events reported with the scalar VALUE representation. + /// Event that represents a Component where the EntryDefinition identifies the Component and the CellDefinitions define the Component's observed DataItems. + /// [JsonPropertyName("ComponentData")] public IEnumerable ComponentData { get; set; } + /// + /// The ComponentData events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ComponentDataDataSet")] public IEnumerable ComponentDataDataSet { get; set; } + /// + /// The ComponentData events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ComponentDataTable")] public IEnumerable ComponentDataTable { get; set; } + /// + /// The CompositionState events reported with the scalar VALUE representation. + /// Operating state of a mechanism represented by a Composition entity. + /// [JsonPropertyName("CompositionState")] public IEnumerable CompositionState { get; set; } + /// + /// The CompositionState events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("CompositionStateDataSet")] public IEnumerable CompositionStateDataSet { get; set; } + /// + /// The CompositionState events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("CompositionStateTable")] public IEnumerable CompositionStateTable { get; set; } + /// + /// The ConnectionStatus events reported with the scalar VALUE representation. + /// Status of the connection between an adapter and an agent. + /// [JsonPropertyName("ConnectionStatus")] public IEnumerable ConnectionStatus { get; set; } + /// + /// The ConnectionStatus events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ConnectionStatusDataSet")] public IEnumerable ConnectionStatusDataSet { get; set; } + /// + /// The ConnectionStatus events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ConnectionStatusTable")] public IEnumerable ConnectionStatusTable { get; set; } + /// + /// The ControlLimit events reported with the scalar VALUE representation. + /// Set of limits used to indicate whether a process variable is stable and in control.**DEPRECATED** in *Version 2.5*. Replaced by `CONTROL_LIMITS`. + /// [JsonPropertyName("ControlLimit")] public IEnumerable ControlLimit { get; set; } + /// + /// The ControlLimit events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ControlLimitDataSet")] public IEnumerable ControlLimitDataSet { get; set; } + /// + /// The ControlLimit events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ControlLimitTable")] public IEnumerable ControlLimitTable { get; set; } + /// + /// The ControlLimits events reported with the scalar VALUE representation. + /// Set of limits used to indicate whether a process variable is stable and in control. + /// [JsonPropertyName("ControlLimits")] public IEnumerable ControlLimits { get; set; } + /// + /// The ControlLimits events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ControlLimitsDataSet")] public IEnumerable ControlLimitsDataSet { get; set; } + /// + /// The ControlLimits events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ControlLimitsTable")] public IEnumerable ControlLimitsTable { get; set; } + /// + /// The ControllerMode events reported with the scalar VALUE representation. + /// Current mode of the Controller component. + /// [JsonPropertyName("ControllerMode")] public IEnumerable ControllerMode { get; set; } + /// + /// The ControllerMode events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ControllerModeDataSet")] public IEnumerable ControllerModeDataSet { get; set; } + /// + /// The ControllerMode events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ControllerModeTable")] public IEnumerable ControllerModeTable { get; set; } + /// + /// The ControllerModeOverride events reported with the scalar VALUE representation. + /// Setting or operator selection that changes the behavior of a piece of equipment. + /// [JsonPropertyName("ControllerModeOverride")] public IEnumerable ControllerModeOverride { get; set; } + /// + /// The ControllerModeOverride events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ControllerModeOverrideDataSet")] public IEnumerable ControllerModeOverrideDataSet { get; set; } + /// + /// The ControllerModeOverride events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ControllerModeOverrideTable")] public IEnumerable ControllerModeOverrideTable { get; set; } + /// + /// The CoupledAxes events reported with the scalar VALUE representation. + /// Set of associated axes. + /// [JsonPropertyName("CoupledAxes")] public IEnumerable CoupledAxes { get; set; } + /// + /// The CoupledAxes events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("CoupledAxesDataSet")] public IEnumerable CoupledAxesDataSet { get; set; } + /// + /// The CoupledAxes events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("CoupledAxesTable")] public IEnumerable CoupledAxesTable { get; set; } + /// + /// The CycleCount events reported with the scalar VALUE representation. + /// Accumulation of the number of times a cyclic function has attempted to, or is planned to attempt to execute. + /// [JsonPropertyName("CycleCount")] public IEnumerable CycleCount { get; set; } + /// + /// The CycleCount events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("CycleCountDataSet")] public IEnumerable CycleCountDataSet { get; set; } + /// + /// The CycleCount events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("CycleCountTable")] public IEnumerable CycleCountTable { get; set; } + /// + /// The DateCode events reported with the scalar VALUE representation. + /// Time and date code associated with a material or other physical item. + /// [JsonPropertyName("DateCode")] public IEnumerable DateCode { get; set; } + /// + /// The DateCode events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("DateCodeDataSet")] public IEnumerable DateCodeDataSet { get; set; } + /// + /// The DateCode events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("DateCodeTable")] public IEnumerable DateCodeTable { get; set; } + /// + /// The DeactivationCount events reported with the scalar VALUE representation. + /// Accumulation of the number of times a function has attempted to, or is planned to attempt to, deactivate or cease. + /// [JsonPropertyName("DeactivationCount")] public IEnumerable DeactivationCount { get; set; } + /// + /// The DeactivationCount events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("DeactivationCountDataSet")] public IEnumerable DeactivationCountDataSet { get; set; } + /// + /// The DeactivationCount events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("DeactivationCountTable")] public IEnumerable DeactivationCountTable { get; set; } + /// + /// The Depth events reported with the scalar VALUE representation. + /// Dimension or distance as measured downwards from the top + /// [JsonPropertyName("Depth")] public IEnumerable Depth { get; set; } + /// + /// The Depth events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("DepthDataSet")] public IEnumerable DepthDataSet { get; set; } + /// + /// The Depth events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("DepthTable")] public IEnumerable DepthTable { get; set; } + /// + /// The DeviceAdded events reported with the scalar VALUE representation. + /// UUID of new device added to an MTConnect Agent. + /// [JsonPropertyName("DeviceAdded")] public IEnumerable DeviceAdded { get; set; } + /// + /// The DeviceAdded events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("DeviceAddedDataSet")] public IEnumerable DeviceAddedDataSet { get; set; } + /// + /// The DeviceAdded events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("DeviceAddedTable")] public IEnumerable DeviceAddedTable { get; set; } + /// + /// The DeviceChanged events reported with the scalar VALUE representation. + /// UUID of the device whose metadata has changed. + /// [JsonPropertyName("DeviceChanged")] public IEnumerable DeviceChanged { get; set; } + /// + /// The DeviceChanged events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("DeviceChangedDataSet")] public IEnumerable DeviceChangedDataSet { get; set; } + /// + /// The DeviceChanged events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("DeviceChangedTable")] public IEnumerable DeviceChangedTable { get; set; } + /// + /// The DeviceRemoved events reported with the scalar VALUE representation. + /// UUID of a device removed from an MTConnect Agent. + /// [JsonPropertyName("DeviceRemoved")] public IEnumerable DeviceRemoved { get; set; } + /// + /// The DeviceRemoved events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("DeviceRemovedDataSet")] public IEnumerable DeviceRemovedDataSet { get; set; } + /// + /// The DeviceRemoved events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("DeviceRemovedTable")] public IEnumerable DeviceRemovedTable { get; set; } + /// + /// The DeviceUuid events reported with the scalar VALUE representation. + /// Identifier of another piece of equipment that is temporarily associated with a component of this piece of equipment to perform a particular function. + /// [JsonPropertyName("DeviceUuid")] public IEnumerable DeviceUuid { get; set; } + /// + /// The DeviceUuid events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("DeviceUuidDataSet")] public IEnumerable DeviceUuidDataSet { get; set; } + /// + /// The DeviceUuid events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("DeviceUuidTable")] public IEnumerable DeviceUuidTable { get; set; } + /// + /// The Direction events reported with the scalar VALUE representation. + /// Direction of motion. + /// [JsonPropertyName("Direction")] public IEnumerable Direction { get; set; } + /// + /// The Direction events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("DirectionDataSet")] public IEnumerable DirectionDataSet { get; set; } + /// + /// The Direction events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("DirectionTable")] public IEnumerable DirectionTable { get; set; } + /// + /// The DoorState events reported with the scalar VALUE representation. + /// Operational state of a Door component or composition element. + /// [JsonPropertyName("DoorState")] public IEnumerable DoorState { get; set; } + /// + /// The DoorState events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("DoorStateDataSet")] public IEnumerable DoorStateDataSet { get; set; } + /// + /// The DoorState events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("DoorStateTable")] public IEnumerable DoorStateTable { get; set; } + /// + /// The EmergencyStop events reported with the scalar VALUE representation. + /// State of the emergency stop signal for a piece of equipment, controller path, or any other component or subsystem of a piece of equipment. + /// [JsonPropertyName("EmergencyStop")] public IEnumerable EmergencyStop { get; set; } + /// + /// The EmergencyStop events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("EmergencyStopDataSet")] public IEnumerable EmergencyStopDataSet { get; set; } + /// + /// The EmergencyStop events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("EmergencyStopTable")] public IEnumerable EmergencyStopTable { get; set; } + /// + /// The EndOfBar events reported with the scalar VALUE representation. + /// Indication of whether the end of a piece of bar stock being feed by a bar feeder has been reached. + /// [JsonPropertyName("EndOfBar")] public IEnumerable EndOfBar { get; set; } + /// + /// The EndOfBar events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("EndOfBarDataSet")] public IEnumerable EndOfBarDataSet { get; set; } + /// + /// The EndOfBar events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("EndOfBarTable")] public IEnumerable EndOfBarTable { get; set; } + /// + /// The EquipmentMode events reported with the scalar VALUE representation. + /// Indication that a piece of equipment, or a sub-part of a piece of equipment, is performing specific types of activities. + /// [JsonPropertyName("EquipmentMode")] public IEnumerable EquipmentMode { get; set; } + /// + /// The EquipmentMode events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("EquipmentModeDataSet")] public IEnumerable EquipmentModeDataSet { get; set; } + /// + /// The EquipmentMode events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("EquipmentModeTable")] public IEnumerable EquipmentModeTable { get; set; } + /// + /// The Execution events reported with the scalar VALUE representation. + /// Operating state of a Component. + /// [JsonPropertyName("Execution")] public IEnumerable Execution { get; set; } + /// + /// The Execution events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ExecutionDataSet")] public IEnumerable ExecutionDataSet { get; set; } + /// + /// The Execution events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ExecutionTable")] public IEnumerable ExecutionTable { get; set; } + /// + /// The FeatureMeasurement events reported with the scalar VALUE representation. + /// Assessing elements of a feature. + /// [JsonPropertyName("FeatureMeasurement")] public IEnumerable FeatureMeasurement { get; set; } + /// + /// The FeatureMeasurement events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("FeatureMeasurementDataSet")] public IEnumerable FeatureMeasurementDataSet { get; set; } + /// + /// The FeatureMeasurement events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("FeatureMeasurementTable")] public IEnumerable FeatureMeasurementTable { get; set; } + /// + /// The Firmware events reported with the scalar VALUE representation. + /// Embedded software of a Component. + /// [JsonPropertyName("Firmware")] public IEnumerable Firmware { get; set; } + /// + /// The Firmware events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("FirmwareDataSet")] public IEnumerable FirmwareDataSet { get; set; } + /// + /// The Firmware events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("FirmwareTable")] public IEnumerable FirmwareTable { get; set; } + /// + /// The FixtureAssetId events reported with the scalar VALUE representation. + /// AssetId of the Fixture that is associated with a Component + /// [JsonPropertyName("FixtureAssetId")] public IEnumerable FixtureAssetId { get; set; } + /// + /// The FixtureAssetId events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("FixtureAssetIdDataSet")] public IEnumerable FixtureAssetIdDataSet { get; set; } + /// + /// The FixtureAssetId events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("FixtureAssetIdTable")] public IEnumerable FixtureAssetIdTable { get; set; } + /// + /// The FixtureId events reported with the scalar VALUE representation. + /// Identifier for the current workholding or part clamp in use by a piece of equipment. + /// [JsonPropertyName("FixtureId")] public IEnumerable FixtureId { get; set; } + /// + /// The FixtureId events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("FixtureIdDataSet")] public IEnumerable FixtureIdDataSet { get; set; } + /// + /// The FixtureId events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("FixtureIdTable")] public IEnumerable FixtureIdTable { get; set; } + /// + /// The FunctionalMode events reported with the scalar VALUE representation. + /// Current intended production status of the Component. + /// [JsonPropertyName("FunctionalMode")] public IEnumerable FunctionalMode { get; set; } + /// + /// The FunctionalMode events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("FunctionalModeDataSet")] public IEnumerable FunctionalModeDataSet { get; set; } + /// + /// The FunctionalMode events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("FunctionalModeTable")] public IEnumerable FunctionalModeTable { get; set; } + /// + /// The Hardness events reported with the scalar VALUE representation. + /// Hardness of a material. + /// [JsonPropertyName("Hardness")] public IEnumerable Hardness { get; set; } + /// + /// The Hardness events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("HardnessDataSet")] public IEnumerable HardnessDataSet { get; set; } + /// + /// The Hardness events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("HardnessTable")] public IEnumerable HardnessTable { get; set; } + /// + /// The Hardware events reported with the scalar VALUE representation. + /// Hardware of a Component. + /// [JsonPropertyName("Hardware")] public IEnumerable Hardware { get; set; } + /// + /// The Hardware events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("HardwareDataSet")] public IEnumerable HardwareDataSet { get; set; } + /// + /// The Hardware events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("HardwareTable")] public IEnumerable HardwareTable { get; set; } + /// + /// The HostName events reported with the scalar VALUE representation. + /// Name of the host computer supplying data. + /// [JsonPropertyName("HostName")] public IEnumerable HostName { get; set; } + /// + /// The HostName events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("HostNameDataSet")] public IEnumerable HostNameDataSet { get; set; } + /// + /// The HostName events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("HostNameTable")] public IEnumerable HostNameTable { get; set; } + /// + /// The LeakDetect events reported with the scalar VALUE representation. + /// Indication designating whether a leak has been detected. + /// [JsonPropertyName("LeakDetect")] public IEnumerable LeakDetect { get; set; } + /// + /// The LeakDetect events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("LeakDetectDataSet")] public IEnumerable LeakDetectDataSet { get; set; } + /// + /// The LeakDetect events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("LeakDetectTable")] public IEnumerable LeakDetectTable { get; set; } + /// + /// The Library events reported with the scalar VALUE representation. + /// Software library on a Component + /// [JsonPropertyName("Library")] public IEnumerable Library { get; set; } + /// + /// The Library events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("LibraryDataSet")] public IEnumerable LibraryDataSet { get; set; } + /// + /// The Library events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("LibraryTable")] public IEnumerable LibraryTable { get; set; } + /// + /// The Line events reported with the scalar VALUE representation. + /// Current line of code being executed.**DEPRECATED** in *Version 1.4.0*. + /// [JsonPropertyName("Line")] public IEnumerable Line { get; set; } + /// + /// The Line events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("LineDataSet")] public IEnumerable LineDataSet { get; set; } + /// + /// The Line events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("LineTable")] public IEnumerable LineTable { get; set; } + /// + /// The LineLabel events reported with the scalar VALUE representation. + /// Identifier for a Block of code in a Program. + /// [JsonPropertyName("LineLabel")] public IEnumerable LineLabel { get; set; } + /// + /// The LineLabel events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("LineLabelDataSet")] public IEnumerable LineLabelDataSet { get; set; } + /// + /// The LineLabel events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("LineLabelTable")] public IEnumerable LineLabelTable { get; set; } + /// + /// The LineNumber events reported with the scalar VALUE representation. + /// Position of a block of program code within a control program. + /// [JsonPropertyName("LineNumber")] public IEnumerable LineNumber { get; set; } + /// + /// The LineNumber events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("LineNumberDataSet")] public IEnumerable LineNumberDataSet { get; set; } + /// + /// The LineNumber events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("LineNumberTable")] public IEnumerable LineNumberTable { get; set; } + /// + /// The LoadCount events reported with the scalar VALUE representation. + /// Accumulation of the number of times an operation has attempted to, or is planned to attempt to, load materials, parts, or other items. + /// [JsonPropertyName("LoadCount")] public IEnumerable LoadCount { get; set; } + /// + /// The LoadCount events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("LoadCountDataSet")] public IEnumerable LoadCountDataSet { get; set; } + /// + /// The LoadCount events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("LoadCountTable")] public IEnumerable LoadCountTable { get; set; } + /// + /// The LocationAddress events reported with the scalar VALUE representation. + /// Structured information that allows the unambiguous determination of an object for purposes of identification and location. ISO 19160-4:2017 + /// [JsonPropertyName("LocationAddress")] public IEnumerable LocationAddress { get; set; } + /// + /// The LocationAddress events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("LocationAddressDataSet")] public IEnumerable LocationAddressDataSet { get; set; } + /// + /// The LocationAddress events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("LocationAddressTable")] public IEnumerable LocationAddressTable { get; set; } + /// + /// The LocationNarrative events reported with the scalar VALUE representation. + /// Textual description of the location of an object or activity. + /// [JsonPropertyName("LocationNarrative")] public IEnumerable LocationNarrative { get; set; } + /// + /// The LocationNarrative events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("LocationNarrativeDataSet")] public IEnumerable LocationNarrativeDataSet { get; set; } + /// + /// The LocationNarrative events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("LocationNarrativeTable")] public IEnumerable LocationNarrativeTable { get; set; } + /// + /// The LocationSpatialGeographic events reported with the scalar VALUE representation. + /// Absolute geographic location defined by two coordinates, longitude and latitude and an elevation. + /// [JsonPropertyName("LocationSpatialGeographic")] public IEnumerable LocationSpatialGeographic { get; set; } + /// + /// The LocationSpatialGeographic events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("LocationSpatialGeographicDataSet")] public IEnumerable LocationSpatialGeographicDataSet { get; set; } + /// + /// The LocationSpatialGeographic events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("LocationSpatialGeographicTable")] public IEnumerable LocationSpatialGeographicTable { get; set; } + /// + /// The LockState events reported with the scalar VALUE representation. + /// State or operating mode of a Lock. + /// [JsonPropertyName("LockState")] public IEnumerable LockState { get; set; } + /// + /// The LockState events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("LockStateDataSet")] public IEnumerable LockStateDataSet { get; set; } + /// + /// The LockState events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("LockStateTable")] public IEnumerable LockStateTable { get; set; } + /// + /// The MaintenanceList events reported with the scalar VALUE representation. + /// Actions or activities to be performed in support of a piece of equipment. + /// [JsonPropertyName("MaintenanceList")] public IEnumerable MaintenanceList { get; set; } + /// + /// The MaintenanceList events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("MaintenanceListDataSet")] public IEnumerable MaintenanceListDataSet { get; set; } + /// + /// The MaintenanceList events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("MaintenanceListTable")] public IEnumerable MaintenanceListTable { get; set; } + /// + /// The Material events reported with the scalar VALUE representation. + /// Identifier of a material used or consumed in the manufacturing process + /// [JsonPropertyName("Material")] public IEnumerable Material { get; set; } + /// + /// The Material events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("MaterialDataSet")] public IEnumerable MaterialDataSet { get; set; } + /// + /// The Material events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("MaterialTable")] public IEnumerable MaterialTable { get; set; } + /// + /// The MaterialLayer events reported with the scalar VALUE representation. + /// Identifies the layers of material applied to a part or product as part of an additive manufacturing process. + /// [JsonPropertyName("MaterialLayer")] public IEnumerable MaterialLayer { get; set; } + /// + /// The MaterialLayer events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("MaterialLayerDataSet")] public IEnumerable MaterialLayerDataSet { get; set; } + /// + /// The MaterialLayer events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("MaterialLayerTable")] public IEnumerable MaterialLayerTable { get; set; } + /// + /// The MeasurementType events reported with the scalar VALUE representation. + /// Class of measurement being performed. QIF 3:2018 Section 6.3 + /// [JsonPropertyName("MeasurementType")] public IEnumerable MeasurementType { get; set; } + /// + /// The MeasurementType events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("MeasurementTypeDataSet")] public IEnumerable MeasurementTypeDataSet { get; set; } + /// + /// The MeasurementType events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("MeasurementTypeTable")] public IEnumerable MeasurementTypeTable { get; set; } + /// + /// The MeasurementUnits events reported with the scalar VALUE representation. + /// Engineering units of the measurement. + /// [JsonPropertyName("MeasurementUnits")] public IEnumerable MeasurementUnits { get; set; } + /// + /// The MeasurementUnits events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("MeasurementUnitsDataSet")] public IEnumerable MeasurementUnitsDataSet { get; set; } + /// + /// The MeasurementUnits events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("MeasurementUnitsTable")] public IEnumerable MeasurementUnitsTable { get; set; } + /// + /// The MeasurementValue events reported with the scalar VALUE representation. + /// Measurement based on the measurement type. + /// [JsonPropertyName("MeasurementValue")] public IEnumerable MeasurementValue { get; set; } + /// + /// The MeasurementValue events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("MeasurementValueDataSet")] public IEnumerable MeasurementValueDataSet { get; set; } + /// + /// The MeasurementValue events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("MeasurementValueTable")] public IEnumerable MeasurementValueTable { get; set; } + /// + /// The Message events reported with the scalar VALUE representation. + /// Information to be transferred from a piece of equipment to a client software application. + /// [JsonPropertyName("Message")] public IEnumerable Message { get; set; } + /// + /// The Message events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("MessageDataSet")] public IEnumerable MessageDataSet { get; set; } + /// + /// The Message events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("MessageTable")] public IEnumerable MessageTable { get; set; } + /// + /// The MTConnectVersion events reported with the scalar VALUE representation. + /// Reference version of the MTConnect Standard supported by the adapter. + /// [JsonPropertyName("MTConnectVersion")] public IEnumerable MTConnectVersion { get; set; } + /// + /// The MTConnectVersion events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("MTConnectVersionDataSet")] public IEnumerable MTConnectVersionDataSet { get; set; } + /// + /// The MTConnectVersion events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("MTConnectVersionTable")] public IEnumerable MTConnectVersionTable { get; set; } + /// + /// The Network events reported with the scalar VALUE representation. + /// Network details of a Component. + /// [JsonPropertyName("Network")] public IEnumerable Network { get; set; } + /// + /// The Network events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("NetworkDataSet")] public IEnumerable NetworkDataSet { get; set; } + /// + /// The Network events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("NetworkTable")] public IEnumerable NetworkTable { get; set; } + /// + /// The NetworkPort events reported with the scalar VALUE representation. + /// Number of the TCP/IP or UDP/IP port for the connection endpoint. + /// [JsonPropertyName("NetworkPort")] public IEnumerable NetworkPort { get; set; } + /// + /// The NetworkPort events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("NetworkPortDataSet")] public IEnumerable NetworkPortDataSet { get; set; } + /// + /// The NetworkPort events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("NetworkPortTable")] public IEnumerable NetworkPortTable { get; set; } + /// + /// The OperatingMode events reported with the scalar VALUE representation. + /// State of Component or Composition that describes the automatic or manual operation of the entity. + /// [JsonPropertyName("OperatingMode")] public IEnumerable OperatingMode { get; set; } + /// + /// The OperatingMode events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("OperatingModeDataSet")] public IEnumerable OperatingModeDataSet { get; set; } + /// + /// The OperatingMode events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("OperatingModeTable")] public IEnumerable OperatingModeTable { get; set; } + /// + /// The OperatingSystem events reported with the scalar VALUE representation. + /// Operating System (OS) of a Component. + /// [JsonPropertyName("OperatingSystem")] public IEnumerable OperatingSystem { get; set; } + /// + /// The OperatingSystem events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("OperatingSystemDataSet")] public IEnumerable OperatingSystemDataSet { get; set; } + /// + /// The OperatingSystem events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("OperatingSystemTable")] public IEnumerable OperatingSystemTable { get; set; } + /// + /// The OperatorId events reported with the scalar VALUE representation. + /// Identifier of the person currently responsible for operating the piece of equipment. + /// [JsonPropertyName("OperatorId")] public IEnumerable OperatorId { get; set; } + /// + /// The OperatorId events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("OperatorIdDataSet")] public IEnumerable OperatorIdDataSet { get; set; } + /// + /// The OperatorId events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("OperatorIdTable")] public IEnumerable OperatorIdTable { get; set; } + /// + /// The PalletId events reported with the scalar VALUE representation. + /// Identifier for a pallet. + /// [JsonPropertyName("PalletId")] public IEnumerable PalletId { get; set; } + /// + /// The PalletId events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PalletIdDataSet")] public IEnumerable PalletIdDataSet { get; set; } + /// + /// The PalletId events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PalletIdTable")] public IEnumerable PalletIdTable { get; set; } + /// + /// The PartCount events reported with the scalar VALUE representation. + /// Aggregate count of parts. + /// [JsonPropertyName("PartCount")] public IEnumerable PartCount { get; set; } + /// + /// The PartCount events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PartCountDataSet")] public IEnumerable PartCountDataSet { get; set; } + /// + /// The PartCount events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PartCountTable")] public IEnumerable PartCountTable { get; set; } + /// + /// The PartCountType events reported with the scalar VALUE representation. + /// Interpretation of `PART_COUNT`. + /// [JsonPropertyName("PartCountType")] public IEnumerable PartCountType { get; set; } + /// + /// The PartCountType events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PartCountTypeDataSet")] public IEnumerable PartCountTypeDataSet { get; set; } + /// + /// The PartCountType events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PartCountTypeTable")] public IEnumerable PartCountTypeTable { get; set; } + /// + /// The PartDetect events reported with the scalar VALUE representation. + /// Indication designating whether a part or work piece has been detected or is present. + /// [JsonPropertyName("PartDetect")] public IEnumerable PartDetect { get; set; } + /// + /// The PartDetect events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PartDetectDataSet")] public IEnumerable PartDetectDataSet { get; set; } + /// + /// The PartDetect events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PartDetectTable")] public IEnumerable PartDetectTable { get; set; } + /// + /// The PartGroupId events reported with the scalar VALUE representation. + /// Identifier given to a collection of individual parts. + /// [JsonPropertyName("PartGroupId")] public IEnumerable PartGroupId { get; set; } + /// + /// The PartGroupId events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PartGroupIdDataSet")] public IEnumerable PartGroupIdDataSet { get; set; } + /// + /// The PartGroupId events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PartGroupIdTable")] public IEnumerable PartGroupIdTable { get; set; } + /// + /// The PartId events reported with the scalar VALUE representation. + /// Identifier of a part in a manufacturing operation. + /// [JsonPropertyName("PartId")] public IEnumerable PartId { get; set; } + /// + /// The PartId events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PartIdDataSet")] public IEnumerable PartIdDataSet { get; set; } + /// + /// The PartId events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PartIdTable")] public IEnumerable PartIdTable { get; set; } + /// + /// The PartIndex events reported with the scalar VALUE representation. + /// Sequence of a part in a group of parts. + /// [JsonPropertyName("PartIndex")] public IEnumerable PartIndex { get; set; } + /// + /// The PartIndex events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PartIndexDataSet")] public IEnumerable PartIndexDataSet { get; set; } + /// + /// The PartIndex events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PartIndexTable")] public IEnumerable PartIndexTable { get; set; } + /// + /// The PartKindId events reported with the scalar VALUE representation. + /// Identifier given to link the individual occurrence to a class of parts, typically distinguished by a particular part design. + /// [JsonPropertyName("PartKindId")] public IEnumerable PartKindId { get; set; } + /// + /// The PartKindId events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PartKindIdDataSet")] public IEnumerable PartKindIdDataSet { get; set; } + /// + /// The PartKindId events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PartKindIdTable")] public IEnumerable PartKindIdTable { get; set; } + /// + /// The PartNumber events reported with the scalar VALUE representation. + /// Identifier of a part or product moving through the manufacturing process.**DEPRECATED** in *Version 1.7*. `PART_NUMBER` is now a `subType` of `PART_KIND_ID`. + /// [JsonPropertyName("PartNumber")] public IEnumerable PartNumber { get; set; } + /// + /// The PartNumber events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PartNumberDataSet")] public IEnumerable PartNumberDataSet { get; set; } + /// + /// The PartNumber events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PartNumberTable")] public IEnumerable PartNumberTable { get; set; } + /// + /// The PartProcessingState events reported with the scalar VALUE representation. + /// Particular condition of the part occurrence at a specific time. + /// [JsonPropertyName("PartProcessingState")] public IEnumerable PartProcessingState { get; set; } + /// + /// The PartProcessingState events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PartProcessingStateDataSet")] public IEnumerable PartProcessingStateDataSet { get; set; } + /// + /// The PartProcessingState events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PartProcessingStateTable")] public IEnumerable PartProcessingStateTable { get; set; } + /// + /// The PartStatus events reported with the scalar VALUE representation. + /// State or condition of a part. + /// [JsonPropertyName("PartStatus")] public IEnumerable PartStatus { get; set; } + /// + /// The PartStatus events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PartStatusDataSet")] public IEnumerable PartStatusDataSet { get; set; } + /// + /// The PartStatus events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PartStatusTable")] public IEnumerable PartStatusTable { get; set; } + /// + /// The PartUniqueId events reported with the scalar VALUE representation. + /// Identifier given to a distinguishable, individual part. + /// [JsonPropertyName("PartUniqueId")] public IEnumerable PartUniqueId { get; set; } + /// + /// The PartUniqueId events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PartUniqueIdDataSet")] public IEnumerable PartUniqueIdDataSet { get; set; } + /// + /// The PartUniqueId events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PartUniqueIdTable")] public IEnumerable PartUniqueIdTable { get; set; } + /// + /// The PathFeedrateOverride events reported with the scalar VALUE representation. + /// Value of a signal or calculation issued to adjust the feedrate for the axes associated with a Path component that may represent a single axis or the coordinated movement of multiple axes. + /// [JsonPropertyName("PathFeedrateOverride")] public IEnumerable PathFeedrateOverride { get; set; } + /// + /// The PathFeedrateOverride events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PathFeedrateOverrideDataSet")] public IEnumerable PathFeedrateOverrideDataSet { get; set; } + /// + /// The PathFeedrateOverride events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PathFeedrateOverrideTable")] public IEnumerable PathFeedrateOverrideTable { get; set; } + /// + /// The PathMode events reported with the scalar VALUE representation. + /// Describes the operational relationship between a Path entity and another Path entity for pieces of equipment comprised of multiple logical groupings of controlled axes or other logical operations. + /// [JsonPropertyName("PathMode")] public IEnumerable PathMode { get; set; } + /// + /// The PathMode events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PathModeDataSet")] public IEnumerable PathModeDataSet { get; set; } + /// + /// The PathMode events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PathModeTable")] public IEnumerable PathModeTable { get; set; } + /// + /// The PowerState events reported with the scalar VALUE representation. + /// Indication of the status of the source of energy for an entity to allow it to perform its intended function or the state of an enabling signal providing permission for the entity to perform its functions. + /// [JsonPropertyName("PowerState")] public IEnumerable PowerState { get; set; } + /// + /// The PowerState events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PowerStateDataSet")] public IEnumerable PowerStateDataSet { get; set; } + /// + /// The PowerState events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PowerStateTable")] public IEnumerable PowerStateTable { get; set; } + /// + /// The PowerStatus events reported with the scalar VALUE representation. + /// Status of the Component.**DEPRECATED** in *Version 1.1.0*. + /// [JsonPropertyName("PowerStatus")] public IEnumerable PowerStatus { get; set; } + /// + /// The PowerStatus events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PowerStatusDataSet")] public IEnumerable PowerStatusDataSet { get; set; } + /// + /// The PowerStatus events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PowerStatusTable")] public IEnumerable PowerStatusTable { get; set; } + /// + /// The ProcessAggregateId events reported with the scalar VALUE representation. + /// Identifier given to link the individual occurrence to a group of related occurrences, such as a process step in a process plan. + /// [JsonPropertyName("ProcessAggregateId")] public IEnumerable ProcessAggregateId { get; set; } + /// + /// The ProcessAggregateId events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ProcessAggregateIdDataSet")] public IEnumerable ProcessAggregateIdDataSet { get; set; } + /// + /// The ProcessAggregateId events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ProcessAggregateIdTable")] public IEnumerable ProcessAggregateIdTable { get; set; } + /// + /// The ProcessKindId events reported with the scalar VALUE representation. + /// Identifier given to link the individual occurrence to a class of processes or process definition. + /// [JsonPropertyName("ProcessKindId")] public IEnumerable ProcessKindId { get; set; } + /// + /// The ProcessKindId events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ProcessKindIdDataSet")] public IEnumerable ProcessKindIdDataSet { get; set; } + /// + /// The ProcessKindId events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ProcessKindIdTable")] public IEnumerable ProcessKindIdTable { get; set; } + /// + /// The ProcessOccurrenceId events reported with the scalar VALUE representation. + /// Identifier of a process being executed by the device. + /// [JsonPropertyName("ProcessOccurrenceId")] public IEnumerable ProcessOccurrenceId { get; set; } + /// + /// The ProcessOccurrenceId events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ProcessOccurrenceIdDataSet")] public IEnumerable ProcessOccurrenceIdDataSet { get; set; } + /// + /// The ProcessOccurrenceId events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ProcessOccurrenceIdTable")] public IEnumerable ProcessOccurrenceIdTable { get; set; } + /// + /// The ProcessState events reported with the scalar VALUE representation. + /// Particular condition of the process occurrence at a specific time. + /// [JsonPropertyName("ProcessState")] public IEnumerable ProcessState { get; set; } + /// + /// The ProcessState events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ProcessStateDataSet")] public IEnumerable ProcessStateDataSet { get; set; } + /// + /// The ProcessState events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ProcessStateTable")] public IEnumerable ProcessStateTable { get; set; } + /// + /// The ProcessTime events reported with the scalar VALUE representation. + /// Time and date associated with an activity or event. + /// [JsonPropertyName("ProcessTime")] public IEnumerable ProcessTime { get; set; } + /// + /// The ProcessTime events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ProcessTimeDataSet")] public IEnumerable ProcessTimeDataSet { get; set; } + /// + /// The ProcessTime events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ProcessTimeTable")] public IEnumerable ProcessTimeTable { get; set; } + /// + /// The Program events reported with the scalar VALUE representation. + /// Name of the logic or motion program being executed by the Controller component. + /// [JsonPropertyName("Program")] public IEnumerable Program { get; set; } + /// + /// The Program events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ProgramDataSet")] public IEnumerable ProgramDataSet { get; set; } + /// + /// The Program events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ProgramTable")] public IEnumerable ProgramTable { get; set; } + /// + /// The ProgramComment events reported with the scalar VALUE representation. + /// Comment or non-executable statement in the control program. + /// [JsonPropertyName("ProgramComment")] public IEnumerable ProgramComment { get; set; } + /// + /// The ProgramComment events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ProgramCommentDataSet")] public IEnumerable ProgramCommentDataSet { get; set; } + /// + /// The ProgramComment events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ProgramCommentTable")] public IEnumerable ProgramCommentTable { get; set; } + /// + /// The ProgramEdit events reported with the scalar VALUE representation. + /// Indication of the status of the Controller components program editing mode.A program may be edited while another is executed. + /// [JsonPropertyName("ProgramEdit")] public IEnumerable ProgramEdit { get; set; } + /// + /// The ProgramEdit events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ProgramEditDataSet")] public IEnumerable ProgramEditDataSet { get; set; } + /// + /// The ProgramEdit events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ProgramEditTable")] public IEnumerable ProgramEditTable { get; set; } + /// + /// The ProgramEditName events reported with the scalar VALUE representation. + /// Name of the program being edited. This is used in conjunction with ProgramEdit when in `ACTIVE` state. + /// [JsonPropertyName("ProgramEditName")] public IEnumerable ProgramEditName { get; set; } + /// + /// The ProgramEditName events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ProgramEditNameDataSet")] public IEnumerable ProgramEditNameDataSet { get; set; } + /// + /// The ProgramEditName events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ProgramEditNameTable")] public IEnumerable ProgramEditNameTable { get; set; } + /// + /// The ProgramHeader events reported with the scalar VALUE representation. + /// Non-executable header section of the control program. + /// [JsonPropertyName("ProgramHeader")] public IEnumerable ProgramHeader { get; set; } + /// + /// The ProgramHeader events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ProgramHeaderDataSet")] public IEnumerable ProgramHeaderDataSet { get; set; } + /// + /// The ProgramHeader events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ProgramHeaderTable")] public IEnumerable ProgramHeaderTable { get; set; } + /// + /// The ProgramLocation events reported with the scalar VALUE representation. + /// URI for the source file associated with Program. + /// [JsonPropertyName("ProgramLocation")] public IEnumerable ProgramLocation { get; set; } + /// + /// The ProgramLocation events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ProgramLocationDataSet")] public IEnumerable ProgramLocationDataSet { get; set; } + /// + /// The ProgramLocation events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ProgramLocationTable")] public IEnumerable ProgramLocationTable { get; set; } + /// + /// The ProgramLocationType events reported with the scalar VALUE representation. + /// Defines whether the logic or motion program defined by Program is being executed from the local memory of the controller or from an outside source. + /// [JsonPropertyName("ProgramLocationType")] public IEnumerable ProgramLocationType { get; set; } + /// + /// The ProgramLocationType events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ProgramLocationTypeDataSet")] public IEnumerable ProgramLocationTypeDataSet { get; set; } + /// + /// The ProgramLocationType events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ProgramLocationTypeTable")] public IEnumerable ProgramLocationTypeTable { get; set; } + /// + /// The ProgramNestLevel events reported with the scalar VALUE representation. + /// Indication of the nesting level within a control program that is associated with the code or instructions that is currently being executed. + /// [JsonPropertyName("ProgramNestLevel")] public IEnumerable ProgramNestLevel { get; set; } + /// + /// The ProgramNestLevel events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ProgramNestLevelDataSet")] public IEnumerable ProgramNestLevelDataSet { get; set; } + /// + /// The ProgramNestLevel events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ProgramNestLevelTable")] public IEnumerable ProgramNestLevelTable { get; set; } + /// + /// The RotaryMode events reported with the scalar VALUE representation. + /// Current operating mode for a Rotary type axis. + /// [JsonPropertyName("RotaryMode")] public IEnumerable RotaryMode { get; set; } + /// + /// The RotaryMode events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("RotaryModeDataSet")] public IEnumerable RotaryModeDataSet { get; set; } + /// + /// The RotaryMode events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("RotaryModeTable")] public IEnumerable RotaryModeTable { get; set; } + /// + /// The RotaryVelocityOverride events reported with the scalar VALUE representation. + /// Percentage change to the velocity of the programmed velocity for a Rotary axis. + /// [JsonPropertyName("RotaryVelocityOverride")] public IEnumerable RotaryVelocityOverride { get; set; } + /// + /// The RotaryVelocityOverride events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("RotaryVelocityOverrideDataSet")] public IEnumerable RotaryVelocityOverrideDataSet { get; set; } + /// + /// The RotaryVelocityOverride events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("RotaryVelocityOverrideTable")] public IEnumerable RotaryVelocityOverrideTable { get; set; } + /// + /// The Rotation events reported with the scalar VALUE representation. + /// Three space angular displacement of an object or coordinate system relative to a cartesian coordinate system. + /// [JsonPropertyName("Rotation")] public IEnumerable Rotation { get; set; } + /// + /// The Rotation events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("RotationDataSet")] public IEnumerable RotationDataSet { get; set; } + /// + /// The Rotation events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("RotationTable")] public IEnumerable RotationTable { get; set; } + /// + /// The SensorAttachment events reported with the scalar VALUE representation. + /// Attachment between a sensor and an entity. + /// [JsonPropertyName("SensorAttachment")] public IEnumerable SensorAttachment { get; set; } + /// + /// The SensorAttachment events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("SensorAttachmentDataSet")] public IEnumerable SensorAttachmentDataSet { get; set; } + /// + /// The SensorAttachment events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("SensorAttachmentTable")] public IEnumerable SensorAttachmentTable { get; set; } + /// + /// The SensorState events reported with the scalar VALUE representation. + /// Detection result of a sensor. + /// [JsonPropertyName("SensorState")] public IEnumerable SensorState { get; set; } + /// + /// The SensorState events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("SensorStateDataSet")] public IEnumerable SensorStateDataSet { get; set; } + /// + /// The SensorState events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("SensorStateTable")] public IEnumerable SensorStateTable { get; set; } + /// + /// The SerialNumber events reported with the scalar VALUE representation. + /// Serial number associated with a Component, Asset, or Device. + /// [JsonPropertyName("SerialNumber")] public IEnumerable SerialNumber { get; set; } + /// + /// The SerialNumber events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("SerialNumberDataSet")] public IEnumerable SerialNumberDataSet { get; set; } + /// + /// The SerialNumber events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("SerialNumberTable")] public IEnumerable SerialNumberTable { get; set; } + /// + /// The SpecificationLimit events reported with the scalar VALUE representation. + /// Set of limits defining a range of values designating acceptable performance for a variable.**DEPRECATED** in *Version 2.5*. Replaced by `SPECIFICATION_LIMITS`. + /// [JsonPropertyName("SpecificationLimit")] public IEnumerable SpecificationLimit { get; set; } + /// + /// The SpecificationLimit events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("SpecificationLimitDataSet")] public IEnumerable SpecificationLimitDataSet { get; set; } + /// + /// The SpecificationLimit events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("SpecificationLimitTable")] public IEnumerable SpecificationLimitTable { get; set; } + /// + /// The SpecificationLimits events reported with the scalar VALUE representation. + /// Set of limits defining a range of values designating acceptable performance for a variable. + /// [JsonPropertyName("SpecificationLimits")] public IEnumerable SpecificationLimits { get; set; } + /// + /// The SpecificationLimits events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("SpecificationLimitsDataSet")] public IEnumerable SpecificationLimitsDataSet { get; set; } + /// + /// The SpecificationLimits events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("SpecificationLimitsTable")] public IEnumerable SpecificationLimitsTable { get; set; } + /// + /// The SpindleInterlock events reported with the scalar VALUE representation. + /// Indication of the status of the spindle for a piece of equipment when power has been removed and it is free to rotate. + /// [JsonPropertyName("SpindleInterlock")] public IEnumerable SpindleInterlock { get; set; } + /// + /// The SpindleInterlock events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("SpindleInterlockDataSet")] public IEnumerable SpindleInterlockDataSet { get; set; } + /// + /// The SpindleInterlock events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("SpindleInterlockTable")] public IEnumerable SpindleInterlockTable { get; set; } + /// + /// The SwingAngle events reported with the scalar VALUE representation. + /// Angular range over which the object is designed to move about a fixed axis or pivot + /// [JsonPropertyName("SwingAngle")] public IEnumerable SwingAngle { get; set; } + /// + /// The SwingAngle events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("SwingAngleDataSet")] public IEnumerable SwingAngleDataSet { get; set; } + /// + /// The SwingAngle events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("SwingAngleTable")] public IEnumerable SwingAngleTable { get; set; } + /// + /// The SwingDiameter events reported with the scalar VALUE representation. + /// Maximal linear width (diameter) of the area described by the object’s movement about an axis + /// [JsonPropertyName("SwingDiameter")] public IEnumerable SwingDiameter { get; set; } + /// + /// The SwingDiameter events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("SwingDiameterDataSet")] public IEnumerable SwingDiameterDataSet { get; set; } + /// + /// The SwingDiameter events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("SwingDiameterTable")] public IEnumerable SwingDiameterTable { get; set; } + /// + /// The SwingRadius events reported with the scalar VALUE representation. + /// Maximal linear distance from the pivot or axis to the furthest point reached by the object’s swing + /// [JsonPropertyName("SwingRadius")] public IEnumerable SwingRadius { get; set; } + /// + /// The SwingRadius events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("SwingRadiusDataSet")] public IEnumerable SwingRadiusDataSet { get; set; } + /// + /// The SwingRadius events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("SwingRadiusTable")] public IEnumerable SwingRadiusTable { get; set; } + /// + /// The TaskAssetId events reported with the scalar VALUE representation. + /// AssetId of the Task that the Component binds to + /// [JsonPropertyName("TaskAssetId")] public IEnumerable TaskAssetId { get; set; } + /// + /// The TaskAssetId events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("TaskAssetIdDataSet")] public IEnumerable TaskAssetIdDataSet { get; set; } + /// + /// The TaskAssetId events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("TaskAssetIdTable")] public IEnumerable TaskAssetIdTable { get; set; } + /// + /// The Thickness events reported with the scalar VALUE representation. + /// Dimension between two surfaces of an object, usually the dimension of smallest measure, for example an additive layer, or a depth of cut. + /// [JsonPropertyName("Thickness")] public IEnumerable Thickness { get; set; } + /// + /// The Thickness events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ThicknessDataSet")] public IEnumerable ThicknessDataSet { get; set; } + /// + /// The Thickness events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ThicknessTable")] public IEnumerable ThicknessTable { get; set; } + /// + /// The ToolAssetId events reported with the scalar VALUE representation. + /// Identifier of an individual tool asset. + /// [JsonPropertyName("ToolAssetId")] public IEnumerable ToolAssetId { get; set; } + /// + /// The ToolAssetId events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ToolAssetIdDataSet")] public IEnumerable ToolAssetIdDataSet { get; set; } + /// + /// The ToolAssetId events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ToolAssetIdTable")] public IEnumerable ToolAssetIdTable { get; set; } + /// + /// The ToolCuttingItem events reported with the scalar VALUE representation. + /// Indices of the currently active cutting tool edge. + /// [JsonPropertyName("ToolCuttingItem")] public IEnumerable ToolCuttingItem { get; set; } + /// + /// The ToolCuttingItem events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ToolCuttingItemDataSet")] public IEnumerable ToolCuttingItemDataSet { get; set; } + /// + /// The ToolCuttingItem events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ToolCuttingItemTable")] public IEnumerable ToolCuttingItemTable { get; set; } + /// + /// The ToolGroup events reported with the scalar VALUE representation. + /// Identifier for the tool group associated with a specific tool. Commonly used to designate spare tools. + /// [JsonPropertyName("ToolGroup")] public IEnumerable ToolGroup { get; set; } + /// + /// The ToolGroup events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ToolGroupDataSet")] public IEnumerable ToolGroupDataSet { get; set; } + /// + /// The ToolGroup events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ToolGroupTable")] public IEnumerable ToolGroupTable { get; set; } + /// + /// The ToolId events reported with the scalar VALUE representation. + /// Identifier of the tool currently in use for a given `Path`.**DEPRECATED** in *Version 1.2.0*. See `TOOL_NUMBER`. + /// [JsonPropertyName("ToolId")] public IEnumerable ToolId { get; set; } + /// + /// The ToolId events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ToolIdDataSet")] public IEnumerable ToolIdDataSet { get; set; } + /// + /// The ToolId events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ToolIdTable")] public IEnumerable ToolIdTable { get; set; } + /// + /// The ToolNumber events reported with the scalar VALUE representation. + /// Identifier assigned by the Controller component to a cutting tool when in use by a piece of equipment. + /// [JsonPropertyName("ToolNumber")] public IEnumerable ToolNumber { get; set; } + /// + /// The ToolNumber events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ToolNumberDataSet")] public IEnumerable ToolNumberDataSet { get; set; } + /// + /// The ToolNumber events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ToolNumberTable")] public IEnumerable ToolNumberTable { get; set; } + /// + /// The ToolOffset events reported with the scalar VALUE representation. + /// Reference to the tool offset variables applied to the active cutting tool. + /// [JsonPropertyName("ToolOffset")] public IEnumerable ToolOffset { get; set; } + /// + /// The ToolOffset events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ToolOffsetDataSet")] public IEnumerable ToolOffsetDataSet { get; set; } + /// + /// The ToolOffset events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ToolOffsetTable")] public IEnumerable ToolOffsetTable { get; set; } + /// + /// The ToolOffsets events reported with the scalar VALUE representation. + /// Properties of each addressable tool offset. + /// [JsonPropertyName("ToolOffsets")] public IEnumerable ToolOffsets { get; set; } + /// + /// The ToolOffsets events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ToolOffsetsDataSet")] public IEnumerable ToolOffsetsDataSet { get; set; } + /// + /// The ToolOffsets events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ToolOffsetsTable")] public IEnumerable ToolOffsetsTable { get; set; } + /// + /// The TransferCount events reported with the scalar VALUE representation. + /// Accumulation of the number of times an operation has attempted to, or is planned to attempt to, transfer materials, parts, or other items from one location to another. + /// [JsonPropertyName("TransferCount")] public IEnumerable TransferCount { get; set; } + /// + /// The TransferCount events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("TransferCountDataSet")] public IEnumerable TransferCountDataSet { get; set; } + /// + /// The TransferCount events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("TransferCountTable")] public IEnumerable TransferCountTable { get; set; } + /// + /// The Translation events reported with the scalar VALUE representation. + /// Three space linear displacement of an object or coordinate system relative to a cartesian coordinate system. + /// [JsonPropertyName("Translation")] public IEnumerable Translation { get; set; } + /// + /// The Translation events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("TranslationDataSet")] public IEnumerable TranslationDataSet { get; set; } + /// + /// The Translation events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("TranslationTable")] public IEnumerable TranslationTable { get; set; } + /// + /// The Uncertainty events reported with the scalar VALUE representation. + /// Uncertainty specified by UncertaintyType. + /// [JsonPropertyName("Uncertainty")] public IEnumerable Uncertainty { get; set; } + /// + /// The Uncertainty events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("UncertaintyDataSet")] public IEnumerable UncertaintyDataSet { get; set; } + /// + /// The Uncertainty events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("UncertaintyTable")] public IEnumerable UncertaintyTable { get; set; } + /// + /// The UncertaintyType events reported with the scalar VALUE representation. + /// Method used to compute standard uncertainty. + /// [JsonPropertyName("UncertaintyType")] public IEnumerable UncertaintyType { get; set; } + /// + /// The UncertaintyType events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("UncertaintyTypeDataSet")] public IEnumerable UncertaintyTypeDataSet { get; set; } + /// + /// The UncertaintyType events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("UncertaintyTypeTable")] public IEnumerable UncertaintyTypeTable { get; set; } + /// + /// The UnloadCount events reported with the scalar VALUE representation. + /// Accumulation of the number of times an operation has attempted to, or is planned to attempt to, unload materials, parts, or other items. + /// [JsonPropertyName("UnloadCount")] public IEnumerable UnloadCount { get; set; } + /// + /// The UnloadCount events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("UnloadCountDataSet")] public IEnumerable UnloadCountDataSet { get; set; } + /// + /// The UnloadCount events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("UnloadCountTable")] public IEnumerable UnloadCountTable { get; set; } + /// + /// The User events reported with the scalar VALUE representation. + /// Identifier of the person currently responsible for operating the piece of equipment. + /// [JsonPropertyName("User")] public IEnumerable User { get; set; } + /// + /// The User events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("UserDataSet")] public IEnumerable UserDataSet { get; set; } + /// + /// The User events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("UserTable")] public IEnumerable UserTable { get; set; } + /// + /// The ValveState events reported with the scalar VALUE representation. + /// State of a valve is one of open, closed, or transitioning between the states. + /// [JsonPropertyName("ValveState")] public IEnumerable ValveState { get; set; } + /// + /// The ValveState events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ValveStateDataSet")] public IEnumerable ValveStateDataSet { get; set; } + /// + /// The ValveState events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ValveStateTable")] public IEnumerable ValveStateTable { get; set; } + /// + /// The Variable events reported with the scalar VALUE representation. + /// Data whose meaning may change over time due to changes in the operation of a piece of equipment or the process being executed on that piece of equipment. + /// [JsonPropertyName("Variable")] public IEnumerable Variable { get; set; } + /// + /// The Variable events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("VariableDataSet")] public IEnumerable VariableDataSet { get; set; } + /// + /// The Variable events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("VariableTable")] public IEnumerable VariableTable { get; set; } + /// + /// The WaitState events reported with the scalar VALUE representation. + /// Indication of the reason that Execution is reporting a value of `WAIT`. + /// [JsonPropertyName("WaitState")] public IEnumerable WaitState { get; set; } + /// + /// The WaitState events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("WaitStateDataSet")] public IEnumerable WaitStateDataSet { get; set; } + /// + /// The WaitState events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("WaitStateTable")] public IEnumerable WaitStateTable { get; set; } + /// + /// The Wire events reported with the scalar VALUE representation. + /// Identifier for the type of wire used as the cutting mechanism in Electrical Discharge Machining or similar processes. + /// [JsonPropertyName("Wire")] public IEnumerable Wire { get; set; } + /// + /// The Wire events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("WireDataSet")] public IEnumerable WireDataSet { get; set; } + /// + /// The Wire events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("WireTable")] public IEnumerable WireTable { get; set; } + /// + /// The WorkOffset events reported with the scalar VALUE representation. + /// Reference to offset variables for a work piece or part. + /// [JsonPropertyName("WorkOffset")] public IEnumerable WorkOffset { get; set; } + /// + /// The WorkOffset events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("WorkOffsetDataSet")] public IEnumerable WorkOffsetDataSet { get; set; } + /// + /// The WorkOffset events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("WorkOffsetTable")] public IEnumerable WorkOffsetTable { get; set; } + /// + /// The WorkOffsets events reported with the scalar VALUE representation. + /// Properties of each addressable work offset. + /// [JsonPropertyName("WorkOffsets")] public IEnumerable WorkOffsets { get; set; } + /// + /// The WorkOffsets events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("WorkOffsetsDataSet")] public IEnumerable WorkOffsetsDataSet { get; set; } + /// + /// The WorkOffsets events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("WorkOffsetsTable")] public IEnumerable WorkOffsetsTable { get; set; } + /// + /// The WorkholdingId events reported with the scalar VALUE representation. + /// Identifier for the current workholding or part clamp in use by a piece of equipment.**DEPRECATION WARNING**: Recommend using `FIXTURE_ID` instead. + /// [JsonPropertyName("WorkholdingId")] public IEnumerable WorkholdingId { get; set; } + /// + /// The WorkholdingId events reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("WorkholdingIdDataSet")] public IEnumerable WorkholdingIdDataSet { get; set; } + /// + /// The WorkholdingId events reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("WorkholdingIdTable")] public IEnumerable WorkholdingIdTable { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonEvents() { } + /// + /// Initializes a new instance from a flat sequence of , + /// routing each one into the typed collection matching its MTConnect type and + /// representation. + /// public JsonEvents(IEnumerable observations) { if (observations != null) @@ -7482,5 +9252,5 @@ public JsonEvents(IEnumerable observations) } } } - } -} \ No newline at end of file + } +} diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonMTConnectStreams.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonMTConnectStreams.cs index b63047d30..8518a9ef0 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonMTConnectStreams.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonMTConnectStreams.cs @@ -6,8 +6,20 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for the top-level + /// MTConnectStreams document in the cppagent-compatible + /// shape. Sits inside a + /// envelope and carries the wire-format version, the agent header, + /// and the document's device streams. Converts to and from the + /// strongly-typed model. + /// public class JsonMTConnectStreams { + /// + /// The wire-format version of the cppagent JSON envelope + /// emitted by this producer. + /// [JsonPropertyName("jsonVersion")] public int JsonVersion { get; set; } @@ -22,18 +34,35 @@ public class JsonMTConnectStreams [JsonPropertyName("schemaVersion")] public string SchemaVersion { get; set; } + /// + /// The MTConnect Agent header. + /// [JsonPropertyName("Header")] public JsonStreamsHeader Header { get; set; } + /// + /// The keyed device-stream container holding every device's + /// observations. + /// [JsonPropertyName("Streams")] public JsonStreams Streams { get; set; } + /// + /// Initializes a fresh container, defaulting + /// to the current emitter version. + /// public JsonMTConnectStreams() { JsonVersion = 2; } + /// + /// Initializes the container from a strongly-typed + /// , capturing the + /// agent schema version (distinct from + /// ). + /// public JsonMTConnectStreams(IStreamsResponseOutputDocument streamsDocument) { JsonVersion = 2; @@ -47,6 +76,10 @@ public JsonMTConnectStreams(IStreamsResponseOutputDocument streamsDocument) } + /// + /// Converts the container to a strongly-typed + /// . + /// public IStreamsResponseDocument ToStreamsDocument() { var streamsDocument = new StreamsResponseDocument(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonObservation.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonObservation.cs index dec675777..bbe9547e1 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonObservation.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonObservation.cs @@ -9,45 +9,96 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for an MTConnect observation in the + /// cppagent-compatible shape. Carries the metadata common to samples, + /// events, and conditions; subclasses add representation-specific + /// payloads. Static helpers project data-set, table, and time-series + /// payloads to and from their wire representations. + /// public class JsonObservation { + /// + /// Reference to the id of the data item the observation + /// reports. + /// [JsonPropertyName("dataItemId")] public string DataItemId { get; set; } + /// + /// The name of the data item the observation reports. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The category of the observation (SAMPLE, EVENT, or CONDITION). + /// [JsonPropertyName("category")] public string Category { get; set; } + /// + /// The representation of the observation. + /// [JsonPropertyName("representation")] public string Representation { get; set; } + /// + /// The subtype further qualifying the data item's type. + /// [JsonPropertyName("subType")] public string SubType { get; set; } + /// + /// Reference to the id of the composition the observation + /// originates from. + /// [JsonPropertyName("compositionId")] public string CompositionId { get; set; } + /// + /// The timestamp at which the observation was recorded. + /// [JsonPropertyName("timestamp")] public DateTime Timestamp { get; set; } + /// + /// The sequence number assigned to the observation by the agent. + /// [JsonPropertyName("sequence")] public ulong Sequence { get; set; } + /// + /// The instance identifier of the agent that produced the observation. + /// [JsonPropertyName("instanceId")] public ulong InstanceId { get; set; } + /// + /// Indicates whether a resettable observation's accumulated value was + /// reset on this observation. + /// [JsonPropertyName("resetTriggered")] public string ResetTriggered { get; set; } + /// + /// The native code of a condition observation as reported by the data + /// source. + /// [JsonPropertyName("nativeCode")] public string NativeCode { get; set; } + /// + /// The asset type, for an asset-changed or asset-removed observation. + /// [JsonPropertyName("assetType")] public string AssetType { get; set; } + /// + /// Converts strongly-typed data set entries to the cppagent key/value + /// JSON shape, parsing numeric values to double when possible. + /// public static JsonDataSetEntries CreateDataSetEntries(IEnumerable entries) { if (!entries.IsNullOrEmpty()) @@ -74,6 +125,10 @@ public static JsonDataSetEntries CreateDataSetEntries(IEnumerable return null; } + /// + /// Converts the cppagent key/value JSON shape back to strongly-typed + /// data set entries. + /// public static IEnumerable CreateDataSetEntries(Dictionary entries) { if (!entries.IsNullOrEmpty()) @@ -90,6 +145,11 @@ public static IEnumerable CreateDataSetEntries(Dictionary + /// Converts strongly-typed table entries to the cppagent + /// row/key/value nested JSON shape, parsing numeric cell values to + /// double when possible. + /// public static JsonTableEntries CreateTableEntries(IEnumerable entries) { if (!entries.IsNullOrEmpty()) @@ -125,6 +185,10 @@ public static JsonTableEntries CreateTableEntries(IEnumerable entri return null; } + /// + /// Converts the cppagent row/key/value nested JSON shape back to + /// strongly-typed table entries. + /// public static IEnumerable CreateTableEntries(Dictionary> entries) { if (!entries.IsNullOrEmpty()) @@ -149,6 +213,10 @@ public static IEnumerable CreateTableEntries(Dictionary + /// Wraps a sample value sequence as a , + /// or null when there are none. + /// public static JsonTimeSeriesSamples CreateTimeSeriesSamples(IEnumerable samples) { if (!samples.IsNullOrEmpty()) diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSampleDataSet.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSampleDataSet.cs index a3048fd29..9b8b549fc 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSampleDataSet.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSampleDataSet.cs @@ -9,17 +9,40 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for a SAMPLE observation carrying a + /// DATA_SET representation in the cppagent-compatible Streams shape. + /// The keyed entries are emitted as a JSON object on the + /// value property (via ) and + /// the entry count is carried alongside. + /// public class JsonSampleDataSet : JsonObservation { + /// + /// The keyed entries of the data set, emitted as a JSON object + /// or as the UNAVAILABLE string sentinel. + /// [JsonPropertyName("value")] public JsonDataSetEntries Entries { get; set; } + /// + /// The number of entries in the data set. + /// [JsonPropertyName("count")] public long? Count { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonSampleDataSet() { } + /// + /// Initializes the surrogate from a strongly-typed data-set + /// sample , optionally surfacing + /// category and instance-id. Emits an unavailable marker when + /// the source has no entries. + /// public JsonSampleDataSet(IObservation observation, bool categoryOutput = false, bool instanceIdOutput = false) { if (observation != null) @@ -55,6 +78,11 @@ public JsonSampleDataSet(IObservation observation, bool categoryOutput = false, } } + /// + /// Initializes the surrogate from a streaming + /// , rehydrating the data-set + /// entries from the observation's value bag. + /// public JsonSampleDataSet(IObservationOutput observation) { if (observation != null) @@ -90,6 +118,13 @@ public JsonSampleDataSet(IObservationOutput observation) } } + /// + /// Converts this surrogate to a strongly-typed + /// , restoring the + /// data-item type from the supplied dictionary key, or emitting + /// the UNAVAILABLE result when the entries are marked + /// unavailable. + /// public ISampleDataSetObservation ToObservation(string type) { var observation = new SampleDataSetObservation(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSampleTable.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSampleTable.cs index ab9e3971c..b1c688e5e 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSampleTable.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSampleTable.cs @@ -9,17 +9,40 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for a SAMPLE observation carrying a + /// TABLE representation in the cppagent-compatible Streams shape. + /// The rows are emitted as a nested JSON object on the + /// value property (via ) and + /// the row count is carried alongside. + /// public class JsonSampleTable : JsonObservation { + /// + /// The keyed table rows, emitted as a nested JSON object or as + /// the UNAVAILABLE string sentinel. + /// [JsonPropertyName("value")] public JsonTableEntries Entries { get; set; } + /// + /// The number of rows in the table. + /// [JsonPropertyName("count")] public long? Count { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonSampleTable() { } + /// + /// Initializes the surrogate from a strongly-typed table sample + /// , optionally surfacing category and + /// instance-id. Emits an unavailable marker when the source has + /// no rows. + /// public JsonSampleTable(IObservation observation, bool categoryOutput = false, bool instanceIdOutput = false) { if (observation != null) @@ -55,6 +78,11 @@ public JsonSampleTable(IObservation observation, bool categoryOutput = false, bo } } + /// + /// Initializes the surrogate from a streaming + /// , rehydrating the table rows + /// from the observation's value bag. + /// public JsonSampleTable(IObservationOutput observation) { if (observation != null) @@ -90,6 +118,13 @@ public JsonSampleTable(IObservationOutput observation) } } + /// + /// Converts this surrogate to a strongly-typed + /// , restoring the + /// data-item type from the supplied dictionary key, or emitting + /// the UNAVAILABLE result when the rows are marked + /// unavailable. + /// public ISampleTableObservation ToObservation(string type) { var observation = new SampleTableObservation(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSampleTimeSeries.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSampleTimeSeries.cs index 57e07df31..5be4b453b 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSampleTimeSeries.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSampleTimeSeries.cs @@ -10,20 +10,47 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for a SAMPLE observation carrying a + /// TIME_SERIES representation in the cppagent-compatible Streams + /// shape. The series of sample values is emitted as a numeric JSON + /// array on the value property (via + /// ), with the sample count and + /// rate carried alongside. + /// public class JsonSampleTimeSeries : JsonObservation { + /// + /// The series of sample values, emitted as a numeric JSON array + /// or as the UNAVAILABLE string sentinel. + /// [JsonPropertyName("value")] public JsonTimeSeriesSamples Samples { get; set; } + /// + /// The number of samples in the series. + /// [JsonPropertyName("sampleCount")] public long? SampleCount { get; set; } + /// + /// The sample rate, in Hz. + /// [JsonPropertyName("sampleRate")] public double? SampleRate { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonSampleTimeSeries() { } + /// + /// Initializes the surrogate from a strongly-typed time-series + /// , optionally surfacing category and + /// instance-id. Emits an unavailable marker when the source has + /// no samples. + /// public JsonSampleTimeSeries(IObservation observation, bool categoryOutput = false, bool instanceIdOutput = false) { if (observation != null) @@ -60,6 +87,11 @@ public JsonSampleTimeSeries(IObservation observation, bool categoryOutput = fals } } + /// + /// Initializes the surrogate from a streaming + /// , rehydrating the time-series + /// samples from the observation's value bag. + /// public JsonSampleTimeSeries(IObservationOutput observation) { if (observation != null) @@ -96,6 +128,14 @@ public JsonSampleTimeSeries(IObservationOutput observation) } } + /// + /// Converts this surrogate to a strongly-typed + /// , restoring the + /// data-item type from the supplied dictionary key and writing + /// each sample into the observation's keyed value bag, or + /// emitting the UNAVAILABLE result when the series is + /// marked unavailable. + /// public ISampleTimeSeriesObservation ToObservation(string type) { var observation = new SampleTimeSeriesObservation(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSampleValue.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSampleValue.cs index d1c1ef8b8..b9f8dd36d 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSampleValue.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSampleValue.cs @@ -9,24 +9,58 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for a SAMPLE observation carrying a + /// scalar value in the cppagent-compatible Streams shape. The + /// numeric value is emitted under the value property and + /// routed through so that the + /// UNAVAILABLE sentinel can be round-tripped as a string while + /// regular readings stay numeric. + /// public class JsonSampleValue : JsonObservation { + /// + /// The sample rate the observation was reported at, in Hz. + /// [JsonPropertyName("sampleRate")] public double? SampleRate { get; set; } + /// + /// The statistical function applied to the underlying data (for + /// example AVERAGE, MAXIMUM). + /// [JsonPropertyName("statistic")] public string Statistic { get; set; } + /// + /// The time-window duration the statistic was computed over, in + /// seconds. + /// [JsonPropertyName("duration")] public double? Duration { get; set; } + /// + /// The scalar value of the sample, written as a number when + /// available and as the UNAVAILABLE string sentinel + /// otherwise. + /// [JsonPropertyName("value")] [JsonConverter(typeof(JsonSampleValueConverter))] public object Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonSampleValue() { } + /// + /// Initializes the surrogate from a strongly-typed sample + /// , optionally surfacing category and + /// instance-id, and pulling the value, reset trigger, sample + /// rate, duration, and statistic from the observation's value + /// bag. + /// public JsonSampleValue(IObservation observation, bool categoryOutput = false, bool instanceIdOutput = false) { if (observation != null) @@ -50,6 +84,11 @@ public JsonSampleValue(IObservation observation, bool categoryOutput = false, bo } } + /// + /// Initializes the surrogate from a streaming + /// , pulling the same value-bag + /// fields as the model-level constructor. + /// public JsonSampleValue(IObservationOutput observation) { if (observation != null) @@ -72,6 +111,13 @@ public JsonSampleValue(IObservationOutput observation) } } + /// + /// Converts this surrogate to a strongly-typed + /// , restoring the data-item + /// type from the supplied dictionary key and guarding the optional + /// reset-trigger/statistic fields so an absent JSON property does + /// not stamp a stray default enumeration value. + /// public ISampleValueObservation ToObservation(string type) { var sample = new SampleValueObservation(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSampleValueConverter.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSampleValueConverter.cs index 65cbe8953..d916cefa9 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSampleValueConverter.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSampleValueConverter.cs @@ -31,6 +31,12 @@ namespace MTConnect.NET_JSON_cppagent.Streams /// public class JsonSampleValueConverter : JsonConverter { + /// + /// Reads a sample value, returning a boxed + /// for a JSON number token and the raw string for a JSON string + /// token. Any other token kind throws to make feed corruption + /// visible rather than silently dropped. + /// public override object Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options) { switch (reader.TokenType) @@ -46,6 +52,14 @@ public override object Read(ref Utf8JsonReader reader, Type typeToConvert, JsonS } } + /// + /// Writes a sample value to the wire, emitting a JSON number + /// for numeric primitives and numeric-string payloads, a JSON + /// string for the UNAVAILABLE sentinel and any non-numeric + /// payload, and a JSON null for null/blank strings so the + /// carrier honours the + /// contract. + /// public override void Write(Utf8JsonWriter writer, object value, JsonSerializerOptions options) { if (value is null) diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSamples.g.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSamples.g.cs index 7853b918b..147260756 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSamples.g.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonSamples.g.cs @@ -11,8 +11,18 @@ namespace MTConnect.Streams.Json { + /// + /// cppagent-style JSON representation of the SAMPLE-category observations in a + /// stream. Every MTConnect sample type is exposed as four typed collections — + /// one each for the VALUE, DATA_SET, TABLE, and TIME_SERIES representations — so + /// the serialized object shape matches the C++ reference agent's output. + /// public class JsonSamples { + /// + /// Materializes every typed collection into a single flat list of + /// , restoring each observation's MTConnect type. + /// [JsonIgnore] public List Observations { @@ -498,1244 +508,2772 @@ public List Observations return l; } } + /// + /// The Acceleration samples reported with the scalar VALUE representation. + /// Positive rate of change of velocity. + /// [JsonPropertyName("Acceleration")] public IEnumerable Acceleration { get; set; } + /// + /// The Acceleration samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AccelerationDataSet")] public IEnumerable AccelerationDataSet { get; set; } + /// + /// The Acceleration samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AccelerationTable")] public IEnumerable AccelerationTable { get; set; } + /// + /// The Acceleration samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("AccelerationTimeSeries")] public IEnumerable AccelerationTimeSeries { get; set; } + /// + /// The AccumulatedTime samples reported with the scalar VALUE representation. + /// Accumulated time for an activity or event. + /// [JsonPropertyName("AccumulatedTime")] public IEnumerable AccumulatedTime { get; set; } + /// + /// The AccumulatedTime samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AccumulatedTimeDataSet")] public IEnumerable AccumulatedTimeDataSet { get; set; } + /// + /// The AccumulatedTime samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AccumulatedTimeTable")] public IEnumerable AccumulatedTimeTable { get; set; } + /// + /// The AccumulatedTime samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("AccumulatedTimeTimeSeries")] public IEnumerable AccumulatedTimeTimeSeries { get; set; } + /// + /// The Amperage samples reported with the scalar VALUE representation. + /// Strength of electrical current.**DEPRECATED** in *Version 1.6*. Replaced by `AMPERAGE_AC` and `AMPERAGE_DC`. + /// [JsonPropertyName("Amperage")] public IEnumerable Amperage { get; set; } + /// + /// The Amperage samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AmperageDataSet")] public IEnumerable AmperageDataSet { get; set; } + /// + /// The Amperage samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AmperageTable")] public IEnumerable AmperageTable { get; set; } + /// + /// The Amperage samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("AmperageTimeSeries")] public IEnumerable AmperageTimeSeries { get; set; } + /// + /// The AmperageAC samples reported with the scalar VALUE representation. + /// Electrical current that reverses direction at regular short intervals. + /// [JsonPropertyName("AmperageAC")] public IEnumerable AmperageAC { get; set; } + /// + /// The AmperageAC samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AmperageACDataSet")] public IEnumerable AmperageACDataSet { get; set; } + /// + /// The AmperageAC samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AmperageACTable")] public IEnumerable AmperageACTable { get; set; } + /// + /// The AmperageAC samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("AmperageACTimeSeries")] public IEnumerable AmperageACTimeSeries { get; set; } + /// + /// The AmperageDC samples reported with the scalar VALUE representation. + /// Electric current flowing in one direction only. + /// [JsonPropertyName("AmperageDC")] public IEnumerable AmperageDC { get; set; } + /// + /// The AmperageDC samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AmperageDCDataSet")] public IEnumerable AmperageDCDataSet { get; set; } + /// + /// The AmperageDC samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AmperageDCTable")] public IEnumerable AmperageDCTable { get; set; } + /// + /// The AmperageDC samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("AmperageDCTimeSeries")] public IEnumerable AmperageDCTimeSeries { get; set; } + /// + /// The Angle samples reported with the scalar VALUE representation. + /// Angular position. + /// [JsonPropertyName("Angle")] public IEnumerable Angle { get; set; } + /// + /// The Angle samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AngleDataSet")] public IEnumerable AngleDataSet { get; set; } + /// + /// The Angle samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AngleTable")] public IEnumerable AngleTable { get; set; } + /// + /// The Angle samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("AngleTimeSeries")] public IEnumerable AngleTimeSeries { get; set; } + /// + /// The AngularAcceleration samples reported with the scalar VALUE representation. + /// Positive rate of change of angular velocity. + /// [JsonPropertyName("AngularAcceleration")] public IEnumerable AngularAcceleration { get; set; } + /// + /// The AngularAcceleration samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AngularAccelerationDataSet")] public IEnumerable AngularAccelerationDataSet { get; set; } + /// + /// The AngularAcceleration samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AngularAccelerationTable")] public IEnumerable AngularAccelerationTable { get; set; } + /// + /// The AngularAcceleration samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("AngularAccelerationTimeSeries")] public IEnumerable AngularAccelerationTimeSeries { get; set; } + /// + /// The AngularDeceleration samples reported with the scalar VALUE representation. + /// Negative rate of change of angular velocity. + /// [JsonPropertyName("AngularDeceleration")] public IEnumerable AngularDeceleration { get; set; } + /// + /// The AngularDeceleration samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AngularDecelerationDataSet")] public IEnumerable AngularDecelerationDataSet { get; set; } + /// + /// The AngularDeceleration samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AngularDecelerationTable")] public IEnumerable AngularDecelerationTable { get; set; } + /// + /// The AngularDeceleration samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("AngularDecelerationTimeSeries")] public IEnumerable AngularDecelerationTimeSeries { get; set; } + /// + /// The AngularVelocity samples reported with the scalar VALUE representation. + /// Rate of change of angular position. + /// [JsonPropertyName("AngularVelocity")] public IEnumerable AngularVelocity { get; set; } + /// + /// The AngularVelocity samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AngularVelocityDataSet")] public IEnumerable AngularVelocityDataSet { get; set; } + /// + /// The AngularVelocity samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AngularVelocityTable")] public IEnumerable AngularVelocityTable { get; set; } + /// + /// The AngularVelocity samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("AngularVelocityTimeSeries")] public IEnumerable AngularVelocityTimeSeries { get; set; } + /// + /// The AssetUpdateRate samples reported with the scalar VALUE representation. + /// Average rate of change of values for assets in the MTConnect streams. The average is computed over a rolling window defined by the implementation. + /// [JsonPropertyName("AssetUpdateRate")] public IEnumerable AssetUpdateRate { get; set; } + /// + /// The AssetUpdateRate samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AssetUpdateRateDataSet")] public IEnumerable AssetUpdateRateDataSet { get; set; } + /// + /// The AssetUpdateRate samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AssetUpdateRateTable")] public IEnumerable AssetUpdateRateTable { get; set; } + /// + /// The AssetUpdateRate samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("AssetUpdateRateTimeSeries")] public IEnumerable AssetUpdateRateTimeSeries { get; set; } + /// + /// The AxisFeedrate samples reported with the scalar VALUE representation. + /// Feedrate of a linear axis. + /// [JsonPropertyName("AxisFeedrate")] public IEnumerable AxisFeedrate { get; set; } + /// + /// The AxisFeedrate samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("AxisFeedrateDataSet")] public IEnumerable AxisFeedrateDataSet { get; set; } + /// + /// The AxisFeedrate samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("AxisFeedrateTable")] public IEnumerable AxisFeedrateTable { get; set; } + /// + /// The AxisFeedrate samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("AxisFeedrateTimeSeries")] public IEnumerable AxisFeedrateTimeSeries { get; set; } + /// + /// The BatteryCapacity samples reported with the scalar VALUE representation. + /// Maximum rated charge a battery is capable of maintaining based on the battery discharging at a specified current over a specified time period. + /// [JsonPropertyName("BatteryCapacity")] public IEnumerable BatteryCapacity { get; set; } + /// + /// The BatteryCapacity samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("BatteryCapacityDataSet")] public IEnumerable BatteryCapacityDataSet { get; set; } + /// + /// The BatteryCapacity samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("BatteryCapacityTable")] public IEnumerable BatteryCapacityTable { get; set; } + /// + /// The BatteryCapacity samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("BatteryCapacityTimeSeries")] public IEnumerable BatteryCapacityTimeSeries { get; set; } + /// + /// The BatteryCharge samples reported with the scalar VALUE representation. + /// Value of the battery's present capacity expressed as a percentage of the battery's maximum rated capacity. + /// [JsonPropertyName("BatteryCharge")] public IEnumerable BatteryCharge { get; set; } + /// + /// The BatteryCharge samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("BatteryChargeDataSet")] public IEnumerable BatteryChargeDataSet { get; set; } + /// + /// The BatteryCharge samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("BatteryChargeTable")] public IEnumerable BatteryChargeTable { get; set; } + /// + /// The BatteryCharge samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("BatteryChargeTimeSeries")] public IEnumerable BatteryChargeTimeSeries { get; set; } + /// + /// The CapacityFluid samples reported with the scalar VALUE representation. + /// Maximum amount of fluid that can be held by a container. + /// [JsonPropertyName("CapacityFluid")] public IEnumerable CapacityFluid { get; set; } + /// + /// The CapacityFluid samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("CapacityFluidDataSet")] public IEnumerable CapacityFluidDataSet { get; set; } + /// + /// The CapacityFluid samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("CapacityFluidTable")] public IEnumerable CapacityFluidTable { get; set; } + /// + /// The CapacityFluid samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("CapacityFluidTimeSeries")] public IEnumerable CapacityFluidTimeSeries { get; set; } + /// + /// The CapacitySpatial samples reported with the scalar VALUE representation. + /// Maximum amount of material that can be held by a container. + /// [JsonPropertyName("CapacitySpatial")] public IEnumerable CapacitySpatial { get; set; } + /// + /// The CapacitySpatial samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("CapacitySpatialDataSet")] public IEnumerable CapacitySpatialDataSet { get; set; } + /// + /// The CapacitySpatial samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("CapacitySpatialTable")] public IEnumerable CapacitySpatialTable { get; set; } + /// + /// The CapacitySpatial samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("CapacitySpatialTimeSeries")] public IEnumerable CapacitySpatialTimeSeries { get; set; } + /// + /// The ChargeRate samples reported with the scalar VALUE representation. + /// Value of the current being supplied to the Component for the purpose of charging. + /// [JsonPropertyName("ChargeRate")] public IEnumerable ChargeRate { get; set; } + /// + /// The ChargeRate samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ChargeRateDataSet")] public IEnumerable ChargeRateDataSet { get; set; } + /// + /// The ChargeRate samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ChargeRateTable")] public IEnumerable ChargeRateTable { get; set; } + /// + /// The ChargeRate samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("ChargeRateTimeSeries")] public IEnumerable ChargeRateTimeSeries { get; set; } + /// + /// The Concentration samples reported with the scalar VALUE representation. + /// Percentage of one component within a mixture of components. + /// [JsonPropertyName("Concentration")] public IEnumerable Concentration { get; set; } + /// + /// The Concentration samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ConcentrationDataSet")] public IEnumerable ConcentrationDataSet { get; set; } + /// + /// The Concentration samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ConcentrationTable")] public IEnumerable ConcentrationTable { get; set; } + /// + /// The Concentration samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("ConcentrationTimeSeries")] public IEnumerable ConcentrationTimeSeries { get; set; } + /// + /// The Conductivity samples reported with the scalar VALUE representation. + /// Ability of a material to conduct electricity. + /// [JsonPropertyName("Conductivity")] public IEnumerable Conductivity { get; set; } + /// + /// The Conductivity samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ConductivityDataSet")] public IEnumerable ConductivityDataSet { get; set; } + /// + /// The Conductivity samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ConductivityTable")] public IEnumerable ConductivityTable { get; set; } + /// + /// The Conductivity samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("ConductivityTimeSeries")] public IEnumerable ConductivityTimeSeries { get; set; } + /// + /// The CuttingSpeed samples reported with the scalar VALUE representation. + /// Speed difference (relative velocity) between the cutting mechanism and the surface of the workpiece it is operating on. + /// [JsonPropertyName("CuttingSpeed")] public IEnumerable CuttingSpeed { get; set; } + /// + /// The CuttingSpeed samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("CuttingSpeedDataSet")] public IEnumerable CuttingSpeedDataSet { get; set; } + /// + /// The CuttingSpeed samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("CuttingSpeedTable")] public IEnumerable CuttingSpeedTable { get; set; } + /// + /// The CuttingSpeed samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("CuttingSpeedTimeSeries")] public IEnumerable CuttingSpeedTimeSeries { get; set; } + /// + /// The Deceleration samples reported with the scalar VALUE representation. + /// Negative rate of change of velocity. + /// [JsonPropertyName("Deceleration")] public IEnumerable Deceleration { get; set; } + /// + /// The Deceleration samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("DecelerationDataSet")] public IEnumerable DecelerationDataSet { get; set; } + /// + /// The Deceleration samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("DecelerationTable")] public IEnumerable DecelerationTable { get; set; } + /// + /// The Deceleration samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("DecelerationTimeSeries")] public IEnumerable DecelerationTimeSeries { get; set; } + /// + /// The Density samples reported with the scalar VALUE representation. + /// Volumetric mass of a material per unit volume of that material. + /// [JsonPropertyName("Density")] public IEnumerable Density { get; set; } + /// + /// The Density samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("DensityDataSet")] public IEnumerable DensityDataSet { get; set; } + /// + /// The Density samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("DensityTable")] public IEnumerable DensityTable { get; set; } + /// + /// The Density samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("DensityTimeSeries")] public IEnumerable DensityTimeSeries { get; set; } + /// + /// The DepositionAccelerationVolumetric samples reported with the scalar VALUE representation. + /// Rate of change in spatial volume of material deposited in an additive manufacturing process. + /// [JsonPropertyName("DepositionAccelerationVolumetric")] public IEnumerable DepositionAccelerationVolumetric { get; set; } + /// + /// The DepositionAccelerationVolumetric samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("DepositionAccelerationVolumetricDataSet")] public IEnumerable DepositionAccelerationVolumetricDataSet { get; set; } + /// + /// The DepositionAccelerationVolumetric samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("DepositionAccelerationVolumetricTable")] public IEnumerable DepositionAccelerationVolumetricTable { get; set; } + /// + /// The DepositionAccelerationVolumetric samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("DepositionAccelerationVolumetricTimeSeries")] public IEnumerable DepositionAccelerationVolumetricTimeSeries { get; set; } + /// + /// The DepositionDensity samples reported with the scalar VALUE representation. + /// Density of the material deposited in an additive manufacturing process per unit of volume. + /// [JsonPropertyName("DepositionDensity")] public IEnumerable DepositionDensity { get; set; } + /// + /// The DepositionDensity samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("DepositionDensityDataSet")] public IEnumerable DepositionDensityDataSet { get; set; } + /// + /// The DepositionDensity samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("DepositionDensityTable")] public IEnumerable DepositionDensityTable { get; set; } + /// + /// The DepositionDensity samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("DepositionDensityTimeSeries")] public IEnumerable DepositionDensityTimeSeries { get; set; } + /// + /// The DepositionMass samples reported with the scalar VALUE representation. + /// Mass of the material deposited in an additive manufacturing process. + /// [JsonPropertyName("DepositionMass")] public IEnumerable DepositionMass { get; set; } + /// + /// The DepositionMass samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("DepositionMassDataSet")] public IEnumerable DepositionMassDataSet { get; set; } + /// + /// The DepositionMass samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("DepositionMassTable")] public IEnumerable DepositionMassTable { get; set; } + /// + /// The DepositionMass samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("DepositionMassTimeSeries")] public IEnumerable DepositionMassTimeSeries { get; set; } + /// + /// The DepositionRateVolumetric samples reported with the scalar VALUE representation. + /// Rate at which a spatial volume of material is deposited in an additive manufacturing process. + /// [JsonPropertyName("DepositionRateVolumetric")] public IEnumerable DepositionRateVolumetric { get; set; } + /// + /// The DepositionRateVolumetric samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("DepositionRateVolumetricDataSet")] public IEnumerable DepositionRateVolumetricDataSet { get; set; } + /// + /// The DepositionRateVolumetric samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("DepositionRateVolumetricTable")] public IEnumerable DepositionRateVolumetricTable { get; set; } + /// + /// The DepositionRateVolumetric samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("DepositionRateVolumetricTimeSeries")] public IEnumerable DepositionRateVolumetricTimeSeries { get; set; } + /// + /// The DepositionVolume samples reported with the scalar VALUE representation. + /// Spatial volume of material to be deposited in an additive manufacturing process. + /// [JsonPropertyName("DepositionVolume")] public IEnumerable DepositionVolume { get; set; } + /// + /// The DepositionVolume samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("DepositionVolumeDataSet")] public IEnumerable DepositionVolumeDataSet { get; set; } + /// + /// The DepositionVolume samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("DepositionVolumeTable")] public IEnumerable DepositionVolumeTable { get; set; } + /// + /// The DepositionVolume samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("DepositionVolumeTimeSeries")] public IEnumerable DepositionVolumeTimeSeries { get; set; } + /// + /// The DewPoint samples reported with the scalar VALUE representation. + /// Temperature at which moisture begins to condense, corresponding to saturation for a given absolute humidity. + /// [JsonPropertyName("DewPoint")] public IEnumerable DewPoint { get; set; } + /// + /// The DewPoint samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("DewPointDataSet")] public IEnumerable DewPointDataSet { get; set; } + /// + /// The DewPoint samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("DewPointTable")] public IEnumerable DewPointTable { get; set; } + /// + /// The DewPoint samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("DewPointTimeSeries")] public IEnumerable DewPointTimeSeries { get; set; } + /// + /// The Diameter samples reported with the scalar VALUE representation. + /// Dimension of a diameter. + /// [JsonPropertyName("Diameter")] public IEnumerable Diameter { get; set; } + /// + /// The Diameter samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("DiameterDataSet")] public IEnumerable DiameterDataSet { get; set; } + /// + /// The Diameter samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("DiameterTable")] public IEnumerable DiameterTable { get; set; } + /// + /// The Diameter samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("DiameterTimeSeries")] public IEnumerable DiameterTimeSeries { get; set; } + /// + /// The DischargeRate samples reported with the scalar VALUE representation. + /// Value of current being drawn from the Component. + /// [JsonPropertyName("DischargeRate")] public IEnumerable DischargeRate { get; set; } + /// + /// The DischargeRate samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("DischargeRateDataSet")] public IEnumerable DischargeRateDataSet { get; set; } + /// + /// The DischargeRate samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("DischargeRateTable")] public IEnumerable DischargeRateTable { get; set; } + /// + /// The DischargeRate samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("DischargeRateTimeSeries")] public IEnumerable DischargeRateTimeSeries { get; set; } + /// + /// The Displacement samples reported with the scalar VALUE representation. + /// Change in position of an object. + /// [JsonPropertyName("Displacement")] public IEnumerable Displacement { get; set; } + /// + /// The Displacement samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("DisplacementDataSet")] public IEnumerable DisplacementDataSet { get; set; } + /// + /// The Displacement samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("DisplacementTable")] public IEnumerable DisplacementTable { get; set; } + /// + /// The Displacement samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("DisplacementTimeSeries")] public IEnumerable DisplacementTimeSeries { get; set; } + /// + /// The DisplacementAngular samples reported with the scalar VALUE representation. + /// Absolute value of the change in angular position around a vector + /// [JsonPropertyName("DisplacementAngular")] public IEnumerable DisplacementAngular { get; set; } + /// + /// The DisplacementAngular samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("DisplacementAngularDataSet")] public IEnumerable DisplacementAngularDataSet { get; set; } + /// + /// The DisplacementAngular samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("DisplacementAngularTable")] public IEnumerable DisplacementAngularTable { get; set; } + /// + /// The DisplacementAngular samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("DisplacementAngularTimeSeries")] public IEnumerable DisplacementAngularTimeSeries { get; set; } + /// + /// The DisplacementLinear samples reported with the scalar VALUE representation. + /// Absolute value of the change in position along a vector. + /// [JsonPropertyName("DisplacementLinear")] public IEnumerable DisplacementLinear { get; set; } + /// + /// The DisplacementLinear samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("DisplacementLinearDataSet")] public IEnumerable DisplacementLinearDataSet { get; set; } + /// + /// The DisplacementLinear samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("DisplacementLinearTable")] public IEnumerable DisplacementLinearTable { get; set; } + /// + /// The DisplacementLinear samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("DisplacementLinearTimeSeries")] public IEnumerable DisplacementLinearTimeSeries { get; set; } + /// + /// The ElectricalEnergy samples reported with the scalar VALUE representation. + /// Wattage used or generated by a component over an interval of time. + /// [JsonPropertyName("ElectricalEnergy")] public IEnumerable ElectricalEnergy { get; set; } + /// + /// The ElectricalEnergy samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ElectricalEnergyDataSet")] public IEnumerable ElectricalEnergyDataSet { get; set; } + /// + /// The ElectricalEnergy samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ElectricalEnergyTable")] public IEnumerable ElectricalEnergyTable { get; set; } + /// + /// The ElectricalEnergy samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("ElectricalEnergyTimeSeries")] public IEnumerable ElectricalEnergyTimeSeries { get; set; } + /// + /// The EquipmentTimer samples reported with the scalar VALUE representation. + /// Amount of time a piece of equipment or a sub-part of a piece of equipment has performed specific activities. + /// [JsonPropertyName("EquipmentTimer")] public IEnumerable EquipmentTimer { get; set; } + /// + /// The EquipmentTimer samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("EquipmentTimerDataSet")] public IEnumerable EquipmentTimerDataSet { get; set; } + /// + /// The EquipmentTimer samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("EquipmentTimerTable")] public IEnumerable EquipmentTimerTable { get; set; } + /// + /// The EquipmentTimer samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("EquipmentTimerTimeSeries")] public IEnumerable EquipmentTimerTimeSeries { get; set; } + /// + /// The FillHeight samples reported with the scalar VALUE representation. + /// Amount of a substance in a container. + /// [JsonPropertyName("FillHeight")] public IEnumerable FillHeight { get; set; } + /// + /// The FillHeight samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("FillHeightDataSet")] public IEnumerable FillHeightDataSet { get; set; } + /// + /// The FillHeight samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("FillHeightTable")] public IEnumerable FillHeightTable { get; set; } + /// + /// The FillHeight samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("FillHeightTimeSeries")] public IEnumerable FillHeightTimeSeries { get; set; } + /// + /// The FillLevel samples reported with the scalar VALUE representation. + /// Amount of a substance remaining compared to the planned maximum amount of that substance. + /// [JsonPropertyName("FillLevel")] public IEnumerable FillLevel { get; set; } + /// + /// The FillLevel samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("FillLevelDataSet")] public IEnumerable FillLevelDataSet { get; set; } + /// + /// The FillLevel samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("FillLevelTable")] public IEnumerable FillLevelTable { get; set; } + /// + /// The FillLevel samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("FillLevelTimeSeries")] public IEnumerable FillLevelTimeSeries { get; set; } + /// + /// The Flow samples reported with the scalar VALUE representation. + /// Rate of flow of a fluid. + /// [JsonPropertyName("Flow")] public IEnumerable Flow { get; set; } + /// + /// The Flow samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("FlowDataSet")] public IEnumerable FlowDataSet { get; set; } + /// + /// The Flow samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("FlowTable")] public IEnumerable FlowTable { get; set; } + /// + /// The Flow samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("FlowTimeSeries")] public IEnumerable FlowTimeSeries { get; set; } + /// + /// The FollowingError samples reported with the scalar VALUE representation. + /// Difference between actual and commanded position at any specific point in time during a motion. + /// [JsonPropertyName("FollowingError")] public IEnumerable FollowingError { get; set; } + /// + /// The FollowingError samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("FollowingErrorDataSet")] public IEnumerable FollowingErrorDataSet { get; set; } + /// + /// The FollowingError samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("FollowingErrorTable")] public IEnumerable FollowingErrorTable { get; set; } + /// + /// The FollowingError samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("FollowingErrorTimeSeries")] public IEnumerable FollowingErrorTimeSeries { get; set; } + /// + /// The FollowingErrorAngular samples reported with the scalar VALUE representation. + /// Angular difference between the commanded encoder/resolver position and the actual encoder/resolver position at any specified point in time during a motion. + /// [JsonPropertyName("FollowingErrorAngular")] public IEnumerable FollowingErrorAngular { get; set; } + /// + /// The FollowingErrorAngular samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("FollowingErrorAngularDataSet")] public IEnumerable FollowingErrorAngularDataSet { get; set; } + /// + /// The FollowingErrorAngular samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("FollowingErrorAngularTable")] public IEnumerable FollowingErrorAngularTable { get; set; } + /// + /// The FollowingErrorAngular samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("FollowingErrorAngularTimeSeries")] public IEnumerable FollowingErrorAngularTimeSeries { get; set; } + /// + /// The FollowingErrorLinear samples reported with the scalar VALUE representation. + /// Difference between the commanded encoder/resolver position and the actual encoder/resolver position at any specified point in time during a motion. + /// [JsonPropertyName("FollowingErrorLinear")] public IEnumerable FollowingErrorLinear { get; set; } + /// + /// The FollowingErrorLinear samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("FollowingErrorLinearDataSet")] public IEnumerable FollowingErrorLinearDataSet { get; set; } + /// + /// The FollowingErrorLinear samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("FollowingErrorLinearTable")] public IEnumerable FollowingErrorLinearTable { get; set; } + /// + /// The FollowingErrorLinear samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("FollowingErrorLinearTimeSeries")] public IEnumerable FollowingErrorLinearTimeSeries { get; set; } + /// + /// The Frequency samples reported with the scalar VALUE representation. + /// Number of occurrences of a repeating event per unit time. + /// [JsonPropertyName("Frequency")] public IEnumerable Frequency { get; set; } + /// + /// The Frequency samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("FrequencyDataSet")] public IEnumerable FrequencyDataSet { get; set; } + /// + /// The Frequency samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("FrequencyTable")] public IEnumerable FrequencyTable { get; set; } + /// + /// The Frequency samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("FrequencyTimeSeries")] public IEnumerable FrequencyTimeSeries { get; set; } + /// + /// The GlobalPosition samples reported with the scalar VALUE representation. + /// Position in three-dimensional space.**DEPRECATED** in Version 1.1. + /// [JsonPropertyName("GlobalPosition")] public IEnumerable GlobalPosition { get; set; } + /// + /// The GlobalPosition samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("GlobalPositionDataSet")] public IEnumerable GlobalPositionDataSet { get; set; } + /// + /// The GlobalPosition samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("GlobalPositionTable")] public IEnumerable GlobalPositionTable { get; set; } + /// + /// The GlobalPosition samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("GlobalPositionTimeSeries")] public IEnumerable GlobalPositionTimeSeries { get; set; } + /// + /// The GravitationalAcceleration samples reported with the scalar VALUE representation. + /// Acceleration relative to Earth's gravity of 9.80665 `METER/SECOND^2`. + /// [JsonPropertyName("GravitationalAcceleration")] public IEnumerable GravitationalAcceleration { get; set; } + /// + /// The GravitationalAcceleration samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("GravitationalAccelerationDataSet")] public IEnumerable GravitationalAccelerationDataSet { get; set; } + /// + /// The GravitationalAcceleration samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("GravitationalAccelerationTable")] public IEnumerable GravitationalAccelerationTable { get; set; } + /// + /// The GravitationalAcceleration samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("GravitationalAccelerationTimeSeries")] public IEnumerable GravitationalAccelerationTimeSeries { get; set; } + /// + /// The GravitationalForce samples reported with the scalar VALUE representation. + /// Force relative to earth's gravity. + /// [JsonPropertyName("GravitationalForce")] public IEnumerable GravitationalForce { get; set; } + /// + /// The GravitationalForce samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("GravitationalForceDataSet")] public IEnumerable GravitationalForceDataSet { get; set; } + /// + /// The GravitationalForce samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("GravitationalForceTable")] public IEnumerable GravitationalForceTable { get; set; } + /// + /// The GravitationalForce samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("GravitationalForceTimeSeries")] public IEnumerable GravitationalForceTimeSeries { get; set; } + /// + /// The HumidityAbsolute samples reported with the scalar VALUE representation. + /// Amount of water vapor expressed in grams per cubic meter. + /// [JsonPropertyName("HumidityAbsolute")] public IEnumerable HumidityAbsolute { get; set; } + /// + /// The HumidityAbsolute samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("HumidityAbsoluteDataSet")] public IEnumerable HumidityAbsoluteDataSet { get; set; } + /// + /// The HumidityAbsolute samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("HumidityAbsoluteTable")] public IEnumerable HumidityAbsoluteTable { get; set; } + /// + /// The HumidityAbsolute samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("HumidityAbsoluteTimeSeries")] public IEnumerable HumidityAbsoluteTimeSeries { get; set; } + /// + /// The HumidityRelative samples reported with the scalar VALUE representation. + /// Amount of water vapor present expressed as a percent to reach saturation at the same temperature. + /// [JsonPropertyName("HumidityRelative")] public IEnumerable HumidityRelative { get; set; } + /// + /// The HumidityRelative samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("HumidityRelativeDataSet")] public IEnumerable HumidityRelativeDataSet { get; set; } + /// + /// The HumidityRelative samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("HumidityRelativeTable")] public IEnumerable HumidityRelativeTable { get; set; } + /// + /// The HumidityRelative samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("HumidityRelativeTimeSeries")] public IEnumerable HumidityRelativeTimeSeries { get; set; } + /// + /// The HumiditySpecific samples reported with the scalar VALUE representation. + /// Ratio of the water vapor present over the total weight of the water vapor and air present expressed as a percent. + /// [JsonPropertyName("HumiditySpecific")] public IEnumerable HumiditySpecific { get; set; } + /// + /// The HumiditySpecific samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("HumiditySpecificDataSet")] public IEnumerable HumiditySpecificDataSet { get; set; } + /// + /// The HumiditySpecific samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("HumiditySpecificTable")] public IEnumerable HumiditySpecificTable { get; set; } + /// + /// The HumiditySpecific samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("HumiditySpecificTimeSeries")] public IEnumerable HumiditySpecificTimeSeries { get; set; } + /// + /// The Length samples reported with the scalar VALUE representation. + /// Length of an object. + /// [JsonPropertyName("Length")] public IEnumerable Length { get; set; } + /// + /// The Length samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("LengthDataSet")] public IEnumerable LengthDataSet { get; set; } + /// + /// The Length samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("LengthTable")] public IEnumerable LengthTable { get; set; } + /// + /// The Length samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("LengthTimeSeries")] public IEnumerable LengthTimeSeries { get; set; } + /// + /// The Level samples reported with the scalar VALUE representation. + /// Level of a resource.**DEPRECATED** in *Version 1.2*. See `FILL_LEVEL`. + /// [JsonPropertyName("Level")] public IEnumerable Level { get; set; } + /// + /// The Level samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("LevelDataSet")] public IEnumerable LevelDataSet { get; set; } + /// + /// The Level samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("LevelTable")] public IEnumerable LevelTable { get; set; } + /// + /// The Level samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("LevelTimeSeries")] public IEnumerable LevelTimeSeries { get; set; } + /// + /// The LinearForce samples reported with the scalar VALUE representation. + /// Force applied to a mass in one direction only. + /// [JsonPropertyName("LinearForce")] public IEnumerable LinearForce { get; set; } + /// + /// The LinearForce samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("LinearForceDataSet")] public IEnumerable LinearForceDataSet { get; set; } + /// + /// The LinearForce samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("LinearForceTable")] public IEnumerable LinearForceTable { get; set; } + /// + /// The LinearForce samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("LinearForceTimeSeries")] public IEnumerable LinearForceTimeSeries { get; set; } + /// + /// The Load samples reported with the scalar VALUE representation. + /// Actual versus the standard rating of a piece of equipment. + /// [JsonPropertyName("Load")] public IEnumerable Load { get; set; } + /// + /// The Load samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("LoadDataSet")] public IEnumerable LoadDataSet { get; set; } + /// + /// The Load samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("LoadTable")] public IEnumerable LoadTable { get; set; } + /// + /// The Load samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("LoadTimeSeries")] public IEnumerable LoadTimeSeries { get; set; } + /// + /// The Mass samples reported with the scalar VALUE representation. + /// Mass of an object(s) or an amount of material. + /// [JsonPropertyName("Mass")] public IEnumerable Mass { get; set; } + /// + /// The Mass samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("MassDataSet")] public IEnumerable MassDataSet { get; set; } + /// + /// The Mass samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("MassTable")] public IEnumerable MassTable { get; set; } + /// + /// The Mass samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("MassTimeSeries")] public IEnumerable MassTimeSeries { get; set; } + /// + /// The ObservationUpdateRate samples reported with the scalar VALUE representation. + /// Average rate of change of values for data items in the MTConnect streams. The average is computed over a rolling window defined by the implementation. + /// [JsonPropertyName("ObservationUpdateRate")] public IEnumerable ObservationUpdateRate { get; set; } + /// + /// The ObservationUpdateRate samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ObservationUpdateRateDataSet")] public IEnumerable ObservationUpdateRateDataSet { get; set; } + /// + /// The ObservationUpdateRate samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ObservationUpdateRateTable")] public IEnumerable ObservationUpdateRateTable { get; set; } + /// + /// The ObservationUpdateRate samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("ObservationUpdateRateTimeSeries")] public IEnumerable ObservationUpdateRateTimeSeries { get; set; } + /// + /// The Openness samples reported with the scalar VALUE representation. + /// Percentage open where 100% is fully open and 0% is fully closed. + /// [JsonPropertyName("Openness")] public IEnumerable Openness { get; set; } + /// + /// The Openness samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("OpennessDataSet")] public IEnumerable OpennessDataSet { get; set; } + /// + /// The Openness samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("OpennessTable")] public IEnumerable OpennessTable { get; set; } + /// + /// The Openness samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("OpennessTimeSeries")] public IEnumerable OpennessTimeSeries { get; set; } + /// + /// The Orientation samples reported with the scalar VALUE representation. + /// Angular position of a plane or vector relative to a cartesian coordinate system + /// [JsonPropertyName("Orientation")] public IEnumerable Orientation { get; set; } + /// + /// The Orientation samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("OrientationDataSet")] public IEnumerable OrientationDataSet { get; set; } + /// + /// The Orientation samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("OrientationTable")] public IEnumerable OrientationTable { get; set; } + /// + /// The Orientation samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("OrientationTimeSeries")] public IEnumerable OrientationTimeSeries { get; set; } + /// + /// The ParticleCount samples reported with the scalar VALUE representation. + /// Number of particles counted by their size or other characteristics. + /// [JsonPropertyName("ParticleCount")] public IEnumerable ParticleCount { get; set; } + /// + /// The ParticleCount samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ParticleCountDataSet")] public IEnumerable ParticleCountDataSet { get; set; } + /// + /// The ParticleCount samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ParticleCountTable")] public IEnumerable ParticleCountTable { get; set; } + /// + /// The ParticleCount samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("ParticleCountTimeSeries")] public IEnumerable ParticleCountTimeSeries { get; set; } + /// + /// The ParticleSize samples reported with the scalar VALUE representation. + /// Size of particles counted by their size or other characteristics. + /// [JsonPropertyName("ParticleSize")] public IEnumerable ParticleSize { get; set; } + /// + /// The ParticleSize samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ParticleSizeDataSet")] public IEnumerable ParticleSizeDataSet { get; set; } + /// + /// The ParticleSize samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ParticleSizeTable")] public IEnumerable ParticleSizeTable { get; set; } + /// + /// The ParticleSize samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("ParticleSizeTimeSeries")] public IEnumerable ParticleSizeTimeSeries { get; set; } + /// + /// The PathFeedrate samples reported with the scalar VALUE representation. + /// Feedrate for the axes, or a single axis, associated with a Path component. + /// [JsonPropertyName("PathFeedrate")] public IEnumerable PathFeedrate { get; set; } + /// + /// The PathFeedrate samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PathFeedrateDataSet")] public IEnumerable PathFeedrateDataSet { get; set; } + /// + /// The PathFeedrate samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PathFeedrateTable")] public IEnumerable PathFeedrateTable { get; set; } + /// + /// The PathFeedrate samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("PathFeedrateTimeSeries")] public IEnumerable PathFeedrateTimeSeries { get; set; } + /// + /// The PathFeedratePerRevolution samples reported with the scalar VALUE representation. + /// Feedrate for the axes, or a single axis. + /// [JsonPropertyName("PathFeedratePerRevolution")] public IEnumerable PathFeedratePerRevolution { get; set; } + /// + /// The PathFeedratePerRevolution samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PathFeedratePerRevolutionDataSet")] public IEnumerable PathFeedratePerRevolutionDataSet { get; set; } + /// + /// The PathFeedratePerRevolution samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PathFeedratePerRevolutionTable")] public IEnumerable PathFeedratePerRevolutionTable { get; set; } + /// + /// The PathFeedratePerRevolution samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("PathFeedratePerRevolutionTimeSeries")] public IEnumerable PathFeedratePerRevolutionTimeSeries { get; set; } + /// + /// The PathPosition samples reported with the scalar VALUE representation. + /// Position of a control point associated with a Controller or a Path. + /// [JsonPropertyName("PathPosition")] public IEnumerable PathPosition { get; set; } + /// + /// The PathPosition samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PathPositionDataSet")] public IEnumerable PathPositionDataSet { get; set; } + /// + /// The PathPosition samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PathPositionTable")] public IEnumerable PathPositionTable { get; set; } + /// + /// The PathPosition samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("PathPositionTimeSeries")] public IEnumerable PathPositionTimeSeries { get; set; } + /// + /// The PH samples reported with the scalar VALUE representation. + /// Acidity or alkalinity of a solution. + /// [JsonPropertyName("PH")] public IEnumerable PH { get; set; } + /// + /// The PH samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PHDataSet")] public IEnumerable PHDataSet { get; set; } + /// + /// The PH samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PHTable")] public IEnumerable PHTable { get; set; } + /// + /// The PH samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("PHTimeSeries")] public IEnumerable PHTimeSeries { get; set; } + /// + /// The Position samples reported with the scalar VALUE representation. + /// Point along an axis in a cartesian coordinate system. + /// [JsonPropertyName("Position")] public IEnumerable Position { get; set; } + /// + /// The Position samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PositionDataSet")] public IEnumerable PositionDataSet { get; set; } + /// + /// The Position samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PositionTable")] public IEnumerable PositionTable { get; set; } + /// + /// The Position samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("PositionTimeSeries")] public IEnumerable PositionTimeSeries { get; set; } + /// + /// The PositionCartesian samples reported with the scalar VALUE representation. + /// Point in a cartesian coordinate system. + /// [JsonPropertyName("PositionCartesian")] public IEnumerable PositionCartesian { get; set; } + /// + /// The PositionCartesian samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PositionCartesianDataSet")] public IEnumerable PositionCartesianDataSet { get; set; } + /// + /// The PositionCartesian samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PositionCartesianTable")] public IEnumerable PositionCartesianTable { get; set; } + /// + /// The PositionCartesian samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("PositionCartesianTimeSeries")] public IEnumerable PositionCartesianTimeSeries { get; set; } + /// + /// The PowerFactor samples reported with the scalar VALUE representation. + /// Ratio of real power flowing to a load to the apparent power in that AC circuit. + /// [JsonPropertyName("PowerFactor")] public IEnumerable PowerFactor { get; set; } + /// + /// The PowerFactor samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PowerFactorDataSet")] public IEnumerable PowerFactorDataSet { get; set; } + /// + /// The PowerFactor samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PowerFactorTable")] public IEnumerable PowerFactorTable { get; set; } + /// + /// The PowerFactor samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("PowerFactorTimeSeries")] public IEnumerable PowerFactorTimeSeries { get; set; } + /// + /// The Pressure samples reported with the scalar VALUE representation. + /// Force per unit area measured relative to atmospheric pressure. Commonly referred to as gauge pressure. + /// [JsonPropertyName("Pressure")] public IEnumerable Pressure { get; set; } + /// + /// The Pressure samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PressureDataSet")] public IEnumerable PressureDataSet { get; set; } + /// + /// The Pressure samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PressureTable")] public IEnumerable PressureTable { get; set; } + /// + /// The Pressure samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("PressureTimeSeries")] public IEnumerable PressureTimeSeries { get; set; } + /// + /// The PressureAbsolute samples reported with the scalar VALUE representation. + /// Force per unit area measured relative to a vacuum. + /// [JsonPropertyName("PressureAbsolute")] public IEnumerable PressureAbsolute { get; set; } + /// + /// The PressureAbsolute samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PressureAbsoluteDataSet")] public IEnumerable PressureAbsoluteDataSet { get; set; } + /// + /// The PressureAbsolute samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PressureAbsoluteTable")] public IEnumerable PressureAbsoluteTable { get; set; } + /// + /// The PressureAbsolute samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("PressureAbsoluteTimeSeries")] public IEnumerable PressureAbsoluteTimeSeries { get; set; } + /// + /// The PressurizationRate samples reported with the scalar VALUE representation. + /// Change of pressure per unit time. + /// [JsonPropertyName("PressurizationRate")] public IEnumerable PressurizationRate { get; set; } + /// + /// The PressurizationRate samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("PressurizationRateDataSet")] public IEnumerable PressurizationRateDataSet { get; set; } + /// + /// The PressurizationRate samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("PressurizationRateTable")] public IEnumerable PressurizationRateTable { get; set; } + /// + /// The PressurizationRate samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("PressurizationRateTimeSeries")] public IEnumerable PressurizationRateTimeSeries { get; set; } + /// + /// The ProcessTimer samples reported with the scalar VALUE representation. + /// Amount of time a piece of equipment has performed different types of activities associated with the process being performed at that piece of equipment. + /// [JsonPropertyName("ProcessTimer")] public IEnumerable ProcessTimer { get; set; } + /// + /// The ProcessTimer samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ProcessTimerDataSet")] public IEnumerable ProcessTimerDataSet { get; set; } + /// + /// The ProcessTimer samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ProcessTimerTable")] public IEnumerable ProcessTimerTable { get; set; } + /// + /// The ProcessTimer samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("ProcessTimerTimeSeries")] public IEnumerable ProcessTimerTimeSeries { get; set; } + /// + /// The Resistance samples reported with the scalar VALUE representation. + /// Degree to which a substance opposes the passage of an electric current. + /// [JsonPropertyName("Resistance")] public IEnumerable Resistance { get; set; } + /// + /// The Resistance samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ResistanceDataSet")] public IEnumerable ResistanceDataSet { get; set; } + /// + /// The Resistance samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ResistanceTable")] public IEnumerable ResistanceTable { get; set; } + /// + /// The Resistance samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("ResistanceTimeSeries")] public IEnumerable ResistanceTimeSeries { get; set; } + /// + /// The Resistivity samples reported with the scalar VALUE representation. + /// Inability of a material to conduct electricity. + /// [JsonPropertyName("Resistivity")] public IEnumerable Resistivity { get; set; } + /// + /// The Resistivity samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ResistivityDataSet")] public IEnumerable ResistivityDataSet { get; set; } + /// + /// The Resistivity samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ResistivityTable")] public IEnumerable ResistivityTable { get; set; } + /// + /// The Resistivity samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("ResistivityTimeSeries")] public IEnumerable ResistivityTimeSeries { get; set; } + /// + /// The RotaryVelocity samples reported with the scalar VALUE representation. + /// Rotational speed of a rotary axis. + /// [JsonPropertyName("RotaryVelocity")] public IEnumerable RotaryVelocity { get; set; } + /// + /// The RotaryVelocity samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("RotaryVelocityDataSet")] public IEnumerable RotaryVelocityDataSet { get; set; } + /// + /// The RotaryVelocity samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("RotaryVelocityTable")] public IEnumerable RotaryVelocityTable { get; set; } + /// + /// The RotaryVelocity samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("RotaryVelocityTimeSeries")] public IEnumerable RotaryVelocityTimeSeries { get; set; } + /// + /// The SettlingError samples reported with the scalar VALUE representation. + /// Difference between actual and commanded position at the end of a motion. + /// [JsonPropertyName("SettlingError")] public IEnumerable SettlingError { get; set; } + /// + /// The SettlingError samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("SettlingErrorDataSet")] public IEnumerable SettlingErrorDataSet { get; set; } + /// + /// The SettlingError samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("SettlingErrorTable")] public IEnumerable SettlingErrorTable { get; set; } + /// + /// The SettlingError samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("SettlingErrorTimeSeries")] public IEnumerable SettlingErrorTimeSeries { get; set; } + /// + /// The SettlingErrorAngular samples reported with the scalar VALUE representation. + /// Angular difference between the commanded encoder/resolver position, and the actual encoder/resolver position when motion is complete. + /// [JsonPropertyName("SettlingErrorAngular")] public IEnumerable SettlingErrorAngular { get; set; } + /// + /// The SettlingErrorAngular samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("SettlingErrorAngularDataSet")] public IEnumerable SettlingErrorAngularDataSet { get; set; } + /// + /// The SettlingErrorAngular samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("SettlingErrorAngularTable")] public IEnumerable SettlingErrorAngularTable { get; set; } + /// + /// The SettlingErrorAngular samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("SettlingErrorAngularTimeSeries")] public IEnumerable SettlingErrorAngularTimeSeries { get; set; } + /// + /// The SettlingErrorLinear samples reported with the scalar VALUE representation. + /// Difference between the commanded encoder/resolver position, and the actual encoder/resolver position when motion is complete. + /// [JsonPropertyName("SettlingErrorLinear")] public IEnumerable SettlingErrorLinear { get; set; } + /// + /// The SettlingErrorLinear samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("SettlingErrorLinearDataSet")] public IEnumerable SettlingErrorLinearDataSet { get; set; } + /// + /// The SettlingErrorLinear samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("SettlingErrorLinearTable")] public IEnumerable SettlingErrorLinearTable { get; set; } + /// + /// The SettlingErrorLinear samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("SettlingErrorLinearTimeSeries")] public IEnumerable SettlingErrorLinearTimeSeries { get; set; } + /// + /// The SoundLevel samples reported with the scalar VALUE representation. + /// Sound level or sound pressure level relative to atmospheric pressure. + /// [JsonPropertyName("SoundLevel")] public IEnumerable SoundLevel { get; set; } + /// + /// The SoundLevel samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("SoundLevelDataSet")] public IEnumerable SoundLevelDataSet { get; set; } + /// + /// The SoundLevel samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("SoundLevelTable")] public IEnumerable SoundLevelTable { get; set; } + /// + /// The SoundLevel samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("SoundLevelTimeSeries")] public IEnumerable SoundLevelTimeSeries { get; set; } + /// + /// The SpindleSpeed samples reported with the scalar VALUE representation. + /// Rotational speed of the rotary axis.**DEPRECATED** in *Version 1.2*. Replaced by `ROTARY_VELOCITY`. + /// [JsonPropertyName("SpindleSpeed")] public IEnumerable SpindleSpeed { get; set; } + /// + /// The SpindleSpeed samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("SpindleSpeedDataSet")] public IEnumerable SpindleSpeedDataSet { get; set; } + /// + /// The SpindleSpeed samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("SpindleSpeedTable")] public IEnumerable SpindleSpeedTable { get; set; } + /// + /// The SpindleSpeed samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("SpindleSpeedTimeSeries")] public IEnumerable SpindleSpeedTimeSeries { get; set; } + /// + /// The Strain samples reported with the scalar VALUE representation. + /// Amount of deformation per unit length of an object when a load is applied. + /// [JsonPropertyName("Strain")] public IEnumerable Strain { get; set; } + /// + /// The Strain samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("StrainDataSet")] public IEnumerable StrainDataSet { get; set; } + /// + /// The Strain samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("StrainTable")] public IEnumerable StrainTable { get; set; } + /// + /// The Strain samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("StrainTimeSeries")] public IEnumerable StrainTimeSeries { get; set; } + /// + /// The Temperature samples reported with the scalar VALUE representation. + /// Degree of hotness or coldness measured on a definite scale. + /// [JsonPropertyName("Temperature")] public IEnumerable Temperature { get; set; } + /// + /// The Temperature samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("TemperatureDataSet")] public IEnumerable TemperatureDataSet { get; set; } + /// + /// The Temperature samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("TemperatureTable")] public IEnumerable TemperatureTable { get; set; } + /// + /// The Temperature samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("TemperatureTimeSeries")] public IEnumerable TemperatureTimeSeries { get; set; } + /// + /// The Tension samples reported with the scalar VALUE representation. + /// Force that stretches or elongates an object. + /// [JsonPropertyName("Tension")] public IEnumerable Tension { get; set; } + /// + /// The Tension samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("TensionDataSet")] public IEnumerable TensionDataSet { get; set; } + /// + /// The Tension samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("TensionTable")] public IEnumerable TensionTable { get; set; } + /// + /// The Tension samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("TensionTimeSeries")] public IEnumerable TensionTimeSeries { get; set; } + /// + /// The Tilt samples reported with the scalar VALUE representation. + /// Angular displacement. + /// [JsonPropertyName("Tilt")] public IEnumerable Tilt { get; set; } + /// + /// The Tilt samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("TiltDataSet")] public IEnumerable TiltDataSet { get; set; } + /// + /// The Tilt samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("TiltTable")] public IEnumerable TiltTable { get; set; } + /// + /// The Tilt samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("TiltTimeSeries")] public IEnumerable TiltTimeSeries { get; set; } + /// + /// The Torque samples reported with the scalar VALUE representation. + /// Turning force exerted on an object or by an object. + /// [JsonPropertyName("Torque")] public IEnumerable Torque { get; set; } + /// + /// The Torque samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("TorqueDataSet")] public IEnumerable TorqueDataSet { get; set; } + /// + /// The Torque samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("TorqueTable")] public IEnumerable TorqueTable { get; set; } + /// + /// The Torque samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("TorqueTimeSeries")] public IEnumerable TorqueTimeSeries { get; set; } + /// + /// The Velocity samples reported with the scalar VALUE representation. + /// Rate of change of position of a Component. + /// [JsonPropertyName("Velocity")] public IEnumerable Velocity { get; set; } + /// + /// The Velocity samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("VelocityDataSet")] public IEnumerable VelocityDataSet { get; set; } + /// + /// The Velocity samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("VelocityTable")] public IEnumerable VelocityTable { get; set; } + /// + /// The Velocity samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("VelocityTimeSeries")] public IEnumerable VelocityTimeSeries { get; set; } + /// + /// The Viscosity samples reported with the scalar VALUE representation. + /// Fluid's resistance to flow. + /// [JsonPropertyName("Viscosity")] public IEnumerable Viscosity { get; set; } + /// + /// The Viscosity samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ViscosityDataSet")] public IEnumerable ViscosityDataSet { get; set; } + /// + /// The Viscosity samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ViscosityTable")] public IEnumerable ViscosityTable { get; set; } + /// + /// The Viscosity samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("ViscosityTimeSeries")] public IEnumerable ViscosityTimeSeries { get; set; } + /// + /// The VoltAmpere samples reported with the scalar VALUE representation. + /// Apparent power in an electrical circuit, equal to the product of root-mean-square (RMS) voltage and RMS current (commonly referred to as VA). + /// [JsonPropertyName("VoltAmpere")] public IEnumerable VoltAmpere { get; set; } + /// + /// The VoltAmpere samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("VoltAmpereDataSet")] public IEnumerable VoltAmpereDataSet { get; set; } + /// + /// The VoltAmpere samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("VoltAmpereTable")] public IEnumerable VoltAmpereTable { get; set; } + /// + /// The VoltAmpere samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("VoltAmpereTimeSeries")] public IEnumerable VoltAmpereTimeSeries { get; set; } + /// + /// The VoltAmpereReactive samples reported with the scalar VALUE representation. + /// Reactive power in an AC electrical circuit (commonly referred to as VAR). + /// [JsonPropertyName("VoltAmpereReactive")] public IEnumerable VoltAmpereReactive { get; set; } + /// + /// The VoltAmpereReactive samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("VoltAmpereReactiveDataSet")] public IEnumerable VoltAmpereReactiveDataSet { get; set; } + /// + /// The VoltAmpereReactive samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("VoltAmpereReactiveTable")] public IEnumerable VoltAmpereReactiveTable { get; set; } + /// + /// The VoltAmpereReactive samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("VoltAmpereReactiveTimeSeries")] public IEnumerable VoltAmpereReactiveTimeSeries { get; set; } + /// + /// The Voltage samples reported with the scalar VALUE representation. + /// Electrical potential between two points.**DEPRECATED** in *Version 1.6*. Replaced by `VOLTAGE_AC` and `VOLTAGE_DC`. + /// [JsonPropertyName("Voltage")] public IEnumerable Voltage { get; set; } + /// + /// The Voltage samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("VoltageDataSet")] public IEnumerable VoltageDataSet { get; set; } + /// + /// The Voltage samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("VoltageTable")] public IEnumerable VoltageTable { get; set; } + /// + /// The Voltage samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("VoltageTimeSeries")] public IEnumerable VoltageTimeSeries { get; set; } + /// + /// The VoltageAC samples reported with the scalar VALUE representation. + /// Electrical potential between two points in an electrical circuit in which the current periodically reverses direction. + /// [JsonPropertyName("VoltageAC")] public IEnumerable VoltageAC { get; set; } + /// + /// The VoltageAC samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("VoltageACDataSet")] public IEnumerable VoltageACDataSet { get; set; } + /// + /// The VoltageAC samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("VoltageACTable")] public IEnumerable VoltageACTable { get; set; } + /// + /// The VoltageAC samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("VoltageACTimeSeries")] public IEnumerable VoltageACTimeSeries { get; set; } + /// + /// The VoltageDC samples reported with the scalar VALUE representation. + /// Electrical potential between two points in an electrical circuit in which the current is unidirectional. + /// [JsonPropertyName("VoltageDC")] public IEnumerable VoltageDC { get; set; } + /// + /// The VoltageDC samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("VoltageDCDataSet")] public IEnumerable VoltageDCDataSet { get; set; } + /// + /// The VoltageDC samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("VoltageDCTable")] public IEnumerable VoltageDCTable { get; set; } + /// + /// The VoltageDC samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("VoltageDCTimeSeries")] public IEnumerable VoltageDCTimeSeries { get; set; } + /// + /// The VolumeFluid samples reported with the scalar VALUE representation. + /// Fluid volume of an object or container. + /// [JsonPropertyName("VolumeFluid")] public IEnumerable VolumeFluid { get; set; } + /// + /// The VolumeFluid samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("VolumeFluidDataSet")] public IEnumerable VolumeFluidDataSet { get; set; } + /// + /// The VolumeFluid samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("VolumeFluidTable")] public IEnumerable VolumeFluidTable { get; set; } + /// + /// The VolumeFluid samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("VolumeFluidTimeSeries")] public IEnumerable VolumeFluidTimeSeries { get; set; } + /// + /// The VolumeSpatial samples reported with the scalar VALUE representation. + /// Geometric volume of an object or container. + /// [JsonPropertyName("VolumeSpatial")] public IEnumerable VolumeSpatial { get; set; } + /// + /// The VolumeSpatial samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("VolumeSpatialDataSet")] public IEnumerable VolumeSpatialDataSet { get; set; } + /// + /// The VolumeSpatial samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("VolumeSpatialTable")] public IEnumerable VolumeSpatialTable { get; set; } + /// + /// The VolumeSpatial samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("VolumeSpatialTimeSeries")] public IEnumerable VolumeSpatialTimeSeries { get; set; } + /// + /// The WaterHardness samples reported with the scalar VALUE representation. + /// Concentration of calcium carbonate (CaCO3) in water + /// [JsonPropertyName("WaterHardness")] public IEnumerable WaterHardness { get; set; } + /// + /// The WaterHardness samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("WaterHardnessDataSet")] public IEnumerable WaterHardnessDataSet { get; set; } + /// + /// The WaterHardness samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("WaterHardnessTable")] public IEnumerable WaterHardnessTable { get; set; } + /// + /// The WaterHardness samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("WaterHardnessTimeSeries")] public IEnumerable WaterHardnessTimeSeries { get; set; } + /// + /// The Wattage samples reported with the scalar VALUE representation. + /// Power flowing through or dissipated by an electrical circuit or piece of equipment. + /// [JsonPropertyName("Wattage")] public IEnumerable Wattage { get; set; } + /// + /// The Wattage samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("WattageDataSet")] public IEnumerable WattageDataSet { get; set; } + /// + /// The Wattage samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("WattageTable")] public IEnumerable WattageTable { get; set; } + /// + /// The Wattage samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("WattageTimeSeries")] public IEnumerable WattageTimeSeries { get; set; } + /// + /// The XDimension samples reported with the scalar VALUE representation. + /// Dimension of an entity relative to the X direction of the referenced coordinate system. + /// [JsonPropertyName("XDimension")] public IEnumerable XDimension { get; set; } + /// + /// The XDimension samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("XDimensionDataSet")] public IEnumerable XDimensionDataSet { get; set; } + /// + /// The XDimension samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("XDimensionTable")] public IEnumerable XDimensionTable { get; set; } + /// + /// The XDimension samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("XDimensionTimeSeries")] public IEnumerable XDimensionTimeSeries { get; set; } + /// + /// The YDimension samples reported with the scalar VALUE representation. + /// Dimension of an entity relative to the Y direction of the referenced coordinate system. + /// [JsonPropertyName("YDimension")] public IEnumerable YDimension { get; set; } + /// + /// The YDimension samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("YDimensionDataSet")] public IEnumerable YDimensionDataSet { get; set; } + /// + /// The YDimension samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("YDimensionTable")] public IEnumerable YDimensionTable { get; set; } + /// + /// The YDimension samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("YDimensionTimeSeries")] public IEnumerable YDimensionTimeSeries { get; set; } + /// + /// The ZDimension samples reported with the scalar VALUE representation. + /// Dimension of an entity relative to the Z direction of the referenced coordinate system. + /// [JsonPropertyName("ZDimension")] public IEnumerable ZDimension { get; set; } + /// + /// The ZDimension samples reported with the DATA_SET representation + /// (a set of key/value entries). + /// [JsonPropertyName("ZDimensionDataSet")] public IEnumerable ZDimensionDataSet { get; set; } + /// + /// The ZDimension samples reported with the TABLE representation + /// (a set of keyed rows of cells). + /// [JsonPropertyName("ZDimensionTable")] public IEnumerable ZDimensionTable { get; set; } + /// + /// The ZDimension samples reported with the TIME_SERIES representation + /// (a sequence of values sampled at a fixed rate). + /// [JsonPropertyName("ZDimensionTimeSeries")] public IEnumerable ZDimensionTimeSeries { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonSamples() { } + /// + /// Initializes a new instance from a flat sequence of , + /// routing each one into the typed collection matching its MTConnect type and + /// representation. + /// public JsonSamples(IEnumerable observations) { if (observations != null) @@ -6401,5 +7939,5 @@ public JsonSamples(IEnumerable observations) } } } - } -} \ No newline at end of file + } +} diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonStreams.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonStreams.cs index 2fc210780..c3b4209e3 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonStreams.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonStreams.cs @@ -7,14 +7,29 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for a typed container of device + /// streams inside MTConnectStreams, keyed by the singular + /// cppagent element name DeviceStream. + /// public class JsonStreams { + /// + /// The device streams in the document. + /// [JsonPropertyName("DeviceStream")] public List DeviceStreams { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonStreams() { } + /// + /// Initializes the container from a strongly-typed streams + /// document. + /// public JsonStreams(IStreamsResponseOutputDocument streamsDocument) { if (streamsDocument != null) @@ -34,6 +49,10 @@ public JsonStreams(IStreamsResponseOutputDocument streamsDocument) } + /// + /// Flattens the container back into a uniform + /// sequence. + /// public IEnumerable ToStreams() { if (!DeviceStreams.IsNullOrEmpty()) diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonStreamsHeader.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonStreamsHeader.cs index 8aea7a4f5..13c4f1768 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonStreamsHeader.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonStreamsHeader.cs @@ -7,11 +7,22 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for the Header of an + /// MTConnectStreams document in the cppagent-compatible shape. + /// public class JsonStreamsHeader { + /// + /// The instance identifier of the agent, which changes whenever the + /// agent's buffer is cleared. + /// [JsonPropertyName("instanceId")] public ulong InstanceId { get; set; } + /// + /// The agent's version. + /// [JsonPropertyName("version")] public string Version { get; set; } @@ -22,24 +33,46 @@ public class JsonStreamsHeader [JsonPropertyName("schemaVersion")] public string SchemaVersion { get; set; } + /// + /// The identifier of the agent that produced the document. + /// [JsonPropertyName("sender")] public string Sender { get; set; } + /// + /// The maximum number of observations the agent's buffer can hold. + /// [JsonPropertyName("bufferSize")] public ulong BufferSize { get; set; } + /// + /// The sequence number of the oldest observation still in the buffer. + /// [JsonPropertyName("firstSequence")] public ulong FirstSequence { get; set; } + /// + /// The sequence number of the newest observation in the buffer. + /// [JsonPropertyName("lastSequence")] public ulong LastSequence { get; set; } + /// + /// The sequence number the next observation will be assigned. + /// [JsonPropertyName("nextSequence")] public ulong NextSequence { get; set; } + /// + /// The timestamp of the most recent change to the device model. + /// [JsonPropertyName("deviceModelChangeTime")] public string DeviceModelChangeTime { get; set; } + /// + /// Whether the document was produced for testing rather than + /// production use. + /// [JsonPropertyName("testIndicator")] public bool TestIndicator { get; set; } @@ -50,12 +83,22 @@ public class JsonStreamsHeader [JsonPropertyName("validation")] public bool Validation { get; set; } + /// + /// The time the document was created. + /// [JsonPropertyName("creationTime")] public DateTime CreationTime { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonStreamsHeader() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonStreamsHeader(IMTConnectStreamsHeader header) { if (header != null) @@ -76,6 +119,10 @@ public JsonStreamsHeader(IMTConnectStreamsHeader header) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public virtual IMTConnectStreamsHeader ToStreamsHeader() { var header = new MTConnectStreamsHeader(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonStreamsResponseDocument.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonStreamsResponseDocument.cs index 9f789ba0e..eb6a99bc5 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonStreamsResponseDocument.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonStreamsResponseDocument.cs @@ -6,14 +6,30 @@ namespace MTConnect.Streams.Json { + /// + /// Outer JSON envelope for a Streams response document in the + /// cppagent-compatible shape, with the actual content wrapped in a + /// single MTConnectStreams property to mirror the XML root + /// element name. + /// public class JsonStreamsResponseDocument { + /// + /// The wrapped streams document. + /// [JsonPropertyName("MTConnectStreams")] public JsonMTConnectStreams MTConnectStreams { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonStreamsResponseDocument() { } + /// + /// Initializes the envelope from a strongly-typed streams + /// document. + /// public JsonStreamsResponseDocument(IStreamsResponseOutputDocument streamsDocument) { if (streamsDocument != null) @@ -23,6 +39,11 @@ public JsonStreamsResponseDocument(IStreamsResponseOutputDocument streamsDocumen } + /// + /// Unwraps the envelope and converts it to a strongly-typed + /// streams document, returning null when the envelope is + /// empty. + /// public IStreamsResponseDocument ToStreamsDocument() { if (MTConnectStreams != null) diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonTableEntries.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonTableEntries.cs index 632ee3dca..10f30b13a 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonTableEntries.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonTableEntries.cs @@ -12,36 +12,81 @@ namespace MTConnect.NET_JSON_cppagent.Streams { + /// + /// JSON serialization surrogate for the keyed table of cell-maps + /// carried by a TABLE observation in the cppagent-compatible shape. + /// Each row is a JSON object whose properties are the cell values + /// (numeric or string, inferred per cell), keyed by row identifier on + /// the outer object. The unavailable state collapses to the string + /// UNAVAILABLE. + /// [JsonConverter(typeof(JsonTableEntriesConverter))] public class JsonTableEntries { + /// + /// The table rows keyed by row identifier; each row is a map of + /// cell name to cell value. + /// public Dictionary> Entries { get; set; } + /// + /// The number of rows, captured at construction for round-trip + /// and inspection convenience. + /// public int Count { get; set; } + /// + /// True when the underlying table observation reported the + /// UNAVAILABLE sentinel rather than a set of rows. + /// public bool IsUnavailable { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonTableEntries() { } - public JsonTableEntries(bool isUnavailable) + /// + /// Initializes an unavailable-marker instance that will be + /// serialized as the string UNAVAILABLE. + /// + public JsonTableEntries(bool isUnavailable) { IsUnavailable = isUnavailable; } + /// + /// Initializes the surrogate from a nested dictionary of rows, + /// also caching the row count. + /// public JsonTableEntries(Dictionary> entries) - { + { Entries = entries; Count = entries != null ? entries.Count : 0; } + /// + /// that reads and writes + /// as either a nested JSON object + /// or the UNAVAILABLE string sentinel. + /// public class JsonTableEntriesConverter : JsonConverter { #if NET5_0_OR_GREATER + /// + /// Returns true so the converter is invoked for null + /// or unavailable JSON values. + /// public override bool HandleNull => true; #endif + /// + /// Reads a nested JSON object into a + /// , returning null when + /// the token is not an object (the unavailable sentinel case). + /// public override JsonTableEntries Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options) { if (reader.TokenType == JsonTokenType.StartObject) @@ -60,6 +105,12 @@ public override JsonTableEntries Read(ref Utf8JsonReader reader, Type typeToConv return null; } + /// + /// Writes the surrogate as a nested JSON object whose row + /// cell values are inferred per cell (number vs. string), or + /// as the UNAVAILABLE string sentinel when no rows are + /// available. + /// public override void Write(Utf8JsonWriter writer, JsonTableEntries value, JsonSerializerOptions options) { if (value != null && !value.IsUnavailable) @@ -71,7 +122,7 @@ public override void Write(Utf8JsonWriter writer, JsonTableEntries value, JsonSe foreach (var entry in value.Entries) { writer.WritePropertyName(entry.Key); - + if (!entry.Value.IsNullOrEmpty()) { writer.WriteStartObject(); diff --git a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonTimeSeriesSamples.cs b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonTimeSeriesSamples.cs index e99f87c0c..d428c3ade 100644 --- a/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonTimeSeriesSamples.cs +++ b/libraries/MTConnect.NET-JSON-cppagent/Streams/JsonTimeSeriesSamples.cs @@ -13,23 +13,52 @@ namespace MTConnect.NET_JSON_cppagent.Streams { + /// + /// JSON serialization surrogate for the array of samples carried by a + /// TIME_SERIES observation in the cppagent-compatible shape. The + /// samples are serialized as a bare JSON array of numbers rather than + /// an object, with the unavailable state collapsed to the string + /// UNAVAILABLE. + /// [JsonConverter(typeof(JsonTimeSeriesSamplesConverter))] public class JsonTimeSeriesSamples { + /// + /// The series of sample values. + /// public IEnumerable Samples { get; set; } + /// + /// The number of samples in the series, captured at construction + /// for round-trip and inspection convenience. + /// public int Count { get; set; } + /// + /// True when the underlying time-series observation reported the + /// UNAVAILABLE sentinel rather than a numeric series. + /// public bool IsUnavailable { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonTimeSeriesSamples() { } - public JsonTimeSeriesSamples(bool isUnavailable) + /// + /// Initializes an unavailable-marker instance that will be + /// serialized as the string UNAVAILABLE. + /// + public JsonTimeSeriesSamples(bool isUnavailable) { IsUnavailable = isUnavailable; } + /// + /// Initializes the surrogate from a sequence of sample values, + /// also caching the sample count. + /// public JsonTimeSeriesSamples(IEnumerable samples) { Samples = samples; @@ -37,12 +66,28 @@ public JsonTimeSeriesSamples(IEnumerable samples) } + /// + /// that reads and writes + /// as either a numeric JSON + /// array or the UNAVAILABLE string sentinel. + /// public class JsonTimeSeriesSamplesConverter : JsonConverter { #if NET5_0_OR_GREATER + /// + /// Returns true so the converter is invoked for null + /// or unavailable JSON values, allowing it to emit the + /// UNAVAILABLE sentinel. + /// public override bool HandleNull => true; #endif + /// + /// Reads a JSON numeric array into a + /// , returning + /// null when the token is not an array (the unavailable + /// sentinel case). + /// public override JsonTimeSeriesSamples Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options) { if (reader.TokenType == JsonTokenType.StartArray) @@ -61,6 +106,11 @@ public override JsonTimeSeriesSamples Read(ref Utf8JsonReader reader, Type typeT return null; } + /// + /// Writes the surrogate as a JSON numeric array, or as the + /// UNAVAILABLE string sentinel when no samples are + /// available. + /// public override void Write(Utf8JsonWriter writer, JsonTimeSeriesSamples value, JsonSerializerOptions options) { if (value != null && !value.IsUnavailable) diff --git a/libraries/MTConnect.NET-JSON/Assets/ComponentConfigurationParameters/JsonComponentConfigurationParametersAsset.cs b/libraries/MTConnect.NET-JSON/Assets/ComponentConfigurationParameters/JsonComponentConfigurationParametersAsset.cs index feaf47f39..45ebeeece 100644 --- a/libraries/MTConnect.NET-JSON/Assets/ComponentConfigurationParameters/JsonComponentConfigurationParametersAsset.cs +++ b/libraries/MTConnect.NET-JSON/Assets/ComponentConfigurationParameters/JsonComponentConfigurationParametersAsset.cs @@ -8,35 +8,73 @@ namespace MTConnect.Assets.Json.ComponentConfigurationParameters { + /// + /// JSON serialization surrogate for an MTConnect + /// ComponentConfigurationParameters asset, which carries named + /// parameter sets for a component. Mirrors the on-the-wire shape so the + /// JSON serializer can read and write it, then converts to and from the + /// strongly-typed + /// model. + /// public class JsonComponentConfigurationParametersAsset { + /// + /// The unique identifier of the asset. + /// [JsonPropertyName("assetId")] public string AssetId { get; set; } + /// + /// The asset type identifier, ComponentConfigurationParameters. + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The timestamp at which the asset was last reported. + /// [JsonPropertyName("timestamp")] public DateTime Timestamp { get; set; } + /// + /// The UUID of the device the asset is associated with. + /// [JsonPropertyName("deviceUuid")] public string DeviceUuid { get; set; } + /// + /// Whether the asset has been removed from the agent. + /// [JsonPropertyName("removed")] public bool Removed { get; set; } + /// + /// The free-form description of the asset. + /// [JsonPropertyName("description")] public string Description { get; set; } + /// + /// The named parameter sets defined for the component. + /// [JsonPropertyName("parameterSets")] public IEnumerable ParameterSets { get; set; } - public JsonComponentConfigurationParametersAsset() + /// + /// Initializes an empty instance for JSON deserialization, defaulting + /// to the ComponentConfigurationParameters type + /// identifier. + /// + public JsonComponentConfigurationParametersAsset() { Type = ComponentConfigurationParametersAsset.TypeId; } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonComponentConfigurationParametersAsset(IComponentConfigurationParametersAsset asset) { if (asset != null) @@ -57,6 +95,11 @@ public JsonComponentConfigurationParametersAsset(IComponentConfigurationParamete } + /// + /// Converts this surrogate to a strongly-typed + /// , converting + /// each parameter set. + /// public IComponentConfigurationParametersAsset ToComponentConfigurationParametersAsset() { var asset = new ComponentConfigurationParametersAsset(); diff --git a/libraries/MTConnect.NET-JSON/Assets/ComponentConfigurationParameters/JsonParameter.cs b/libraries/MTConnect.NET-JSON/Assets/ComponentConfigurationParameters/JsonParameter.cs index 9e046a054..4e7797a88 100644 --- a/libraries/MTConnect.NET-JSON/Assets/ComponentConfigurationParameters/JsonParameter.cs +++ b/libraries/MTConnect.NET-JSON/Assets/ComponentConfigurationParameters/JsonParameter.cs @@ -6,32 +6,66 @@ namespace MTConnect.Assets.Json.ComponentConfigurationParameters { + /// + /// JSON serialization surrogate for a Parameter within a + /// ComponentConfigurationParameters asset. Mirrors the on-the-wire shape so + /// the JSON serializer can read and write it, then converts to and from the + /// strongly-typed model. + /// public class JsonParameter { + /// + /// The identifier of the parameter within its set. + /// [JsonPropertyName("identifier")] public string Identifier { get; set; } + /// + /// The human-readable name of the parameter. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The maximum permitted value. + /// [JsonPropertyName("maximum")] public double? Maximum { get; set; } + /// + /// The minimum permitted value. + /// [JsonPropertyName("minimum")] public double? Minimum { get; set; } + /// + /// The nominal (target) value. + /// [JsonPropertyName("nominal")] public double? Nominal { get; set; } + /// + /// The engineering units the parameter is expressed in. + /// [JsonPropertyName("units")] public string Units { get; set; } + /// + /// The current value of the parameter. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonParameter() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonParameter(IParameter parameter) { if (parameter != null) @@ -47,6 +81,9 @@ public JsonParameter(IParameter parameter) } + /// + /// Converts this surrogate to a strongly-typed . + /// public IParameter ToParameter() { var parameter = new Parameter(); diff --git a/libraries/MTConnect.NET-JSON/Assets/ComponentConfigurationParameters/JsonParameterSet.cs b/libraries/MTConnect.NET-JSON/Assets/ComponentConfigurationParameters/JsonParameterSet.cs index 1f694e72f..d83b9d0e0 100644 --- a/libraries/MTConnect.NET-JSON/Assets/ComponentConfigurationParameters/JsonParameterSet.cs +++ b/libraries/MTConnect.NET-JSON/Assets/ComponentConfigurationParameters/JsonParameterSet.cs @@ -7,17 +7,36 @@ namespace MTConnect.Assets.Json.ComponentConfigurationParameters { + /// + /// JSON serialization surrogate for a ParameterSet, a named group + /// of parameters within a ComponentConfigurationParameters asset. + /// Converts to and from the strongly-typed + /// model. + /// public class JsonParameterSet { + /// + /// The name of the parameter set. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The parameters in the set. + /// [JsonPropertyName("parameters")] public IEnumerable Parameters { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonParameterSet() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , converting each parameter. + /// public JsonParameterSet(IParameterSet parameterSet) { if (parameterSet != null) @@ -30,13 +49,17 @@ public JsonParameterSet(IParameterSet parameterSet) foreach (var parameter in parameterSet.Parameters) { jsonParameters.Add(new JsonParameter(parameter)); - } + } Parameters = jsonParameters; } } } + /// + /// Converts this surrogate to a strongly-typed + /// , converting each parameter. + /// public IParameterSet ToParameterSet() { var parameterSet = new ParameterSet(); diff --git a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingItem.cs b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingItem.cs index 673432d50..35680015b 100644 --- a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingItem.cs +++ b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingItem.cs @@ -8,41 +8,87 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a CuttingItem, an individual + /// insert or cutting edge of a cutting tool. Mirrors the on-the-wire shape + /// so the JSON serializer can read and write it, then converts to and from + /// the strongly-typed model. + /// public class JsonCuttingItem { + /// + /// The index or range of indices identifying the cutting item's + /// position on the tool. + /// [JsonPropertyName("indices")] public string Indices { get; set; } + /// + /// The unique identifier of the cutting item. + /// [JsonPropertyName("itemId")] public string ItemId { get; set; } + /// + /// The manufacturers of the cutting item. + /// [JsonPropertyName("manufacturers")] public IEnumerable Manufacturers { get; set; } + /// + /// The material grade of the cutting item. + /// [JsonPropertyName("grade")] public string Grade { get; set; } + /// + /// The free-form description of the cutting item. + /// [JsonPropertyName("description")] public string Description { get; set; } + /// + /// The location of the cutting item relative to the tool. + /// [JsonPropertyName("locus")] public string Locus { get; set; } + /// + /// The program tool group the cutting item is assigned to. + /// [JsonPropertyName("programToolGroup")] public string ProgramToolGroup { get; set; } + /// + /// The measured and remaining life values of the cutting item. + /// [JsonPropertyName("itemLife")] public IEnumerable ItemLife { get; set; } + /// + /// The status values of the cutting item (for example NEW or USED), + /// serialized as enumeration names. + /// [JsonPropertyName("cutterStatus")] public IEnumerable CutterStatus { get; set; } + /// + /// The dimensional measurements of the cutting item. + /// [JsonPropertyName("measurements")] public IEnumerable Measurements { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCuttingItem() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , converting cutter statuses to strings + /// and each nested item life and measurement. + /// public JsonCuttingItem(ICuttingItem cuttingItem) { if (cuttingItem != null) @@ -91,6 +137,11 @@ public JsonCuttingItem(ICuttingItem cuttingItem) } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing cutter statuses and converting + /// each nested item life and measurement. + /// public ICuttingItem ToCuttingItem() { var cuttingItem = new CuttingItem(); diff --git a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingItemCollection.cs b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingItemCollection.cs index 2542f81d9..6defeec26 100644 --- a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingItemCollection.cs +++ b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingItemCollection.cs @@ -8,18 +8,37 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for the CuttingItems collection of + /// a cutting tool, including the redundant count attribute so consumers + /// can validate the cardinality without enumerating the collection. + /// public class JsonCuttingItemCollection { + /// + /// The number of cutting items in . + /// [JsonPropertyName("count")] public int Count { get; set; } + /// + /// The cutting items of the tool. + /// [JsonPropertyName("cuttingItems")] public IEnumerable CuttingItems { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCuttingItemCollection() { } + /// + /// Initializes the surrogate from a strongly-typed cutting item + /// collection, populating both and + /// . + /// public JsonCuttingItemCollection(IEnumerable cuttingItems) { if (!cuttingItems.IsNullOrEmpty()) @@ -40,6 +59,10 @@ public JsonCuttingItemCollection(IEnumerable cuttingItems) } + /// + /// Converts the surrogate cutting items back to their strongly-typed + /// form, or null when the collection is empty. + /// public IEnumerable ToCuttingItems() { // CuttingItems diff --git a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingToolArchetype.cs b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingToolArchetype.cs index b77ff70b3..ba39fb909 100644 --- a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingToolArchetype.cs +++ b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingToolArchetype.cs @@ -6,14 +6,30 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a CuttingToolArchetype asset, + /// the template cutting tool definition that cutting tool instances refer + /// to. Converts to and from the strongly-typed + /// model. + /// public class JsonCuttingToolArchetype { + /// + /// The cutting tool definition declared by the archetype. + /// [JsonPropertyName("cuttingToolDefinition")] public JsonCuttingToolDefinition CuttingToolDefinition { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCuttingToolArchetype() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonCuttingToolArchetype(ICuttingToolArchetypeAsset cuttingToolArchetype) { if (cuttingToolArchetype != null) @@ -23,6 +39,10 @@ public JsonCuttingToolArchetype(ICuttingToolArchetypeAsset cuttingToolArchetype) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public ICuttingToolArchetypeAsset ToCuttingToolArchetype() { var cuttingToolArchetype = new CuttingToolArchetypeAsset(); diff --git a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingToolArchetypeReference.cs b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingToolArchetypeReference.cs index 1c52cda83..e29e2746c 100644 --- a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingToolArchetypeReference.cs +++ b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingToolArchetypeReference.cs @@ -6,17 +6,36 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a CuttingToolArchetypeReference, + /// a pointer from a cutting tool asset to the archetype it is an instance + /// of. Converts to and from the strongly-typed + /// model. + /// public class JsonCuttingToolArchetypeReference { + /// + /// The source of the archetype reference. + /// [JsonPropertyName("source")] public string Source { get; set; } + /// + /// The archetype identifier. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCuttingToolArchetypeReference() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonCuttingToolArchetypeReference(ICuttingToolArchetypeReference cuttingToolArchetypeReference) { if (cuttingToolArchetypeReference != null) @@ -27,6 +46,10 @@ public JsonCuttingToolArchetypeReference(ICuttingToolArchetypeReference cuttingT } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public ICuttingToolArchetypeReference ToCuttingToolArchetypeReference() { var location = new CuttingToolArchetypeReference(); diff --git a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingToolAsset.cs b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingToolAsset.cs index 2e40a910a..ba35fca7f 100644 --- a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingToolAsset.cs +++ b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingToolAsset.cs @@ -8,51 +8,104 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for an MTConnect CuttingTool asset. + /// Mirrors the on-the-wire shape so the JSON serializer can read and write + /// it, then converts to and from the strongly-typed + /// model. + /// public class JsonCuttingToolAsset { + /// + /// The unique identifier of the asset. + /// [JsonPropertyName("assetId")] public string AssetId { get; set; } + /// + /// The asset type identifier, CuttingTool. + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The timestamp at which the asset was last reported. + /// [JsonPropertyName("timestamp")] public DateTime Timestamp { get; set; } + /// + /// The instance identifier of the agent that produced this asset. + /// [JsonPropertyName("instanceId")] public ulong InstanceId { get; set; } + /// + /// The UUID of the device the asset is associated with. + /// [JsonPropertyName("deviceUuid")] public string DeviceUuid { get; set; } + /// + /// Whether the asset has been removed from the agent. + /// [JsonPropertyName("removed")] public bool Removed { get; set; } + /// + /// The free-form description of the asset. + /// [JsonPropertyName("description")] public string Description { get; set; } + /// + /// The serial number that uniquely identifies the cutting tool. + /// [JsonPropertyName("serialNumber")] public string SerialNumber { get; set; } + /// + /// The identifier of the tool's definition. + /// [JsonPropertyName("toolId")] public string ToolId { get; set; } + /// + /// The manufacturers of the cutting tool. + /// [JsonPropertyName("manufacturers")] public IEnumerable Manufacturers { get; set; } + /// + /// The life cycle state of the cutting tool, including its measurements + /// and remaining life. + /// [JsonPropertyName("cuttingToolLifeCycle")] public JsonCuttingToolLifeCycle CuttingToolLifeCycle { get; set; } + /// + /// The reference to the cutting tool archetype this asset is an + /// instance of. + /// [JsonPropertyName("cuttingToolArchetypeReference")] public JsonCuttingToolArchetypeReference CuttingToolArchetypeReference { get; set; } - public JsonCuttingToolAsset() + /// + /// Initializes an empty instance for JSON deserialization, defaulting + /// to the CuttingTool type identifier. + /// + public JsonCuttingToolAsset() { Type = CuttingToolAsset.TypeId; } + /// + /// Initializes the surrogate from a strongly-typed + /// , converting the life cycle and + /// archetype reference. + /// public JsonCuttingToolAsset(ICuttingToolAsset asset) { if (asset != null) @@ -76,6 +129,11 @@ public JsonCuttingToolAsset(ICuttingToolAsset asset) } + /// + /// Converts this surrogate to a strongly-typed + /// , converting the life cycle and + /// archetype reference. + /// public ICuttingToolAsset ToCuttingToolAsset() { var asset = new CuttingToolAsset(); diff --git a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingToolDefinition.cs b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingToolDefinition.cs index 7abd7ec85..49acbe8f2 100644 --- a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingToolDefinition.cs +++ b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingToolDefinition.cs @@ -6,14 +6,30 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a CuttingToolDefinition, which + /// declares the format of a cutting tool's payload. Converts to and from + /// the strongly-typed model. + /// public class JsonCuttingToolDefinition { + /// + /// The format of the cutting tool definition, serialized as the + /// enumeration name. + /// [JsonPropertyName("format")] public string Format { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCuttingToolDefinition() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonCuttingToolDefinition(ICuttingToolDefinition cuttingToolDefinition) { if (cuttingToolDefinition != null) @@ -23,6 +39,10 @@ public JsonCuttingToolDefinition(ICuttingToolDefinition cuttingToolDefinition) } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing the format enumeration. + /// public CuttingToolDefinition ToCuttingToolDefinition() { var cuttingToolDefinition = new CuttingToolDefinition(); diff --git a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingToolLifeCycle.cs b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingToolLifeCycle.cs index 9c0f1c135..8be0527b0 100644 --- a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingToolLifeCycle.cs +++ b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonCuttingToolLifeCycle.cs @@ -8,44 +8,93 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a CuttingToolLifeCycle, the + /// in-service state of a cutting tool. Mirrors the on-the-wire shape so the + /// JSON serializer can read and write it, then converts to and from the + /// strongly-typed model. + /// public class JsonCuttingToolLifeCycle { + /// + /// The status values of the cutting tool (for example NEW, USED, or + /// EXPIRED), serialized as enumeration names. + /// [JsonPropertyName("cutterStatus")] public IEnumerable CutterStatus { get; set; } + /// + /// The number of times the tool has been reconditioned. + /// [JsonPropertyName("reconditionCount")] public JsonReconditionCount ReconditionCount { get; set; } + /// + /// The measured and remaining tool life values. + /// [JsonPropertyName("toolLife")] public IEnumerable ToolLife { get; set; } + /// + /// The location of the tool in the machine, such as a pot or spindle. + /// [JsonPropertyName("location")] public JsonLocation Location { get; set; } + /// + /// The program tool group the tool is assigned to. + /// [JsonPropertyName("programToolGroup")] public string ProgramToolGroup { get; set; } + /// + /// The program tool number the tool is referenced by. + /// [JsonPropertyName("programToolNumber")] public string ProgramToolNumber { get; set; } + /// + /// The spindle speed limits the tool is intended to operate within. + /// [JsonPropertyName("processSpindleSpeed")] public JsonProcessSpindleSpeed ProcessSpindleSpeed { get; set; } + /// + /// The feed rate limits the tool is intended to operate within. + /// [JsonPropertyName("processFeedRate")] public JsonProcessFeedrate ProcessFeedRate { get; set; } + /// + /// The connection code identifying the machine-side interface of the + /// tool. + /// [JsonPropertyName("connectionCodeMachineSide")] public string ConnectionCodeMachineSide { get; set; } + /// + /// The dimensional measurements of the tool assembly. + /// [JsonPropertyName("measurements")] public IEnumerable Measurements { get; set; } + /// + /// The cutting items (inserts or edges) making up the tool. + /// [JsonPropertyName("cuttingItems")] public JsonCuttingItemCollection CuttingItems { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCuttingToolLifeCycle() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , converting cutter statuses to + /// strings and each nested measurement, tool life, and cutting item. + /// public JsonCuttingToolLifeCycle(ICuttingToolLifeCycle cuttingToolLifeCycle) { if (cuttingToolLifeCycle != null) @@ -100,6 +149,11 @@ public JsonCuttingToolLifeCycle(ICuttingToolLifeCycle cuttingToolLifeCycle) } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing cutter statuses and + /// converting each nested measurement, tool life, and cutting item. + /// public ICuttingToolLifeCycle ToCuttingToolLifeCycle() { var cuttingToolLifeCycle = new CuttingToolLifeCycle(); diff --git a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonItemLife.cs b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonItemLife.cs index 920551a0d..cb2a58fc9 100644 --- a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonItemLife.cs +++ b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonItemLife.cs @@ -6,29 +6,61 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a cutting tool ItemLife, the + /// life measurement of an individual cutting item. Mirrors the on-the-wire + /// shape so the JSON serializer can read and write it, then converts to + /// and from the strongly-typed model. + /// public class JsonItemLife { + /// + /// The current item life value. + /// [JsonPropertyName("value")] public double Value { get; set; } + /// + /// The type of life being measured (MINUTES, PART_COUNT, or WEAR). + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The direction the value counts in (UP or DOWN). + /// [JsonPropertyName("countDirection")] public string CountDirection { get; set; } + /// + /// The value at which a warning is raised. + /// [JsonPropertyName("warning")] public double? Warning { get; set; } + /// + /// The value at which the cutting item reaches the end of its usable + /// life. + /// [JsonPropertyName("limit")] public double? Limit { get; set; } + /// + /// The value the item life started at. + /// [JsonPropertyName("initial")] public double? Initial { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonItemLife() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , converting enumerations to strings. + /// public JsonItemLife(IItemLife itemLife) { if (itemLife != null) @@ -43,6 +75,10 @@ public JsonItemLife(IItemLife itemLife) } + /// + /// Converts this surrogate to a strongly-typed , + /// parsing the type and count direction enumerations. + /// public IItemLife ToItemLife() { var itemLife = new ItemLife(); diff --git a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonLocation.cs b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonLocation.cs index e1cec9340..64b873a71 100644 --- a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonLocation.cs +++ b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonLocation.cs @@ -6,23 +6,51 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a cutting tool Location, the + /// position of the tool in the machine. Mirrors the on-the-wire shape so + /// the JSON serializer can read and write it, then converts to and from + /// the strongly-typed model. + /// public class JsonLocation { + /// + /// The location identifier (for example a pot or station number). + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// The kind of location (for example POT, STATION, or SPINDLE). + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The number of adjacent locations occupied in the positive + /// direction by an oversized tool. + /// [JsonPropertyName("positiveOverlap")] public int? PositiveOverlap { get; set; } + /// + /// The number of adjacent locations occupied in the negative + /// direction by an oversized tool. + /// [JsonPropertyName("negativeOverlap")] public int? NegativeOverlap { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonLocation() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , converting the type enumeration to a + /// string. + /// public JsonLocation(ILocation location) { if (location != null) @@ -35,6 +63,10 @@ public JsonLocation(ILocation location) } + /// + /// Converts this surrogate to a strongly-typed , + /// parsing the type enumeration. + /// public ILocation ToLocation() { var location = new Location(); diff --git a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonMeasurement.cs b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonMeasurement.cs index 0891d5206..ce33d94f9 100644 --- a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonMeasurement.cs +++ b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonMeasurement.cs @@ -6,38 +6,80 @@ namespace MTConnect.Assets.Json.CuttingTools.Measurements { + /// + /// JSON serialization surrogate for a cutting tool Measurement. + /// Mirrors the on-the-wire shape so the JSON serializer can read and write + /// it, then converts to and from the strongly-typed + /// model. + /// public class JsonMeasurement { + /// + /// The measurement type (for example CuttingDiameter or + /// OverallToolLength). + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The measured value. + /// [JsonPropertyName("value")] public double? Value { get; set; } + /// + /// The number of significant digits in the measured value. + /// [JsonPropertyName("significantDigits")] public int? SignificantDigits { get; set; } + /// + /// The engineering units the measurement is expressed in. + /// [JsonPropertyName("units")] public string Units { get; set; } + /// + /// The units the measurement is natively reported in, prior to + /// conversion to . + /// [JsonPropertyName("nativeUnits")] public string NativeUnits { get; set; } + /// + /// The standardized code identifying the measurement. + /// [JsonPropertyName("code")] public string Code { get; set; } + /// + /// The maximum value within tolerance. + /// [JsonPropertyName("maximum")] public double? Maximum { get; set; } + /// + /// The minimum value within tolerance. + /// [JsonPropertyName("minimum")] public double? Minimum { get; set; } + /// + /// The nominal (target) value. + /// [JsonPropertyName("nominal")] public double? Nominal { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonMeasurement() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonMeasurement(IToolingMeasurement measurement) { if (measurement != null) @@ -55,6 +97,11 @@ public JsonMeasurement(IToolingMeasurement measurement) } + /// + /// Converts this surrogate to a strongly-typed + /// , instantiating the concrete + /// measurement subtype for . + /// public IToolingMeasurement ToMeasurement() { var measurement = new ToolingMeasurement(); diff --git a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonProcessFeedrate.cs b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonProcessFeedrate.cs index 71a1c5ac5..6bcb92fd0 100644 --- a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonProcessFeedrate.cs +++ b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonProcessFeedrate.cs @@ -6,20 +6,41 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a cutting tool ProcessFeedRate, + /// the feed rate limits the tool is intended to operate within. Converts to + /// and from the strongly-typed model. + /// public class JsonProcessFeedrate { + /// + /// The maximum feed rate the tool may be operated at. + /// [JsonPropertyName("maximum")] public double? Maximum { get; set; } + /// + /// The minimum feed rate the tool may be operated at. + /// [JsonPropertyName("minimum")] public double? Minimum { get; set; } + /// + /// The nominal (recommended) feed rate for the tool. + /// [JsonPropertyName("nominal")] public double? Nominal { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonProcessFeedrate() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonProcessFeedrate(IProcessFeedRate processFeedrate) { if (processFeedrate != null) @@ -31,6 +52,10 @@ public JsonProcessFeedrate(IProcessFeedRate processFeedrate) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IProcessFeedRate ToProcessFeedrate() { var processFeedrate = new ProcessFeedRate(); diff --git a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonProcessSpindleSpeed.cs b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonProcessSpindleSpeed.cs index 521d49104..63654f1c5 100644 --- a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonProcessSpindleSpeed.cs +++ b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonProcessSpindleSpeed.cs @@ -6,23 +6,49 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a cutting tool + /// ProcessSpindleSpeed, the spindle speed limits the tool is + /// intended to operate within. Mirrors the on-the-wire shape so the JSON + /// serializer can read and write it, then converts to and from the + /// strongly-typed model. + /// public class JsonProcessSpindleSpeed { + /// + /// The maximum spindle speed the tool may be operated at. + /// [JsonPropertyName("maximum")] public double? Maximum { get; set; } + /// + /// The minimum spindle speed the tool may be operated at. + /// [JsonPropertyName("minimum")] public double? Minimum { get; set; } + /// + /// The nominal (recommended) spindle speed for the tool. + /// [JsonPropertyName("nominal")] public double? Nominal { get; set; } + /// + /// The spindle speed value. + /// [JsonPropertyName("value")] public double? Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonProcessSpindleSpeed() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonProcessSpindleSpeed(IProcessSpindleSpeed processSpindleSpeed) { if (processSpindleSpeed != null) @@ -35,6 +61,10 @@ public JsonProcessSpindleSpeed(IProcessSpindleSpeed processSpindleSpeed) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IProcessSpindleSpeed ToProcessSpindleSpeed() { var processSpindleSpeed = new ProcessSpindleSpeed(); diff --git a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonReconditionCount.cs b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonReconditionCount.cs index 37cbfc052..4447f2fc2 100644 --- a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonReconditionCount.cs +++ b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonReconditionCount.cs @@ -6,17 +6,36 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a ReconditionCount, recording + /// how many times a cutting tool has been reconditioned and the maximum + /// permitted. Converts to and from the strongly-typed + /// model. + /// public class JsonReconditionCount { + /// + /// The maximum number of times the tool may be reconditioned. + /// [JsonPropertyName("maximumCount")] public int? MaximumCount { get; set; } + /// + /// The number of times the tool has been reconditioned so far. + /// [JsonPropertyName("value")] public int? Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonReconditionCount() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonReconditionCount(IReconditionCount reconditionCount) { if (reconditionCount != null) @@ -27,6 +46,10 @@ public JsonReconditionCount(IReconditionCount reconditionCount) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IReconditionCount ToReconditionCount() { var reconditionCount = new ReconditionCount(); diff --git a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonToolLife.cs b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonToolLife.cs index 02c5508a5..c51b49225 100644 --- a/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonToolLife.cs +++ b/libraries/MTConnect.NET-JSON/Assets/CuttingTools/JsonToolLife.cs @@ -6,29 +6,60 @@ namespace MTConnect.Assets.Json.CuttingTools { + /// + /// JSON serialization surrogate for a cutting tool ToolLife, the + /// life measurement of the tool as a whole. Mirrors the on-the-wire shape + /// so the JSON serializer can read and write it, then converts to and from + /// the strongly-typed model. + /// public class JsonToolLife { + /// + /// The current tool life value. + /// [JsonPropertyName("value")] public double Value { get; set; } + /// + /// The type of life being measured (MINUTES, PART_COUNT, or WEAR). + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The direction the value counts in (UP or DOWN). + /// [JsonPropertyName("countDirection")] public string CountDirection { get; set; } + /// + /// The value at which a warning is raised. + /// [JsonPropertyName("warning")] public double? Warning { get; set; } + /// + /// The value at which the tool reaches the end of its usable life. + /// [JsonPropertyName("limit")] public double? Limit { get; set; } + /// + /// The value the tool life started at. + /// [JsonPropertyName("initial")] public double? Initial { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonToolLife() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , converting enumerations to strings. + /// public JsonToolLife(IToolLife toolLife) { if (toolLife != null) @@ -43,6 +74,10 @@ public JsonToolLife(IToolLife toolLife) } + /// + /// Converts this surrogate to a strongly-typed , + /// parsing the type and count direction enumerations. + /// public IToolLife ToToolLife() { var toolLife = new ToolLife(); diff --git a/libraries/MTConnect.NET-JSON/Assets/Files/JsonAbstractFileAsset.cs b/libraries/MTConnect.NET-JSON/Assets/Files/JsonAbstractFileAsset.cs index 3d84938cf..0abcf9d81 100644 --- a/libraries/MTConnect.NET-JSON/Assets/Files/JsonAbstractFileAsset.cs +++ b/libraries/MTConnect.NET-JSON/Assets/Files/JsonAbstractFileAsset.cs @@ -6,23 +6,47 @@ namespace MTConnect.Assets.Json.Files { + /// + /// Common JSON serialization shape for the File and FileArchetype assets, + /// carrying the file's metadata and properties. + /// public abstract class JsonAbstractFileAsset { + /// + /// The name of the file. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The MIME media type of the file's contents. + /// [JsonPropertyName("mediaType")] public string MediaType { get; set; } + /// + /// The category of application the file is associated with, serialized + /// as the enumeration name. + /// [JsonPropertyName("applicationCategory")] public string ApplicationCategory { get; set; } + /// + /// The type of application the file is associated with, serialized as + /// the enumeration name. + /// [JsonPropertyName("applicationType")] public string ApplicationType { get; set; } + /// + /// The key/value properties describing the file. + /// [JsonPropertyName("fileProperties")] public IEnumerable FileProperties { get; set; } + /// + /// The comments associated with the file. + /// [JsonPropertyName("fileComments")] public IEnumerable FileComments { get; set; } } diff --git a/libraries/MTConnect.NET-JSON/Assets/Files/JsonDestination.cs b/libraries/MTConnect.NET-JSON/Assets/Files/JsonDestination.cs index dfa8893ca..440b31d78 100644 --- a/libraries/MTConnect.NET-JSON/Assets/Files/JsonDestination.cs +++ b/libraries/MTConnect.NET-JSON/Assets/Files/JsonDestination.cs @@ -6,14 +6,29 @@ namespace MTConnect.Assets.Json.Files { + /// + /// JSON serialization surrogate for a file Destination, the device + /// the file is intended for. Converts to and from the strongly-typed + /// model. + /// public class JsonDestination { + /// + /// The UUID of the destination device. + /// [JsonPropertyName("deviceUuid")] public string DeviceUuid { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDestination() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonDestination(IDestination destination) { if (destination != null) @@ -23,6 +38,9 @@ public JsonDestination(IDestination destination) } + /// + /// Converts this surrogate to a strongly-typed . + /// public IDestination ToDestination() { var destination = new Destination(); diff --git a/libraries/MTConnect.NET-JSON/Assets/Files/JsonFileAsset.cs b/libraries/MTConnect.NET-JSON/Assets/Files/JsonFileAsset.cs index 2c37f6359..88f125ccb 100644 --- a/libraries/MTConnect.NET-JSON/Assets/Files/JsonFileAsset.cs +++ b/libraries/MTConnect.NET-JSON/Assets/Files/JsonFileAsset.cs @@ -8,82 +8,165 @@ namespace MTConnect.Assets.Json.Files { + /// + /// JSON serialization surrogate for an MTConnect File asset. Mirrors + /// the on-the-wire shape so the JSON serializer can read and write it, then + /// converts to and from the strongly-typed model. + /// public class JsonFileAsset { + /// + /// The unique identifier of the asset. + /// [JsonPropertyName("assetId")] public string AssetId { get; set; } + /// + /// The asset type identifier, File. + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The timestamp at which the asset was last reported. + /// [JsonPropertyName("timestamp")] public DateTime Timestamp { get; set; } + /// + /// The instance identifier of the agent that produced this asset. + /// [JsonPropertyName("instanceId")] public ulong InstanceId { get; set; } + /// + /// The UUID of the device the asset is associated with. + /// [JsonPropertyName("deviceUuid")] public string DeviceUuid { get; set; } + /// + /// Whether the asset has been removed from the agent. + /// [JsonPropertyName("removed")] public bool Removed { get; set; } + /// + /// The free-form description of the asset. + /// [JsonPropertyName("description")] public string Description { get; set; } + /// + /// The name of the file. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The MIME media type of the file's contents. + /// [JsonPropertyName("mediaType")] public string MediaType { get; set; } + /// + /// The category of application the file is associated with (for + /// example DEVICE or PRODUCT), serialized as the enumeration name. + /// [JsonPropertyName("applicationCategory")] public string ApplicationCategory { get; set; } + /// + /// The type of application the file is associated with (for example + /// DESIGN or DATA), serialized as the enumeration name. + /// [JsonPropertyName("applicationType")] public string ApplicationType { get; set; } + /// + /// The key/value properties describing the file. + /// [JsonPropertyName("fileProperties")] public IEnumerable FileProperties { get; set; } + /// + /// The comments associated with the file. + /// [JsonPropertyName("fileComments")] public IEnumerable FileComments { get; set; } + /// + /// The size of the file in bytes. + /// [JsonPropertyName("size")] public int Size { get; set; } + /// + /// The version identifier of the file. + /// [JsonPropertyName("versionId")] public string VersionId { get; set; } + /// + /// The state of the file (for example PRODUCTION or EXPERIMENTAL), + /// serialized as the enumeration name. + /// [JsonPropertyName("state")] public string State { get; set; } + /// + /// The location the file can be retrieved from. + /// [JsonPropertyName("fileLocation")] public JsonFileLocation FileLocation { get; set; } + /// + /// The cryptographic signature used to verify the file. + /// [JsonPropertyName("signature")] public string Signature { get; set; } + /// + /// The public key used to verify the file's . + /// [JsonPropertyName("publicKey")] public string PublicKey { get; set; } + /// + /// The destinations the file is intended to be transferred to. + /// [JsonPropertyName("destinations")] public IEnumerable Destinations { get; set; } + /// + /// The time the file was created. + /// [JsonPropertyName("creationTime")] public DateTime CreationTime { get; set; } + /// + /// The time the file was last modified, when known. + /// [JsonPropertyName("modificationTime")] public DateTime? ModificationTime { get; set; } - public JsonFileAsset() + /// + /// Initializes an empty instance for JSON deserialization, defaulting + /// to the File type identifier. + /// + public JsonFileAsset() { Type = FileAsset.TypeId; } + /// + /// Initializes the surrogate from a strongly-typed + /// , converting enumerations to their string + /// representations and each file property and comment. + /// public JsonFileAsset(IFileAsset asset) { if (asset != null) @@ -137,6 +220,10 @@ public JsonFileAsset(IFileAsset asset) } + /// + /// Converts this surrogate to a strongly-typed , + /// parsing enumerations and converting each file property and comment. + /// public IFileAsset ToFileAsset() { var asset = new FileAsset(); diff --git a/libraries/MTConnect.NET-JSON/Assets/Files/JsonFileComment.cs b/libraries/MTConnect.NET-JSON/Assets/Files/JsonFileComment.cs index 476f3ac73..984dc1a3d 100644 --- a/libraries/MTConnect.NET-JSON/Assets/Files/JsonFileComment.cs +++ b/libraries/MTConnect.NET-JSON/Assets/Files/JsonFileComment.cs @@ -7,17 +7,35 @@ namespace MTConnect.Assets.Json.Files { + /// + /// JSON serialization surrogate for a FileComment, a timestamped + /// remark on a file asset. Converts to and from the strongly-typed + /// model. + /// public class JsonFileComment { + /// + /// The time the comment was made. + /// [JsonPropertyName("timestamp")] public DateTime Timestamp { get; set; } + /// + /// The comment text. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonFileComment() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonFileComment(IFileComment fileComment) { if (fileComment != null) @@ -28,6 +46,9 @@ public JsonFileComment(IFileComment fileComment) } + /// + /// Converts this surrogate to a strongly-typed . + /// public IFileComment ToFileComment() { var fileComment = new FileComment(); diff --git a/libraries/MTConnect.NET-JSON/Assets/Files/JsonFileLocation.cs b/libraries/MTConnect.NET-JSON/Assets/Files/JsonFileLocation.cs index b60614255..6b13e5944 100644 --- a/libraries/MTConnect.NET-JSON/Assets/Files/JsonFileLocation.cs +++ b/libraries/MTConnect.NET-JSON/Assets/Files/JsonFileLocation.cs @@ -6,17 +6,35 @@ namespace MTConnect.Assets.Json.Files { + /// + /// JSON serialization surrogate for a FileLocation, the URL at + /// which a file asset can be retrieved. Converts to and from the + /// strongly-typed model. + /// public class JsonFileLocation { + /// + /// The hyperlink to the file. + /// [JsonPropertyName("href")] public string Href { get; set; } + /// + /// The XLink type of the reference. + /// [JsonPropertyName("xLinkType")] public string XLinkType { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonFileLocation() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonFileLocation(IFileLocation fileLocation) { if (fileLocation != null) @@ -27,6 +45,9 @@ public JsonFileLocation(IFileLocation fileLocation) } + /// + /// Converts this surrogate to a strongly-typed . + /// public IFileLocation ToFileLocation() { var fileLocation = new FileLocation(); diff --git a/libraries/MTConnect.NET-JSON/Assets/Files/JsonFileProperty.cs b/libraries/MTConnect.NET-JSON/Assets/Files/JsonFileProperty.cs index 0b784cd72..db39dea17 100644 --- a/libraries/MTConnect.NET-JSON/Assets/Files/JsonFileProperty.cs +++ b/libraries/MTConnect.NET-JSON/Assets/Files/JsonFileProperty.cs @@ -6,17 +6,35 @@ namespace MTConnect.Assets.Json.Files { + /// + /// JSON serialization surrogate for a FileProperty, a single + /// name/value pair describing a file asset. Converts to and from the + /// strongly-typed model. + /// public class JsonFileProperty { + /// + /// The name of the property. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The value of the property. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonFileProperty() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonFileProperty(IFileProperty fileProperty) { if (fileProperty != null) @@ -27,6 +45,9 @@ public JsonFileProperty(IFileProperty fileProperty) } + /// + /// Converts this surrogate to a strongly-typed . + /// public IFileProperty ToFileProperty() { var fileProperty = new FileProperty(); diff --git a/libraries/MTConnect.NET-JSON/Assets/JsonAsset.cs b/libraries/MTConnect.NET-JSON/Assets/JsonAsset.cs index 886b56680..d05807717 100644 --- a/libraries/MTConnect.NET-JSON/Assets/JsonAsset.cs +++ b/libraries/MTConnect.NET-JSON/Assets/JsonAsset.cs @@ -6,23 +6,46 @@ namespace MTConnect.Assets.Json { + /// + /// Common JSON serialization shape for an MTConnect asset, providing the + /// identifier, type, timestamp, association, removal, and description + /// fields shared by every asset surrogate. + /// public abstract class JsonAsset { + /// + /// The unique identifier of the asset. + /// [JsonPropertyName("assetId")] public string AssetId { get; set; } + /// + /// The asset type identifier. + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The timestamp at which the asset was last reported. + /// [JsonPropertyName("timestamp")] public DateTime Timestamp { get; set; } + /// + /// The UUID of the device the asset is associated with. + /// [JsonPropertyName("deviceUuid")] public string DeviceUuid { get; set; } + /// + /// Whether the asset has been removed from the agent. + /// [JsonPropertyName("removed")] public bool Removed { get; set; } + /// + /// The free-form description of the asset. + /// [JsonPropertyName("description")] public string Description { get; set; } } diff --git a/libraries/MTConnect.NET-JSON/Assets/JsonAssetsDocument.cs b/libraries/MTConnect.NET-JSON/Assets/JsonAssetsDocument.cs index 02a5a167d..e147db4b3 100644 --- a/libraries/MTConnect.NET-JSON/Assets/JsonAssetsDocument.cs +++ b/libraries/MTConnect.NET-JSON/Assets/JsonAssetsDocument.cs @@ -16,15 +16,33 @@ namespace MTConnect.Assets.Json { + /// + /// JSON serialization surrogate for an MTConnectAssets response document, + /// carrying the header and a heterogeneous collection of asset surrogates. + /// Converts to and from the strongly-typed + /// model. + /// public class JsonAssetsDocument { + /// + /// The document header. + /// [JsonPropertyName("header")] public JsonAssetsHeader Header { get; set; } + /// + /// The asset surrogates reported in the document, each selected by the + /// source asset's type. + /// [JsonPropertyName("assets")] public List Assets { get; set; } + /// + /// Initializes the surrogate from a strongly-typed + /// , dispatching each asset to the + /// surrogate that matches its type. + /// public JsonAssetsDocument(IAssetsResponseDocument assetsDocument) { if (assetsDocument != null) @@ -56,6 +74,12 @@ public JsonAssetsDocument(IAssetsResponseDocument assetsDocument) } + /// + /// Converts this surrogate to a strongly-typed + /// ; currently restores the header + /// only, leaving the asset collection empty pending per-type + /// reconstitution. + /// public AssetsResponseDocument ToAssetsDocument() { var assetsDocument = new AssetsResponseDocument(); diff --git a/libraries/MTConnect.NET-JSON/Assets/JsonAssetsHeader.cs b/libraries/MTConnect.NET-JSON/Assets/JsonAssetsHeader.cs index ed5e2ae79..3b41219c8 100644 --- a/libraries/MTConnect.NET-JSON/Assets/JsonAssetsHeader.cs +++ b/libraries/MTConnect.NET-JSON/Assets/JsonAssetsHeader.cs @@ -7,35 +7,74 @@ namespace MTConnect.Assets.Json { + /// + /// JSON serialization surrogate for the Header of an + /// MTConnectAssets document. Mirrors the on-the-wire shape so the JSON + /// serializer can read and write it, then converts to and from the + /// strongly-typed model. + /// public class JsonAssetsHeader { + /// + /// The instance identifier of the agent, which changes whenever the + /// agent's buffer is cleared. + /// [JsonPropertyName("instanceId")] public ulong InstanceId { get; set; } + /// + /// The MTConnect schema version of the document. + /// [JsonPropertyName("version")] public string Version { get; set; } + /// + /// The identifier of the agent that produced the document. + /// [JsonPropertyName("sender")] public string Sender { get; set; } + /// + /// The maximum number of assets the agent can store. + /// [JsonPropertyName("assetBufferSize")] public ulong AssetBufferSize { get; set; } + /// + /// The number of assets currently stored by the agent. + /// [JsonPropertyName("assetCount")] public ulong AssetCount { get; set; } + /// + /// The timestamp of the most recent change to the device model. + /// [JsonPropertyName("deviceModelChangeTime")] public string DeviceModelChangeTime { get; set; } + /// + /// Whether the document was produced for testing rather than + /// production use. + /// [JsonPropertyName("testIndicator")] public bool TestIndicator { get; set; } + /// + /// The time the document was created. + /// [JsonPropertyName("creationTime")] public DateTime CreationTime { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonAssetsHeader() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonAssetsHeader(IMTConnectAssetsHeader header) { if (header != null) @@ -52,6 +91,10 @@ public JsonAssetsHeader(IMTConnectAssetsHeader header) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public virtual IMTConnectAssetsHeader ToAssetsHeader() { var header = new MTConnectAssetsHeader(); diff --git a/libraries/MTConnect.NET-JSON/Assets/QIF/JsonQIFDocumentWrapperAsset.cs b/libraries/MTConnect.NET-JSON/Assets/QIF/JsonQIFDocumentWrapperAsset.cs index 800b6a531..7d18a5c51 100644 --- a/libraries/MTConnect.NET-JSON/Assets/QIF/JsonQIFDocumentWrapperAsset.cs +++ b/libraries/MTConnect.NET-JSON/Assets/QIF/JsonQIFDocumentWrapperAsset.cs @@ -7,42 +7,86 @@ namespace MTConnect.Assets.Json.QIF { + /// + /// JSON serialization surrogate for an MTConnect + /// QIFDocumentWrapper asset, which embeds a Quality Information + /// Framework document. Mirrors the on-the-wire shape so the JSON + /// serializer can read and write it, then converts to and from the + /// strongly-typed model. + /// public class JsonQIFDocumentWrapperAsset { + /// + /// The unique identifier of the asset. + /// [JsonPropertyName("assetId")] public string AssetId { get; set; } + /// + /// The asset type identifier, QIFDocumentWrapper. + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The timestamp at which the asset was last reported. + /// [JsonPropertyName("timestamp")] public DateTime Timestamp { get; set; } + /// + /// The instance identifier of the agent that produced this asset. + /// [JsonPropertyName("instanceId")] public ulong InstanceId { get; set; } + /// + /// The UUID of the device the asset is associated with. + /// [JsonPropertyName("deviceUuid")] public string DeviceUuid { get; set; } + /// + /// Whether the asset has been removed from the agent. + /// [JsonPropertyName("removed")] public bool Removed { get; set; } + /// + /// The free-form description of the asset. + /// [JsonPropertyName("description")] public string Description { get; set; } + /// + /// The QIF document type (for example MEASUREMENT_RESOURCE or PLAN), + /// serialized as the enumeration name. + /// [JsonPropertyName("qifDocumentType")] public string QIFDocumentType { get; set; } + /// + /// The embedded QIF document content. + /// [JsonPropertyName("qifDocument")] public string QIFDocument { get; set; } - public JsonQIFDocumentWrapperAsset() + /// + /// Initializes an empty instance for JSON deserialization, defaulting + /// to the QIFDocumentWrapper type identifier. + /// + public JsonQIFDocumentWrapperAsset() { Type = QIFDocumentWrapperAsset.TypeId; } + /// + /// Initializes the surrogate from a strongly-typed + /// , converting the document type + /// enumeration to a string. + /// public JsonQIFDocumentWrapperAsset(IQIFDocumentWrapperAsset asset) { if (asset != null) @@ -63,6 +107,11 @@ public JsonQIFDocumentWrapperAsset(IQIFDocumentWrapperAsset asset) } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing the document type + /// enumeration. + /// public IQIFDocumentWrapperAsset ToQIFDocumentWrapperAsset() { var asset = new QIFDocumentWrapperAsset(); diff --git a/libraries/MTConnect.NET-JSON/Assets/RawMaterials/JsonMaterial.cs b/libraries/MTConnect.NET-JSON/Assets/RawMaterials/JsonMaterial.cs index cbfd5ce50..1f43961e4 100644 --- a/libraries/MTConnect.NET-JSON/Assets/RawMaterials/JsonMaterial.cs +++ b/libraries/MTConnect.NET-JSON/Assets/RawMaterials/JsonMaterial.cs @@ -7,35 +7,72 @@ namespace MTConnect.Assets.Json.RawMaterials { + /// + /// JSON serialization surrogate for the Material a raw material + /// asset is made of. Mirrors the on-the-wire shape so the JSON serializer + /// can read and write it, then converts to and from the strongly-typed + /// model. + /// public class JsonMaterial { + /// + /// The unique identifier of the material. + /// [JsonPropertyName("id")] public string Id { get; set; } + /// + /// The human-readable name of the material. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The type of the material. + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The lot the material was produced in. + /// [JsonPropertyName("lot")] public string Lot { get; set; } + /// + /// The manufacturer of the material. + /// [JsonPropertyName("manufacturer")] public string Manufacturer { get; set; } + /// + /// The date the material was manufactured. + /// [JsonPropertyName("manufacturingDate")] public DateTime? ManufacturingDate { get; set; } + /// + /// The manufacturer's code identifying the material. + /// [JsonPropertyName("manufacturingCode")] public string ManufacturingCode { get; set; } + /// + /// The standardized code identifying the material. + /// [JsonPropertyName("materialCode")] public string MaterialCode { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonMaterial() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonMaterial(IMaterial material) { if (material != null) @@ -52,6 +89,9 @@ public JsonMaterial(IMaterial material) } + /// + /// Converts this surrogate to a strongly-typed . + /// public IMaterial ToMaterial() { var material = new Material(); diff --git a/libraries/MTConnect.NET-JSON/Assets/RawMaterials/JsonRawMaterialAsset.cs b/libraries/MTConnect.NET-JSON/Assets/RawMaterials/JsonRawMaterialAsset.cs index 20774fb6c..fc4d97255 100644 --- a/libraries/MTConnect.NET-JSON/Assets/RawMaterials/JsonRawMaterialAsset.cs +++ b/libraries/MTConnect.NET-JSON/Assets/RawMaterials/JsonRawMaterialAsset.cs @@ -7,84 +7,172 @@ namespace MTConnect.Assets.Json.RawMaterials { + /// + /// JSON serialization surrogate for an MTConnect RawMaterial asset. + /// Mirrors the on-the-wire shape so the JSON serializer can read and write + /// it, then converts to and from the strongly-typed + /// model. + /// public class JsonRawMaterialAsset { + /// + /// The unique identifier of the asset. + /// [JsonPropertyName("assetId")] public string AssetId { get; set; } + /// + /// The asset type identifier, RawMaterial. + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The timestamp at which the asset was last reported. + /// [JsonPropertyName("timestamp")] public DateTime Timestamp { get; set; } + /// + /// The instance identifier of the agent that produced this asset. + /// [JsonPropertyName("instanceId")] public ulong InstanceId { get; set; } + /// + /// The UUID of the device the asset is associated with. + /// [JsonPropertyName("deviceUuid")] public string DeviceUuid { get; set; } + /// + /// Whether the asset has been removed from the agent. + /// [JsonPropertyName("removed")] public bool Removed { get; set; } + /// + /// The free-form description of the asset. + /// [JsonPropertyName("description")] public string Description { get; set; } + /// + /// The human-readable name of the raw material. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The type of container holding the raw material, such as a bottle or + /// cartridge. + /// [JsonPropertyName("containerType")] public string ContainerType { get; set; } + /// + /// The manufacturing process the raw material is intended for. + /// [JsonPropertyName("processKind")] public string ProcessKind { get; set; } + /// + /// The serial number that uniquely identifies this raw material. + /// [JsonPropertyName("serialNumber")] public string SerialNumber { get; set; } + /// + /// The physical form of the material (for example BAR, BLOCK, or + /// POWDER), serialized as the enumeration name. + /// [JsonPropertyName("form")] public string Form { get; set; } + /// + /// Whether the container currently holds material. + /// [JsonPropertyName("hasMaterial")] public bool? HasMaterial { get; set; } + /// + /// The date the raw material was manufactured. + /// [JsonPropertyName("manufacturingDate")] public DateTime? ManufacturingDate { get; set; } + /// + /// The date the raw material was first used. + /// [JsonPropertyName("firstUseDate")] public DateTime? FirstUseDate { get; set; } + /// + /// The date the raw material was last used. + /// [JsonPropertyName("lastUseDate")] public DateTime? LastUseDate { get; set; } + /// + /// The volume of unused material when first received. + /// [JsonPropertyName("initialVolume")] public double? InitialVolume { get; set; } + /// + /// The dimension of unused material when first received, serialized as + /// a millimeter 3D string. + /// [JsonPropertyName("initialDimension")] public string InitialDimension { get; set; } + /// + /// The quantity of unused material when first received. + /// [JsonPropertyName("initialQuantity")] public int? InitialQuantity { get; set; } + /// + /// The volume of material currently remaining. + /// [JsonPropertyName("currentVolume")] public double? CurrentVolume { get; set; } + /// + /// The dimension of material currently remaining, serialized as a + /// millimeter 3D string. + /// [JsonPropertyName("currentDimension")] public string CurrentDimension { get; set; } + /// + /// The quantity of material currently remaining. + /// [JsonPropertyName("currentQuantity")] public int? CurrentQuantity { get; set; } + /// + /// The material the raw material is made of. + /// [JsonPropertyName("material")] public JsonMaterial Material { get; set; } - public JsonRawMaterialAsset() + /// + /// Initializes an empty instance for JSON deserialization, defaulting + /// to the RawMaterial type identifier. + /// + public JsonRawMaterialAsset() { Type = RawMaterialAsset.TypeId; } + /// + /// Initializes the surrogate from a strongly-typed + /// , converting enumerations and + /// dimensions to their string representations. + /// public JsonRawMaterialAsset(IRawMaterialAsset asset) { if (asset != null) @@ -120,6 +208,11 @@ public JsonRawMaterialAsset(IRawMaterialAsset asset) } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing enumerations and + /// millimeter 3D dimension strings back into typed values. + /// public IRawMaterialAsset ToRawMaterialAsset() { var asset = new RawMaterialAsset(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonAbstractSpecification.cs b/libraries/MTConnect.NET-JSON/Devices/JsonAbstractSpecification.cs index 58decbd34..54a3197ca 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonAbstractSpecification.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonAbstractSpecification.cs @@ -6,38 +6,83 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for the shape common to all Configuration + /// Specification kinds. Mirrors the on-the-wire shape so the JSON + /// serializer can read and write it, then converts to and from the + /// strongly-typed model; + /// extends it with the limit elements. + /// public class JsonAbstractSpecification { + /// + /// The unique id of the specification. + /// [JsonPropertyName("id")] public string Id { get; set; } + /// + /// The human-readable name of the specification. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The MTConnect type of the value the specification constrains. + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The subtype further qualifying . + /// [JsonPropertyName("subType")] public string SubType { get; set; } + /// + /// Reference to the id of the data item the specification + /// applies to. + /// [JsonPropertyName("dataItemIdRef")] public string DataItemIdRef { get; set; } + /// + /// The engineering units the specification limits are expressed in. + /// [JsonPropertyName("units")] public string Units { get; set; } + /// + /// Reference to the id of the composition the specification + /// applies to. + /// [JsonPropertyName("compositionIdRef")] public string CompositionIdRef { get; set; } + /// + /// Reference to the id of the coordinate system the + /// specification limits are expressed in. + /// [JsonPropertyName("coordinateSystemIdRef")] public string CoordinateSystemIdRef { get; set; } + /// + /// The party that defined the specification (MANUFACTURER or USER). + /// [JsonPropertyName("originator")] public string Originator { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonAbstractSpecification() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , converting the originator enumeration + /// to a string. + /// public JsonAbstractSpecification(ISpecification specification) { if (specification != null) @@ -55,6 +100,10 @@ public JsonAbstractSpecification(ISpecification specification) } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing the originator enumeration. + /// public virtual ISpecification ToSpecification() { var specification = new Specification(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonAlarmLimits.cs b/libraries/MTConnect.NET-JSON/Devices/JsonAlarmLimits.cs index c5595b237..86e3f2e8c 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonAlarmLimits.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonAlarmLimits.cs @@ -6,23 +6,46 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for the AlarmLimits of a + /// Specification, carrying the upper/lower alarm and warning bounds. + /// public class JsonAlarmLimits { + /// + /// The upper alarm bound. + /// [JsonPropertyName("upperLimit")] public double? UpperLimit { get; set; } + /// + /// The upper warning bound. + /// [JsonPropertyName("upperWarning")] public double? UpperWarning { get; set; } + /// + /// The lower alarm bound. + /// [JsonPropertyName("lowerLimit")] public double? LowerLimit { get; set; } + /// + /// The lower warning bound. + /// [JsonPropertyName("lowerWarning")] public double? LowerWarning { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonAlarmLimits() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonAlarmLimits(IAlarmLimits alarmLimits) { if (alarmLimits != null) @@ -35,6 +58,9 @@ public JsonAlarmLimits(IAlarmLimits alarmLimits) } + /// + /// Converts this surrogate to a strongly-typed . + /// public IAlarmLimits ToAlarmLimits() { var alarmLimits = new AlarmLimits(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonAxis.cs b/libraries/MTConnect.NET-JSON/Devices/JsonAxis.cs index c567cee79..85a63020b 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonAxis.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonAxis.cs @@ -9,14 +9,29 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for an Axis, the inline variant + /// carrying its direction vector as a single string (space-separated + /// triple). Converts to and from the strongly-typed + /// model. + /// public class JsonAxis { + /// + /// The axis direction vector as a space-separated triple. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonAxis() { } + /// + /// Initializes the surrogate from a strongly-typed . + /// public JsonAxis(IAxis axis) { if (axis != null) @@ -26,6 +41,9 @@ public JsonAxis(IAxis axis) } + /// + /// Converts this surrogate to a strongly-typed . + /// public IAxis ToAxis() { var axis = new Axis(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonAxisDataSet.cs b/libraries/MTConnect.NET-JSON/Devices/JsonAxisDataSet.cs index 5743a4714..929fb1699 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonAxisDataSet.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonAxisDataSet.cs @@ -9,20 +9,41 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for an AxisDataSet, the variant of + /// a motion axis whose components are reported per axis. Converts to and + /// from the strongly-typed model. + /// public class JsonAxisDataSet { + /// + /// The X component of the axis direction vector. + /// [JsonPropertyName("x")] public double X { get; set; } + /// + /// The Y component of the axis direction vector. + /// [JsonPropertyName("y")] public double Y { get; set; } + /// + /// The Z component of the axis direction vector. + /// [JsonPropertyName("z")] public double Z { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonAxisDataSet() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonAxisDataSet(IAxisDataSet dataSet) { if (dataSet != null) @@ -34,6 +55,10 @@ public JsonAxisDataSet(IAxisDataSet dataSet) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IAxisDataSet ToAxisDataSet() { var dataSet = new AxisDataSet(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonCellDefinition.cs b/libraries/MTConnect.NET-JSON/Devices/JsonCellDefinition.cs index 0687fd57d..dfb40f477 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonCellDefinition.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonCellDefinition.cs @@ -5,29 +5,60 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a CellDefinition, which + /// describes a column of a TABLE entry. Mirrors the on-the-wire shape so + /// the JSON serializer can read and write it, then converts to and from + /// the strongly-typed model. + /// public class JsonCellDefinition { + /// + /// The key identifying the cell within the table row. + /// [JsonPropertyName("key")] public string Key { get; set; } + /// + /// The kind of value is interpreted as. + /// [JsonPropertyName("keyType")] public string KeyType { get; set; } + /// + /// The engineering units the cell values are expressed in. + /// [JsonPropertyName("units")] public string Units { get; set; } + /// + /// The MTConnect type the cell values report. + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The subtype further qualifying . + /// [JsonPropertyName("subType")] public string SubType { get; set; } + /// + /// The free-form description of the cell. + /// [JsonPropertyName("description")] public string Description { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCellDefinition() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonCellDefinition(ICellDefinition definition) { if (definition != null) @@ -43,6 +74,10 @@ public JsonCellDefinition(ICellDefinition definition) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public ICellDefinition ToCellDefinition() { var definition = new CellDefinition(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonChannel.cs b/libraries/MTConnect.NET-JSON/Devices/JsonChannel.cs index 9f353dbaa..f107da938 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonChannel.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonChannel.cs @@ -7,29 +7,58 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a single sensing Channel within + /// a SensorConfiguration, carrying its identification and per-channel + /// calibration metadata. + /// public class JsonChannel { + /// + /// The channel number that identifies it within the sensor. + /// [JsonPropertyName("number")] public string Number { get; set; } + /// + /// The optional human-readable channel name. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The date the channel was last calibrated. + /// [JsonPropertyName("calibrationDate")] public DateTime? CalibrationDate { get; set; } + /// + /// The date the channel is next due for calibration. + /// [JsonPropertyName("nextCalibrationDate")] public DateTime? NextCalibrationDate { get; set; } + /// + /// The initials of the person who performed the calibration. + /// [JsonPropertyName("calibrationInitials")] public string CalibrationInitials { get; set; } + /// + /// The free-text channel description (carried as a string from v2.5). + /// [JsonPropertyName("description")] public string Description { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonChannel() { } + /// + /// Initializes the surrogate from a strongly-typed . + /// public JsonChannel(IChannel channel) { if (channel != null) @@ -46,6 +75,9 @@ public JsonChannel(IChannel channel) } + /// + /// Converts this surrogate to a strongly-typed . + /// public IChannel ToChannel() { var channel = new Channel(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonComponent.cs b/libraries/MTConnect.NET-JSON/Devices/JsonComponent.cs index 29e628d1b..d564c2f4a 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonComponent.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonComponent.cs @@ -7,54 +7,121 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for an MTConnect Component. Mirrors a + /// Component element of an MTConnectDevices document so the JSON serializer + /// can read and write the on-the-wire shape, then converts to and from the + /// strongly-typed model. Components nest recursively + /// and carry the device's data items and compositions. + /// public class JsonComponent { + /// + /// The unique id of the component within the device. + /// [JsonPropertyName("id")] public string Id { get; set; } + /// + /// The MTConnect component type (for example Axes, Controller, + /// or Linear). + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The optional human-readable name of the component. Omitted + /// from the JSON output when not set. + /// [JsonPropertyName("name")] [JsonIgnore(Condition = JsonIgnoreCondition.WhenWritingNull)] public string Name { get; set; } + /// + /// The name the component is known by in the native data source, when + /// it differs from . + /// [JsonPropertyName("nativeName")] public string NativeName { get; set; } + /// + /// The interval, in milliseconds, between samples of the component's + /// data, when reported. + /// [JsonPropertyName("sampleInterval")] public double? SampleInterval { get; set; } + /// + /// The rate, in samples per second, at which the component's data is + /// sampled, when reported. + /// [JsonPropertyName("sampleRate")] public double? SampleRate { get; set; } + /// + /// The universally unique identifier of the component instance. + /// [JsonPropertyName("uuid")] public string Uuid { get; set; } + /// + /// Reference to the id of a CoordinateSystem the component's + /// values are expressed relative to. + /// [JsonPropertyName("coordinateSystemIdRef")] public string CoordinateSystemIdRef { get; set; } + /// + /// The descriptive metadata (manufacturer, model, serial number) for + /// the component. + /// [JsonPropertyName("description")] public JsonDescription Description { get; set; } + /// + /// The configuration (coordinate systems, motion, relationships, + /// specifications) of the component. + /// [JsonPropertyName("configuration")] public JsonConfiguration Configuration { get; set; } + /// + /// The data items reported directly by the component. + /// [JsonPropertyName("dataItems")] public IEnumerable DataItems { get; set; } + /// + /// The child components nested within the component. + /// [JsonPropertyName("components")] public IEnumerable Components { get; set; } + /// + /// The compositions (lower-level structural elements) of the component. + /// [JsonPropertyName("compositions")] public IEnumerable Compositions { get; set; } + /// + /// The references from the component to other components and data + /// items. + /// [JsonPropertyName("references")] public JsonReferenceContainer References { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonComponent() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , recursively converting the description, + /// configuration, references, data items, compositions, and child + /// components. + /// public JsonComponent(IComponent component) { if (component != null) @@ -110,8 +177,16 @@ public JsonComponent(IComponent component) } + /// + /// Returns the JSON representation of this surrogate. + /// public override string ToString() => JsonFunctions.Convert(this); + /// + /// Converts this surrogate to a strongly-typed , + /// recursively converting the description, configuration, references, + /// data items, compositions, and child components. + /// public Component ToComponent() { var component = new Component(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonComponentReference.cs b/libraries/MTConnect.NET-JSON/Devices/JsonComponentReference.cs index 6eaa5ebdf..2804b03fa 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonComponentReference.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonComponentReference.cs @@ -6,17 +6,35 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a ComponentReference, a pointer + /// from one component to another. Converts to and from the strongly-typed + /// model. + /// public class JsonComponentReference { + /// + /// Reference to the id of the related component. + /// [JsonPropertyName("idRef")] public string IdRef { get; set; } + /// + /// The human-readable name of the reference. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonComponentReference() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonComponentReference(IComponentReference reference) { if (reference != null) @@ -27,6 +45,9 @@ public JsonComponentReference(IComponentReference reference) } + /// + /// Converts this surrogate to a strongly-typed . + /// public virtual IReference ToReference() { var reference = new ComponentReference(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonComposition.cs b/libraries/MTConnect.NET-JSON/Devices/JsonComposition.cs index 5687f5886..0215be2ac 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonComposition.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonComposition.cs @@ -7,48 +7,106 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for an MTConnect Composition, a + /// lower-level structural element of a component. Mirrors the on-the-wire + /// shape so the JSON serializer can read and write it, then converts to + /// and from the strongly-typed model. + /// public class JsonComposition { + /// + /// The unique id of the composition within the device. + /// [JsonPropertyName("id")] public string Id { get; set; } + /// + /// The MTConnect composition type (for example MOTOR or TANK). + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The optional human-readable name of the composition. Omitted + /// from the JSON output when not set. + /// [JsonPropertyName("name")] [JsonIgnore(Condition = JsonIgnoreCondition.WhenWritingNull)] public string Name { get; set; } + /// + /// The name the composition is known by in the native data source, + /// when it differs from . + /// [JsonPropertyName("nativeName")] public string NativeName { get; set; } + /// + /// The interval, in milliseconds, between samples of the composition's + /// data, when reported. + /// [JsonPropertyName("sampleInterval")] public double? SampleInterval { get; set; } + /// + /// The rate, in samples per second, at which the composition's data is + /// sampled, when reported. + /// [JsonPropertyName("sampleRate")] public double? SampleRate { get; set; } + /// + /// The universally unique identifier of the composition instance. + /// [JsonPropertyName("uuid")] public string Uuid { get; set; } + /// + /// Reference to the id of a CoordinateSystem the composition's + /// values are expressed relative to. + /// [JsonPropertyName("coordinateSystemIdRef")] public string CoordinateSystemIdRef { get; set; } + /// + /// The descriptive metadata (manufacturer, model, serial number) for + /// the composition. + /// [JsonPropertyName("description")] public JsonDescription Description { get; set; } + /// + /// The configuration (coordinate systems, motion, relationships, + /// specifications) of the composition. + /// [JsonPropertyName("configuration")] public JsonConfiguration Configuration { get; set; } + /// + /// The data items reported directly by the composition. + /// [JsonPropertyName("dataItems")] public IEnumerable DataItems { get; set; } + /// + /// The references from the composition to other components and data + /// items. + /// [JsonPropertyName("references")] public JsonReferenceContainer References { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonComposition() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , converting the description, + /// configuration, references, and data items. + /// public JsonComposition(IComposition composition) { if (composition != null) @@ -82,8 +140,16 @@ public JsonComposition(IComposition composition) } + /// + /// Returns the JSON representation of this surrogate. + /// public override string ToString() => JsonFunctions.Convert(this); + /// + /// Converts this surrogate to a strongly-typed + /// , converting the description, + /// configuration, references, and data items. + /// public Composition ToComposition() { var composition = new Composition(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonConfiguration.cs b/libraries/MTConnect.NET-JSON/Devices/JsonConfiguration.cs index 4c18baba6..0268f7c66 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonConfiguration.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonConfiguration.cs @@ -7,29 +7,61 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a Component Configuration, the + /// container for coordinate systems, motion, relationships, sensor and + /// solid-model configuration, and specifications. + /// public class JsonConfiguration { + /// + /// The coordinate systems defined on the component. + /// [JsonPropertyName("coordinateSystems")] public IEnumerable CoordinateSystems { get; set; } + /// + /// The motion definition relating the component to its parent. + /// [JsonPropertyName("motion")] public JsonMotion Motion { get; set; } + /// + /// The relationships from the component to other components, data + /// items, devices, and specifications, grouped by relationship kind. + /// [JsonPropertyName("relationships")] public JsonRelationshipContainer Relationships { get; set; } + /// + /// The sensor configuration when the component is a sensor. + /// [JsonPropertyName("sensorConfiguration")] public JsonSensorConfiguration SensorConfiguration { get; set; } + /// + /// The solid-model reference describing the component geometry. + /// [JsonPropertyName("solidModel")] public JsonSolidModel SolidModel { get; set; } + /// + /// The specifications defined on the component. + /// [JsonPropertyName("specifications")] public IEnumerable Specifications { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonConfiguration() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , converting each child and grouping + /// relationships by their concrete relationship interface. + /// public JsonConfiguration(IConfiguration configuration) { if (configuration != null) @@ -114,10 +146,15 @@ public JsonConfiguration(IConfiguration configuration) } + /// + /// Converts this surrogate to a strongly-typed , + /// converting each child and flattening the grouped relationships back + /// into a single relationship collection. + /// public IConfiguration ToConfiguration() { var configuration = new Configuration(); - + // Coordinate Systems if (!CoordinateSystems.IsNullOrEmpty()) { diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonConstraints.cs b/libraries/MTConnect.NET-JSON/Devices/JsonConstraints.cs index 99d6db52b..4ddd9bfe8 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonConstraints.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonConstraints.cs @@ -7,26 +7,53 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a DataItem Constraints, bounding + /// the values a data item may report through numeric limits, an enumerated + /// value list, or a filter. + /// public class JsonConstraints { + /// + /// The maximum permitted value. + /// [JsonPropertyName("maximum")] public double? Maximum { get; set; } + /// + /// The minimum permitted value. + /// [JsonPropertyName("minimum")] public double? Minimum { get; set; } + /// + /// The nominal (expected) value. + /// [JsonPropertyName("nominal")] public double? Nominal { get; set; } + /// + /// The set of permitted enumerated values. + /// [JsonPropertyName("values")] public List Values { get; set; } + /// + /// An optional filter further constraining reported values. + /// [JsonPropertyName("filter")] public JsonFilter Filter { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonConstraints() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonConstraints(IConstraints constraints) { if (constraints != null) @@ -40,6 +67,10 @@ public JsonConstraints(IConstraints constraints) } + /// + /// Converts this surrogate to a strongly-typed , + /// copying the numeric bounds and the enumerated value list. + /// public IConstraints ToConstraints() { var constraints = new Constraints(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonControlLimits.cs b/libraries/MTConnect.NET-JSON/Devices/JsonControlLimits.cs index f211aa71d..efc857147 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonControlLimits.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonControlLimits.cs @@ -6,26 +6,53 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for the ControlLimits of a + /// Specification, carrying the upper/lower control and warning bounds and + /// the nominal target. + /// public class JsonControlLimits { + /// + /// The upper control bound. + /// [JsonPropertyName("upperLimit")] public double? UpperLimit { get; set; } + /// + /// The upper warning bound. + /// [JsonPropertyName("upperWarning")] public double? UpperWarning { get; set; } + /// + /// The nominal (target) value. + /// [JsonPropertyName("nominal")] public double? Nominal { get; set; } + /// + /// The lower control bound. + /// [JsonPropertyName("lowerLimit")] public double? LowerLimit { get; set; } + /// + /// The lower warning bound. + /// [JsonPropertyName("lowerWarning")] public double? LowerWarning { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonControlLimits() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonControlLimits(IControlLimits controlLimits) { if (controlLimits != null) @@ -39,6 +66,9 @@ public JsonControlLimits(IControlLimits controlLimits) } + /// + /// Converts this surrogate to a strongly-typed . + /// public IControlLimits ToControlLimits() { var controlLimits = new ControlLimits(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonCoordinateSystem.cs b/libraries/MTConnect.NET-JSON/Devices/JsonCoordinateSystem.cs index fd90c0692..679aded00 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonCoordinateSystem.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonCoordinateSystem.cs @@ -6,38 +6,86 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a Configuration + /// CoordinateSystem, which defines a frame of reference for a + /// component's values. Mirrors the on-the-wire shape so the JSON + /// serializer can read and write it, then converts to and from the + /// strongly-typed model. + /// public class JsonCoordinateSystem { + /// + /// The unique id of the coordinate system. + /// [JsonPropertyName("id")] public string Id { get; set; } + /// + /// The human-readable name of the coordinate system. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The name the coordinate system is known by in the native data + /// source. + /// [JsonPropertyName("nativeName")] public string NativeName { get; set; } + /// + /// Reference to the id of the parent coordinate system this + /// system is defined relative to. + /// [JsonPropertyName("parentIdRef")] public string ParentIdRef { get; set; } + /// + /// The kind of coordinate system (for example WORLD, MACHINE, or + /// OBJECT). + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The origin of the coordinate system as a coordinate triple, when + /// expressed inline. + /// [JsonPropertyName("origin")] public JsonOrigin Origin { get; set; } + /// + /// The origin of the coordinate system as a data set, when expressed + /// by reference. + /// [JsonPropertyName("originDataSet")] public JsonOriginDataSet OriginDataSet { get; set; } + /// + /// The translation and rotation relating this coordinate system to its + /// parent. + /// [JsonPropertyName("transformation")] public JsonTransformation Transformation { get; set; } + /// + /// The free-form description of the coordinate system. + /// [JsonPropertyName("description")] public string Description { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCoordinateSystem() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , selecting the inline or data-set + /// representation for the origin based on the source type. + /// public JsonCoordinateSystem(ICoordinateSystem coordinateSystem) { if (coordinateSystem != null) @@ -55,6 +103,11 @@ public JsonCoordinateSystem(ICoordinateSystem coordinateSystem) } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing the type enumeration and + /// preferring the data-set representation of the origin when present. + /// public ICoordinateSystem ToCoordinateSystem() { var coordinateSystem = new CoordinateSystem(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonDataItem.cs b/libraries/MTConnect.NET-JSON/Devices/JsonDataItem.cs index 468214b3d..4dda5361f 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonDataItem.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonDataItem.cs @@ -7,78 +7,179 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for an MTConnect DataItem. Mirrors a + /// DataItem element of an MTConnectDevices document so the JSON serializer + /// can read and write the on-the-wire shape, then converts to and from the + /// strongly-typed model. Properties that match the + /// MTConnect default are omitted on write and restored to that default on + /// read. + /// public class JsonDataItem { + /// + /// The category classifying the data item as SAMPLE, EVENT, or + /// CONDITION. + /// [JsonPropertyName("category")] public string DataItemCategory { get; set; } + /// + /// The unique id of the data item within the device. + /// [JsonPropertyName("id")] public string Id { get; set; } + /// + /// The MTConnect type identifying the kind of data reported. + /// [JsonPropertyName("type")] - public string Type { get; set; } + public string Type { get; set; } + /// + /// The coordinate system the reported values are expressed in. Omitted + /// when the default MACHINE coordinate system applies. + /// [JsonPropertyName("coordinateSystem")] public string CoordinateSystem { get; set; } + /// + /// Reference to the id of a CoordinateSystem the values are + /// expressed relative to. + /// [JsonPropertyName("coordinateSystemIdRef")] public string CoordinateSystemIdRef { get; set; } + /// + /// The optional human-readable name of the data item. Omitted + /// from the JSON output when not set. + /// [JsonPropertyName("name")] [JsonIgnore(Condition = JsonIgnoreCondition.WhenWritingNull)] public string Name { get; set; } + /// + /// The power-of-ten scaling applied to native values before conversion + /// to the reported units. Omitted when zero. + /// [JsonPropertyName("nativeScale")] public int? NativeScale { get; set; } + /// + /// The units the data source natively reports values in, prior to + /// conversion to . + /// [JsonPropertyName("nativeUnits")] public string NativeUnits { get; set; } + /// + /// The optional subType further qualifying . + /// [JsonPropertyName("subType")] public string SubType { get; set; } + /// + /// The statistical operation (for example AVERAGE or MAXIMUM) applied + /// to the reported values. + /// [JsonPropertyName("statistic")] public string Statistic { get; set; } + /// + /// The engineering units the reported values are expressed in. + /// [JsonPropertyName("units")] public string Units { get; set; } + /// + /// The rate, in samples per second, at which the data source samples + /// values for a TIME_SERIES representation. Omitted when zero. + /// [JsonPropertyName("sampleRate")] public double? SampleRate { get; set; } + /// + /// Indicates whether the reported values are discrete events rather + /// than a continuously varying signal. Omitted when false. + /// [JsonPropertyName("discrete")] public bool? Discrete { get; set; } + /// + /// The data item's representation (for example DATA_SET, TABLE, + /// or TIME_SERIES). Omitted when the default VALUE representation + /// applies. + /// [JsonPropertyName("representation")] public string Representation { get; set; } + /// + /// The number of significant digits in the reported values. Omitted + /// when zero. + /// [JsonPropertyName("significantDigits")] public int? SignificantDigits { get; set; } + /// + /// The source (component, composition, or data item) the data item's + /// values originate from. + /// [JsonPropertyName("source")] public JsonSource Source { get; set; } + /// + /// The constraints (limits or enumerated values) bounding the reported + /// values. + /// [JsonPropertyName("constraints")] public JsonConstraints Constraints { get; set; } + /// + /// The filters (minimum delta or period) applied to the reported + /// values. + /// [JsonPropertyName("filters")] public IEnumerable Filters { get; set; } + /// + /// The value reported for the data item before its first observation. + /// [JsonPropertyName("initialValue")] public string InitialValue { get; set; } + /// + /// The condition under which a resettable data item's accumulated + /// value is reset. + /// [JsonPropertyName("resetTrigger")] public string ResetTrigger { get; set; } + /// + /// The definition describing the structure of cell or entry values for + /// a DATA_SET or TABLE representation. + /// [JsonPropertyName("definition")] public JsonDataItemDefinition Definition { get; set; } + /// + /// The relationships from the data item to other data items and + /// specifications, grouped by relationship kind. + /// [JsonPropertyName("relationships")] public JsonRelationshipContainer Relationships { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDataItem() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , omitting properties whose values equal the + /// MTConnect default and grouping relationships by their concrete + /// relationship interface. + /// public JsonDataItem(IDataItem dataItem) { if (dataItem != null) @@ -143,8 +244,17 @@ public JsonDataItem(IDataItem dataItem) } + /// + /// Returns the JSON representation of this surrogate. + /// public override string ToString() => JsonFunctions.Convert(this); + /// + /// Converts this surrogate to a strongly-typed , + /// instantiating the concrete data item subtype for , + /// restoring omitted properties to their MTConnect defaults, and + /// flattening the grouped relationships back into a single collection. + /// public DataItem ToDataItem() { var dataItem = DataItem.Create(Type); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonDataItemDefinition.cs b/libraries/MTConnect.NET-JSON/Devices/JsonDataItemDefinition.cs index b35e1495b..2d42d771a 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonDataItemDefinition.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonDataItemDefinition.cs @@ -6,20 +6,45 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a Definition describing the + /// shape of a DATA_SET or TABLE data item's entries. Mirrors the + /// on-the-wire shape so the JSON serializer can read and write it, then + /// converts to and from the strongly-typed + /// model. + /// public class JsonDataItemDefinition { + /// + /// The free-form description of the data item definition. + /// [JsonPropertyName("description")] public string Description { get; set; } + /// + /// The entry definitions describing the keys of a DATA_SET or TABLE. + /// [JsonPropertyName("entryDefinitions")] public IEnumerable EntryDefinitions { get; set; } + /// + /// The cell definitions describing the columns shared by every TABLE + /// entry. + /// [JsonPropertyName("cellDefinitions")] public IEnumerable CellDefinitions { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDataItemDefinition() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , converting each entry and cell + /// definition. + /// public JsonDataItemDefinition(IDataItemDefinition dataItemDefinition) { if (dataItemDefinition != null) @@ -53,6 +78,11 @@ public JsonDataItemDefinition(IDataItemDefinition dataItemDefinition) + /// + /// Converts this surrogate to a strongly-typed + /// , converting each entry and cell + /// definition. + /// public IDataItemDefinition ToDefinition() { var definition = new DataItemDefinition(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonDataItemReference.cs b/libraries/MTConnect.NET-JSON/Devices/JsonDataItemReference.cs index f4c21c284..4f0a4632f 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonDataItemReference.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonDataItemReference.cs @@ -6,17 +6,35 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a DataItemReference, a pointer + /// from a component to one of its data items. Converts to and from the + /// strongly-typed model. + /// public class JsonDataItemReference { + /// + /// Reference to the id of the related data item. + /// [JsonPropertyName("idRef")] public string IdRef { get; set; } + /// + /// The human-readable name of the reference. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDataItemReference() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonDataItemReference(IDataItemReference reference) { if (reference != null) @@ -27,6 +45,9 @@ public JsonDataItemReference(IDataItemReference reference) } + /// + /// Converts this surrogate to a strongly-typed . + /// public virtual IReference ToReference() { var reference = new DataItemReference(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonDescription.cs b/libraries/MTConnect.NET-JSON/Devices/JsonDescription.cs index d7fb87cf1..3675296a4 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonDescription.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonDescription.cs @@ -5,26 +5,53 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a component or device + /// Description, carrying manufacturer identification and free-text + /// notes. + /// public class JsonDescription { + /// + /// The manufacturer of the component or device. + /// [JsonPropertyName("manufacturer")] public string Manufacturer { get; set; } + /// + /// The manufacturer's model designation. + /// [JsonPropertyName("model")] public string Model { get; set; } + /// + /// The serial number of the component or device. + /// [JsonPropertyName("serialNumber")] public string SerialNumber { get; set; } + /// + /// The station the component or device belongs to. + /// [JsonPropertyName("station")] public string Station { get; set; } + /// + /// The free-text description body. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDescription() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonDescription(IDescription description) { if (description != null) @@ -38,6 +65,9 @@ public JsonDescription(IDescription description) } + /// + /// Converts this surrogate to a strongly-typed . + /// public IDescription ToDescription() { var description = new Description(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonDevice.cs b/libraries/MTConnect.NET-JSON/Devices/JsonDevice.cs index 7a1b4fd74..d889f63a3 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonDevice.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonDevice.cs @@ -8,62 +8,134 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for an MTConnect Device, the + /// top-level component of an MTConnectDevices document. Mirrors the + /// on-the-wire shape so the JSON serializer can read and write it, then + /// converts to and from the strongly-typed model. + /// public class JsonDevice { + /// + /// The unique id of the device. + /// [JsonPropertyName("id")] public string Id { get; set; } + /// + /// The MTConnect device type (typically Device or Agent). + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The human-readable name of the device. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The universally unique identifier of the device. + /// [JsonPropertyName("uuid")] public string Uuid { get; set; } + /// + /// The hash uniquely identifying the device's current configuration. + /// [JsonPropertyName("hash")] public string Hash { get; set; } + /// + /// The ISO 841 classification of the device. + /// [JsonPropertyName("iso841Class")] public string Iso841Class { get; set; } + /// + /// The name the device is known by in the native data source, when it + /// differs from . + /// [JsonPropertyName("nativeName")] public string NativeName { get; set; } + /// + /// The interval, in milliseconds, between samples of the device's + /// data, when reported. + /// [JsonPropertyName("sampleInterval")] public double? SampleInterval { get; set; } + /// + /// The rate, in samples per second, at which the device's data is + /// sampled, when reported. + /// [JsonPropertyName("sampleRate")] public double? SampleRate { get; set; } + /// + /// Reference to the id of a CoordinateSystem the device's + /// values are expressed relative to. + /// [JsonPropertyName("coordinateSystemIdRef")] public string CoordinateSystemIdRef { get; set; } + /// + /// The MTConnect schema version the device definition conforms to. + /// [JsonPropertyName("mtconnectVersion")] public string MTConnectVersion { get; set; } + /// + /// The descriptive metadata (manufacturer, model, serial number) for + /// the device. + /// [JsonPropertyName("description")] public JsonDescription Description { get; set; } + /// + /// The configuration (coordinate systems, motion, relationships, + /// specifications) of the device. + /// [JsonPropertyName("configuration")] public JsonConfiguration Configuration { get; set; } + /// + /// The data items reported directly by the device. + /// [JsonPropertyName("dataItems")] public IEnumerable DataItems { get; set; } + /// + /// The child components of the device. + /// [JsonPropertyName("components")] public IEnumerable Components { get; set; } + /// + /// The compositions (lower-level structural elements) of the device. + /// [JsonPropertyName("compositions")] public IEnumerable Compositions { get; set; } + /// + /// The references from the device to other components and data items. + /// [JsonPropertyName("references")] public JsonReferenceContainer References { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDevice() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , recursively converting the description, + /// configuration, references, data items, compositions, and + /// components. + /// public JsonDevice(IDevice device) { if (device != null) @@ -123,13 +195,31 @@ public JsonDevice(IDevice device) } + /// + /// Returns the JSON representation of this surrogate, optionally + /// indented for readability. + /// public string ToString(bool indent = false) => JsonFunctions.Convert(this, indented: indent); + /// + /// Returns the UTF-8 encoded JSON bytes of this surrogate, optionally + /// indented for readability. + /// public byte[] ToBytes(bool indent = false) => JsonFunctions.ConvertBytes(this, indented: indent); + /// + /// Returns a stream over the JSON representation of this surrogate, + /// optionally indented for readability. + /// public Stream ToStream(bool indent = false) => JsonFunctions.ConvertStream(this, indented: indent); + /// + /// Converts this surrogate to a strongly-typed , + /// parsing the MTConnect version and recursively converting the + /// description, configuration, references, data items, compositions, + /// and components. + /// public Device ToDevice() { var device = new Device(); @@ -175,7 +265,7 @@ public Device ToDevice() { compositions.Add(composition.ToComposition()); } - device.Compositions = compositions; + device.Compositions = compositions; } // Components diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonDevicesDocument.cs b/libraries/MTConnect.NET-JSON/Devices/JsonDevicesDocument.cs index 96c578bc5..8a273283b 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonDevicesDocument.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonDevicesDocument.cs @@ -6,11 +6,22 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for an MTConnectDevices response + /// document, carrying the header and the device collection. Converts to + /// and from the strongly-typed model. + /// public class JsonDevicesDocument { + /// + /// The document header. + /// [JsonPropertyName("header")] public JsonDevicesHeader Header { get; set; } + /// + /// The devices reported in the document. + /// [JsonPropertyName("devices")] public IEnumerable Devices { get; set; } @@ -18,8 +29,16 @@ public class JsonDevicesDocument //public IEnumerable Interfaces { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDevicesDocument() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , converting the header and + /// each device. + /// public JsonDevicesDocument(IDevicesResponseDocument document) { if (document != null) @@ -40,6 +59,11 @@ public JsonDevicesDocument(IDevicesResponseDocument document) } + /// + /// Converts this surrogate to a strongly-typed + /// , converting the header and + /// each device. + /// public DevicesResponseDocument ToDocument() { var document = new DevicesResponseDocument(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonDevicesHeader.cs b/libraries/MTConnect.NET-JSON/Devices/JsonDevicesHeader.cs index 5504dda54..b166b41ce 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonDevicesHeader.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonDevicesHeader.cs @@ -7,38 +7,80 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for the Header of an + /// MTConnectDevices document. Mirrors the on-the-wire shape so the JSON + /// serializer can read and write it, then converts to and from the + /// strongly-typed model. + /// public class JsonDevicesHeader { + /// + /// The instance identifier of the agent, which changes whenever the + /// agent's buffer is cleared. + /// [JsonPropertyName("instanceId")] public ulong InstanceId { get; set; } + /// + /// The MTConnect schema version of the document. + /// [JsonPropertyName("version")] public string Version { get; set; } + /// + /// The identifier of the agent that produced the document. + /// [JsonPropertyName("sender")] public string Sender { get; set; } + /// + /// The maximum number of observations the agent's buffer can hold. + /// [JsonPropertyName("bufferSize")] public ulong BufferSize { get; set; } + /// + /// The maximum number of assets the agent can store. + /// [JsonPropertyName("assetBufferSize")] public ulong AssetBufferSize { get; set; } + /// + /// The number of assets currently stored by the agent. + /// [JsonPropertyName("assetCount")] public ulong AssetCount { get; set; } + /// + /// The timestamp of the most recent change to the device model. + /// [JsonPropertyName("deviceModelChangeTime")] public string DeviceModelChangeTime { get; set; } + /// + /// Whether the document was produced for testing rather than + /// production use. + /// [JsonPropertyName("testIndicator")] public bool TestIndicator { get; set; } + /// + /// The time the document was created. + /// [JsonPropertyName("creationTime")] public DateTime CreationTime { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDevicesHeader() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonDevicesHeader(IMTConnectDevicesHeader header) { if (header != null) @@ -56,6 +98,10 @@ public JsonDevicesHeader(IMTConnectDevicesHeader header) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public virtual IMTConnectDevicesHeader ToDevicesHeader() { var header = new MTConnectDevicesHeader(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonEntryDefinition.cs b/libraries/MTConnect.NET-JSON/Devices/JsonEntryDefinition.cs index 8ded52d4b..9ff170316 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonEntryDefinition.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonEntryDefinition.cs @@ -6,32 +6,67 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for an EntryDefinition, which + /// describes the structure of an entry of a DATA_SET or TABLE data item. + /// Mirrors the on-the-wire shape so the JSON serializer can read and write + /// it, then converts to and from the strongly-typed + /// model. + /// public class JsonEntryDefinition { + /// + /// The key identifying the entry within the data set or table. + /// [JsonPropertyName("key")] public string Key { get; set; } + /// + /// The kind of value is interpreted as. + /// [JsonPropertyName("keyType")] public string KeyType { get; set; } + /// + /// The engineering units the entry values are expressed in. + /// [JsonPropertyName("units")] public string Units { get; set; } + /// + /// The MTConnect type the entry values report. + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The subtype further qualifying . + /// [JsonPropertyName("subType")] public string SubType { get; set; } + /// + /// The free-form description of the entry. + /// [JsonPropertyName("description")] public string Description { get; set; } + /// + /// The cell definitions describing the columns of a TABLE entry. + /// [JsonPropertyName("cellDefinitions")] public IEnumerable CellDefinitions { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonEntryDefinition() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , converting each cell definition. + /// public JsonEntryDefinition(IEntryDefinition definition) { if (definition != null) @@ -59,6 +94,10 @@ public JsonEntryDefinition(IEntryDefinition definition) } + /// + /// Converts this surrogate to a strongly-typed + /// , converting each cell definition. + /// public IEntryDefinition ToEntryDefinition() { var definition = new EntryDefinition(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonFilter.cs b/libraries/MTConnect.NET-JSON/Devices/JsonFilter.cs index eee552983..37df20e65 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonFilter.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonFilter.cs @@ -5,17 +5,35 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a data item Filter, which + /// limits how often a data item produces observations. Converts to and + /// from the strongly-typed model. + /// public class JsonFilter { + /// + /// The filter type (MINIMUM_DELTA or PERIOD), serialized as the + /// enumeration name. + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The filter threshold value. + /// [JsonPropertyName("value")] public double Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonFilter() { } + /// + /// Initializes the surrogate from a strongly-typed . + /// public JsonFilter(IFilter filter) { if (filter != null) @@ -26,6 +44,10 @@ public JsonFilter(IFilter filter) } + /// + /// Converts this surrogate to a strongly-typed , + /// parsing the filter type enumeration. + /// public IFilter ToFilter() { var filter = new Filter(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonMotion.cs b/libraries/MTConnect.NET-JSON/Devices/JsonMotion.cs index 824b3ebe1..93d3ec4af 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonMotion.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonMotion.cs @@ -6,44 +6,95 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a Configuration Motion, which + /// describes how a component moves relative to its parent. Mirrors the + /// on-the-wire shape so the JSON serializer can read and write it, then + /// converts to and from the strongly-typed model. + /// public class JsonMotion { + /// + /// The unique id of the motion definition. + /// [JsonPropertyName("id")] public string Id { get; set; } + /// + /// Reference to the id of the parent motion this motion is + /// defined relative to. + /// [JsonPropertyName("parentIdRef")] public string ParentIdRef { get; set; } + /// + /// Reference to the id of the coordinate system the motion is + /// expressed in. + /// [JsonPropertyName("coordinateSystemIdRef")] public string CoordinateSystemIdRef { get; set; } + /// + /// The kind of motion (for example REVOLUTE, PRISMATIC, or FIXED). + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// How the motion is actuated (DIRECT, VIRTUAL, or NONE). + /// [JsonPropertyName("actuation")] public string Actuation { get; set; } + /// + /// The free-form description of the motion. + /// [JsonPropertyName("description")] public string Description { get; set; } + /// + /// The origin of the motion as a coordinate triple, when expressed + /// inline. + /// [JsonPropertyName("origin")] public JsonOrigin Origin { get; set; } + /// + /// The origin of the motion as a data set, when expressed by + /// reference. + /// [JsonPropertyName("originDataSet")] public JsonOriginDataSet OriginDataSet { get; set; } + /// + /// The translation and rotation relating the motion to its parent. + /// [JsonPropertyName("transformation")] public JsonTransformation Transformation { get; set; } + /// + /// The axis of the motion as a vector, when expressed inline. + /// [JsonPropertyName("axis")] public JsonAxis Axis { get; set; } + /// + /// The axis of the motion as a data set, when expressed by reference. + /// [JsonPropertyName("axisDataSet")] public JsonAxisDataSet AxisDataSet { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonMotion() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , selecting the inline or data-set + /// representation for the origin and axis based on the source type. + /// public JsonMotion(IMotion motion) { if (motion != null) @@ -63,6 +114,11 @@ public JsonMotion(IMotion motion) } + /// + /// Converts this surrogate to a strongly-typed , + /// parsing the type and actuation enumerations and preferring the + /// data-set representation of the origin and axis when present. + /// public IMotion ToMotion() { var motion = new Motion(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonOrigin.cs b/libraries/MTConnect.NET-JSON/Devices/JsonOrigin.cs index 3ff6e8ad1..d289eba6e 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonOrigin.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonOrigin.cs @@ -9,14 +9,29 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for an Origin, the inline variant + /// carrying its coordinates as a single string (space-separated triple). + /// Converts to and from the strongly-typed model. + /// public class JsonOrigin { + /// + /// The origin coordinates as a space-separated triple. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonOrigin() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonOrigin(IOrigin origin) { if (origin != null) @@ -26,6 +41,9 @@ public JsonOrigin(IOrigin origin) } + /// + /// Converts this surrogate to a strongly-typed . + /// public IOrigin ToOrigin() { var origin = new Origin(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonOriginDataSet.cs b/libraries/MTConnect.NET-JSON/Devices/JsonOriginDataSet.cs index 409864445..f52a760f4 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonOriginDataSet.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonOriginDataSet.cs @@ -9,20 +9,42 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for an OriginDataSet, the variant + /// of an origin whose coordinates are references to data items rather than + /// inline numbers. Converts to and from the strongly-typed + /// model. + /// public class JsonOriginDataSet { + /// + /// Reference to the data item or value supplying the X coordinate. + /// [JsonPropertyName("x")] public string X { get; set; } + /// + /// Reference to the data item or value supplying the Y coordinate. + /// [JsonPropertyName("y")] public string Y { get; set; } + /// + /// Reference to the data item or value supplying the Z coordinate. + /// [JsonPropertyName("z")] public string Z { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonOriginDataSet() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonOriginDataSet(IOriginDataSet dataSet) { if (dataSet != null) @@ -34,6 +56,10 @@ public JsonOriginDataSet(IOriginDataSet dataSet) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IOriginDataSet ToOriginDataSet() { var dataSet = new OriginDataSet(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonProcessSpecification.cs b/libraries/MTConnect.NET-JSON/Devices/JsonProcessSpecification.cs index 206577261..541ee08c3 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonProcessSpecification.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonProcessSpecification.cs @@ -6,20 +6,43 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a ProcessSpecification, + /// extending with control, + /// specification, and alarm limit groups. Converts to and from the + /// strongly-typed model. + /// public class JsonProcessSpecification : JsonAbstractSpecification { + /// + /// The statistical control limits (sigma bands) for the process. + /// [JsonPropertyName("controlLimits")] public JsonControlLimits ControlLimits { get; set; } + /// + /// The specification limits (tolerance bands) for the process. + /// [JsonPropertyName("specificationLimits")] public JsonSpecificationLimits SpecificationLimits { get; set; } + /// + /// The alarm limits at which the process triggers warnings or faults. + /// [JsonPropertyName("alarmLimits")] public JsonAlarmLimits AlarmLimits { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonProcessSpecification() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , copying the common fields via + /// the base constructor and converting each limit group. + /// public JsonProcessSpecification(IProcessSpecification specification) : base(specification) { if (specification != null) @@ -31,6 +54,11 @@ public JsonProcessSpecification(IProcessSpecification specification) : base(spec } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing the originator + /// enumeration and converting each limit group. + /// public override ISpecification ToSpecification() { var specification = new ProcessSpecification(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonReferenceContainer.cs b/libraries/MTConnect.NET-JSON/Devices/JsonReferenceContainer.cs index 0cd1d5eb4..6300b12db 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonReferenceContainer.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonReferenceContainer.cs @@ -7,17 +7,36 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate that groups the references of a component + /// or composition by referenced kind (component or data item). Each kind is + /// serialized as a separate JSON array. + /// public class JsonReferenceContainer { + /// + /// References pointing at other components. + /// [JsonPropertyName("componentReferences")] public List ComponentReferences { get; set; } + /// + /// References pointing at data items. + /// [JsonPropertyName("dataItemReferences")] public List DataItemReferences { get; set; } + /// + /// Initializes an empty container. + /// public JsonReferenceContainer() { } + /// + /// Initializes the container by partitioning + /// into component and data item arrays + /// based on the concrete reference interface of each entry. + /// public JsonReferenceContainer(IEnumerable references) { if (!references.IsNullOrEmpty()) @@ -42,6 +61,10 @@ public JsonReferenceContainer(IEnumerable references) } } + /// + /// Flattens the component and data item arrays back into a single + /// reference collection. + /// public IEnumerable ToReferences() { var references = new List(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonRelationship.cs b/libraries/MTConnect.NET-JSON/Devices/JsonRelationship.cs index 8c2718b24..401d180c1 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonRelationship.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonRelationship.cs @@ -6,44 +6,99 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a Configuration Relationship. + /// A single surrogate shape carries every relationship kind (asset, + /// component, data item, device, and specification); only the properties + /// relevant to the originating relationship are populated, and the + /// corresponding ToXxxRelationship method reconstructs the concrete + /// strongly-typed relationship. + /// public class JsonRelationship { + /// + /// The unique id of the relationship, where the relationship + /// kind defines one. + /// [JsonPropertyName("id")] public string Id { get; set; } + /// + /// The human-readable name of the relationship. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The relationship type, interpreted as the relevant + /// relationship-type enumeration for the originating kind. + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The criticality (CRITICAL or NONCRITICAL) of the relationship. + /// [JsonPropertyName("criticality")] public string Criticality { get; set; } + /// + /// Reference to the id of the related component, data item, or + /// specification. + /// [JsonPropertyName("idRef")] public string IdRef { get; set; } + /// + /// Reference to the UUID of the related device, for a device + /// relationship. + /// [JsonPropertyName("deviceUuidRef")] public string DeviceUuidRef { get; set; } + /// + /// Reference to the assetId of the related asset, for an asset + /// relationship. + /// [JsonPropertyName("assetIdRef")] public string AssetIdRef { get; set; } + /// + /// The type of the related asset, for an asset relationship. + /// [JsonPropertyName("assetType")] public string AssetType { get; set; } + /// + /// The role (SYSTEM or AUXILIARY) the related device plays, for a + /// device relationship. + /// [JsonPropertyName("role")] public string Role { get; set; } + /// + /// The hyperlink reference to the related entity. + /// [JsonPropertyName("href")] public string Href { get; set; } + /// + /// The XLink type of the reference. + /// [JsonPropertyName("xLinkType")] public string XLinkType { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonRelationship() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , populating the asset reference + /// properties. + /// public JsonRelationship(IAssetRelationship relationship) { if (relationship != null) @@ -57,6 +112,11 @@ public JsonRelationship(IAssetRelationship relationship) } } + /// + /// Initializes the surrogate from a strongly-typed + /// , populating the component + /// reference properties. + /// public JsonRelationship(IComponentRelationship relationship) { if (relationship != null) @@ -69,6 +129,11 @@ public JsonRelationship(IComponentRelationship relationship) } } + /// + /// Initializes the surrogate from a strongly-typed + /// , populating the data item + /// reference properties. + /// public JsonRelationship(IDataItemRelationship relationship) { if (relationship != null) @@ -79,6 +144,11 @@ public JsonRelationship(IDataItemRelationship relationship) } } + /// + /// Initializes the surrogate from a strongly-typed + /// , populating the device reference + /// and XLink properties. + /// public JsonRelationship(IDeviceRelationship relationship) { if (relationship != null) @@ -94,6 +164,11 @@ public JsonRelationship(IDeviceRelationship relationship) } } + /// + /// Initializes the surrogate from a strongly-typed + /// , populating the + /// specification reference properties. + /// public JsonRelationship(ISpecificationRelationship relationship) { if (relationship != null) @@ -105,6 +180,10 @@ public JsonRelationship(ISpecificationRelationship relationship) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public virtual IAssetRelationship ToAssetRelationship() { var relationship = new AssetRelationship(); @@ -116,6 +195,11 @@ public virtual IAssetRelationship ToAssetRelationship() return relationship; } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing as + /// a . + /// public virtual IComponentRelationship ToComponentRelationship() { var relationship = new ComponentRelationship(); @@ -126,6 +210,11 @@ public virtual IComponentRelationship ToComponentRelationship() return relationship; } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing as a + /// . + /// public virtual IDataItemRelationship ToDataItemRelationship() { var relationship = new DataItemRelationship(); @@ -135,6 +224,11 @@ public virtual IDataItemRelationship ToDataItemRelationship() return relationship; } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing as a + /// . + /// public virtual IDeviceRelationship ToDeviceRelationship() { var relationship = new DeviceRelationship(); @@ -144,6 +238,11 @@ public virtual IDeviceRelationship ToDeviceRelationship() return relationship; } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing + /// as a . + /// public virtual ISpecificationRelationship ToSpecificationRelationship() { var relationship = new SpecificationRelationship(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonRelationshipContainer.cs b/libraries/MTConnect.NET-JSON/Devices/JsonRelationshipContainer.cs index 33bd2b564..e95d54b58 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonRelationshipContainer.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonRelationshipContainer.cs @@ -6,24 +6,48 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate that groups the related entities of a + /// component, composition, or data item by relationship kind. Each kind is + /// serialized as a separate JSON array, populated only when there is at + /// least one relationship of that kind. + /// public class JsonRelationshipContainer { + /// + /// The relationships pointing at related assets. + /// [JsonPropertyName("assetRelationships")] public List AssetRelationships { get; set; } + /// + /// The relationships pointing at related data items. + /// [JsonPropertyName("dataItemRelationships")] public List DataItemRelationships { get; set; } + /// + /// The relationships pointing at related components. + /// [JsonPropertyName("componentRelationships")] public List ComponentRelationships { get; set; } + /// + /// The relationships pointing at related devices. + /// [JsonPropertyName("deviceRelationships")] public List DeviceRelationships { get; set; } + /// + /// The relationships pointing at related specifications. + /// [JsonPropertyName("specificationRelationships")] public List SpecificationRelationships { get; set; } + /// + /// Initializes an empty container. + /// public JsonRelationshipContainer() { //DataItemRelationships = new List(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonRotation.cs b/libraries/MTConnect.NET-JSON/Devices/JsonRotation.cs index b8d79b933..be0cfb719 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonRotation.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonRotation.cs @@ -9,14 +9,29 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a Rotation, the inline variant + /// carrying its angles as a single string (space-separated triple). + /// Converts to and from the strongly-typed model. + /// public class JsonRotation { + /// + /// The rotation angles as a space-separated triple. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonRotation() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonRotation(IRotation rotation) { if (rotation != null) @@ -26,6 +41,9 @@ public JsonRotation(IRotation rotation) } + /// + /// Converts this surrogate to a strongly-typed . + /// public IRotation ToRotation() { var rotation = new Rotation(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonRotationDataSet.cs b/libraries/MTConnect.NET-JSON/Devices/JsonRotationDataSet.cs index 87b885b5e..ea5c4d910 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonRotationDataSet.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonRotationDataSet.cs @@ -9,20 +9,42 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a RotationDataSet, the variant + /// of a rotation whose angles are references to data items rather than + /// inline numbers. Converts to and from the strongly-typed + /// model. + /// public class JsonRotationDataSet { + /// + /// Reference to the data item or value supplying the A rotation angle. + /// [JsonPropertyName("a")] public string A { get; set; } + /// + /// Reference to the data item or value supplying the B rotation angle. + /// [JsonPropertyName("b")] public string B { get; set; } + /// + /// Reference to the data item or value supplying the C rotation angle. + /// [JsonPropertyName("c")] public string C { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonRotationDataSet() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonRotationDataSet(IRotationDataSet dataSet) { if (dataSet != null) @@ -34,6 +56,10 @@ public JsonRotationDataSet(IRotationDataSet dataSet) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IRotationDataSet ToRotationDataSet() { var dataSet = new RotationDataSet(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonScale.cs b/libraries/MTConnect.NET-JSON/Devices/JsonScale.cs index e11469f11..187b9adbd 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonScale.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonScale.cs @@ -9,14 +9,28 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a Scale, the inline variant + /// carrying its components as a single string (space-separated triple). + /// Converts to and from the strongly-typed model. + /// public class JsonScale { + /// + /// The scale factors as a space-separated triple. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonScale() { } + /// + /// Initializes the surrogate from a strongly-typed . + /// public JsonScale(IScale scale) { if (scale != null) @@ -26,6 +40,9 @@ public JsonScale(IScale scale) } + /// + /// Converts this surrogate to a strongly-typed . + /// public IScale ToScale() { var scale = new Scale(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonScaleDataSet.cs b/libraries/MTConnect.NET-JSON/Devices/JsonScaleDataSet.cs index 141daa79d..9e4a74447 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonScaleDataSet.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonScaleDataSet.cs @@ -9,20 +9,41 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a ScaleDataSet, the variant of + /// a scale whose components are reported per axis. Converts to and from + /// the strongly-typed model. + /// public class JsonScaleDataSet { + /// + /// The scale factor applied along the X axis. + /// [JsonPropertyName("x")] public double X { get; set; } + /// + /// The scale factor applied along the Y axis. + /// [JsonPropertyName("y")] public double Y { get; set; } + /// + /// The scale factor applied along the Z axis. + /// [JsonPropertyName("z")] public double Z { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonScaleDataSet() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonScaleDataSet(IScaleDataSet dataSet) { if (dataSet != null) @@ -34,6 +55,10 @@ public JsonScaleDataSet(IScaleDataSet dataSet) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public IScaleDataSet ToScaleDataSet() { var dataSet = new ScaleDataSet(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonSensorConfiguration.cs b/libraries/MTConnect.NET-JSON/Devices/JsonSensorConfiguration.cs index 7556f475a..2ba2e125d 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonSensorConfiguration.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonSensorConfiguration.cs @@ -8,26 +8,53 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a Component SensorConfiguration, + /// recording sensor firmware and calibration metadata along with the + /// per-channel configuration. + /// public class JsonSensorConfiguration { + /// + /// The firmware version of the sensor. + /// [JsonPropertyName("firmwareVersion")] public string FirmwareVersion { get; set; } + /// + /// The date the sensor was last calibrated. + /// [JsonPropertyName("calibrationDate")] public DateTime? CalibrationDate { get; set; } + /// + /// The date the sensor is next due for calibration. + /// [JsonPropertyName("nextCalibrationDate")] public DateTime? NextCalibrationDate { get; set; } + /// + /// The initials of the person who performed the calibration. + /// [JsonPropertyName("calibrationInitials")] public string CalibrationInitials { get; set; } + /// + /// The configuration of each sensing channel. + /// [JsonPropertyName("channels")] public List Channels { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonSensorConfiguration() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , converting each channel. + /// public JsonSensorConfiguration(ISensorConfiguration configuration) { if (configuration != null) @@ -51,6 +78,10 @@ public JsonSensorConfiguration(ISensorConfiguration configuration) } + /// + /// Converts this surrogate to a strongly-typed + /// , converting each channel. + /// public ISensorConfiguration ToSensorConfiguration() { var sensorConfiguration = new SensorConfiguration(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonSolidModel.cs b/libraries/MTConnect.NET-JSON/Devices/JsonSolidModel.cs index 8223727fe..0ee5ac9eb 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonSolidModel.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonSolidModel.cs @@ -6,38 +6,85 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a Configuration SolidModel, + /// which references the 3D geometry describing a component. Mirrors the + /// on-the-wire shape so the JSON serializer can read and write it, then + /// converts to and from the strongly-typed model. + /// public class JsonSolidModel { + /// + /// The unique id of the solid model. + /// [JsonPropertyName("id")] public string Id { get; set; } + /// + /// Reference to the id of another solid model this model is + /// derived from. + /// [JsonPropertyName("solidModelIdRef")] public string SolidModelIdRef { get; set; } + /// + /// The hyperlink to the external model file. + /// [JsonPropertyName("href")] public string Href { get; set; } + /// + /// The identifier of the specific item within the referenced model + /// file. + /// [JsonPropertyName("itemRef")] public string ItemRef { get; set; } + /// + /// The media type of the model file, serialized as the enumeration + /// name. + /// [JsonPropertyName("mediaType")] public string MediaType { get; set; } + /// + /// Reference to the id of the coordinate system the model + /// geometry is expressed in. + /// [JsonPropertyName("coordinateSystemIdRef")] public string CoordinateSystemIdRef { get; set; } + /// + /// The translation and rotation applied to the model geometry. + /// [JsonPropertyName("transformation")] public JsonTransformation Transformation { get; set; } + /// + /// The scale applied to the model geometry as a vector, when expressed + /// inline. + /// [JsonPropertyName("scale")] public JsonScale Scale { get; set; } + /// + /// The scale applied to the model geometry as a data set, when + /// expressed by reference. + /// [JsonPropertyName("scaleDataSet")] public JsonScaleDataSet ScaleDataSet { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonSolidModel() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , selecting the inline or data-set + /// representation for the scale based on the source type. + /// public JsonSolidModel(ISolidModel solidModel) { if (solidModel != null) @@ -54,6 +101,11 @@ public JsonSolidModel(ISolidModel solidModel) } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing the media type enumeration and + /// preferring the data-set representation of the scale when present. + /// public ISolidModel ToSolidModel() { var solidModel = new SolidModel(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonSource.cs b/libraries/MTConnect.NET-JSON/Devices/JsonSource.cs index 8a5b7ad4e..38fe2265a 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonSource.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonSource.cs @@ -6,23 +6,46 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a DataItem Source, identifying + /// the component, data item, or composition that originates the data item's + /// observations. + /// public class JsonSource { + /// + /// The id of the originating component. + /// [JsonPropertyName("componentId")] public string ComponentId { get; set; } + /// + /// The id of the originating data item. + /// [JsonPropertyName("dataItemId")] public string DataItemId { get; set; } + /// + /// The id of the originating composition. + /// [JsonPropertyName("compositionId")] public string CompositionId { get; set; } + /// + /// The free-text source description. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonSource() { } + /// + /// Initializes the surrogate from a strongly-typed . + /// public JsonSource(ISource source) { if (source != null) @@ -35,6 +58,9 @@ public JsonSource(ISource source) } + /// + /// Converts this surrogate to a strongly-typed . + /// public ISource ToSource() { var source = new Source(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonSpecification.cs b/libraries/MTConnect.NET-JSON/Devices/JsonSpecification.cs index 492ad0ee3..be436947a 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonSpecification.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonSpecification.cs @@ -6,32 +6,67 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a Configuration Specification, + /// extending with the scalar limit + /// values. Converts to and from the strongly-typed + /// model. + /// public class JsonSpecification : JsonAbstractSpecification { + /// + /// The absolute maximum permitted value. + /// [JsonPropertyName("maximum")] public double? Maximum { get; set; } + /// + /// The upper limit at which the value is out of specification. + /// [JsonPropertyName("upperLimit")] public double? UpperLimit { get; set; } + /// + /// The upper value at which a warning is raised. + /// [JsonPropertyName("upperWarning")] public double? UpperWarning { get; set; } + /// + /// The nominal (target) value. + /// [JsonPropertyName("nominal")] public double? Nominal { get; set; } + /// + /// The lower limit at which the value is out of specification. + /// [JsonPropertyName("lowerLimit")] public double? LowerLimit { get; set; } + /// + /// The lower value at which a warning is raised. + /// [JsonPropertyName("lowerWarning")] public double? LowerWarning { get; set; } + /// + /// The absolute minimum permitted value. + /// [JsonPropertyName("minimum")] public double? Minimum { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonSpecification() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , copying the common fields via the base + /// constructor and the scalar limits here. + /// public JsonSpecification(ISpecification specification) : base(specification) { if (specification != null) @@ -47,6 +82,11 @@ public JsonSpecification(ISpecification specification) : base(specification) } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing the originator enumeration and + /// applying the scalar limit values. + /// public override ISpecification ToSpecification() { var specification = new Specification(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonSpecificationLimits.cs b/libraries/MTConnect.NET-JSON/Devices/JsonSpecificationLimits.cs index b07808181..d44ccd20b 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonSpecificationLimits.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonSpecificationLimits.cs @@ -6,20 +6,42 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for the SpecificationLimits of a + /// process specification, namely the tolerance band around the nominal + /// value. Converts to and from the strongly-typed + /// model. + /// public class JsonSpecificationLimits { + /// + /// The upper specification limit (USL). + /// [JsonPropertyName("upperLimit")] public double? UpperLimit { get; set; } + /// + /// The nominal (target) value. + /// [JsonPropertyName("nominal")] public double? Nominal { get; set; } + /// + /// The lower specification limit (LSL). + /// [JsonPropertyName("lowerLimit")] public double? LowerLimit { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonSpecificationLimits() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonSpecificationLimits(ISpecificationLimits specificationLimits) { if (specificationLimits != null) @@ -31,6 +53,10 @@ public JsonSpecificationLimits(ISpecificationLimits specificationLimits) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public ISpecificationLimits ToSpecificationLimits() { var specificationLimits = new SpecificationLimits(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonTransformation.cs b/libraries/MTConnect.NET-JSON/Devices/JsonTransformation.cs index e9a999780..2d3e2c71c 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonTransformation.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonTransformation.cs @@ -6,23 +6,49 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a CoordinateSystem Transformation, + /// expressing the translation and rotation that relate one coordinate + /// system to its parent. Each of translation and rotation is carried either + /// as a scalar value or as a keyed data set. + /// public class JsonTransformation { + /// + /// The translation expressed as a scalar value. + /// [JsonPropertyName("translation")] public JsonTranslation Translation { get; set; } + /// + /// The translation expressed as a keyed data set. + /// [JsonPropertyName("translationDataSet")] public JsonTranslationDataSet TranslationDataSet { get; set; } + /// + /// The rotation expressed as a scalar value. + /// [JsonPropertyName("rotation")] public JsonRotation Rotation { get; set; } + /// + /// The rotation expressed as a keyed data set. + /// [JsonPropertyName("rotationDataSet")] public JsonRotationDataSet RotationDataSet { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonTransformation() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , selecting the scalar or data-set + /// representation of translation and rotation as appropriate. + /// public JsonTransformation(ITransformation transformation) { if (transformation != null) @@ -35,6 +61,11 @@ public JsonTransformation(ITransformation transformation) } + /// + /// Converts this surrogate to a strongly-typed + /// , preferring the data-set form over the + /// scalar form when both are present. + /// public ITransformation ToTransformation() { var transformation = new Transformation(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonTranslation.cs b/libraries/MTConnect.NET-JSON/Devices/JsonTranslation.cs index 4da8b186c..f0ede42c1 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonTranslation.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonTranslation.cs @@ -9,14 +9,30 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a Translation, the inline + /// variant carrying its offsets as a single string (space-separated + /// triple). Converts to and from the strongly-typed + /// model. + /// public class JsonTranslation { + /// + /// The translation offsets as a space-separated triple. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonTranslation() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonTranslation(ITranslation translation) { if (translation != null) @@ -26,6 +42,9 @@ public JsonTranslation(ITranslation translation) } + /// + /// Converts this surrogate to a strongly-typed . + /// public ITranslation ToTranslation() { var translation = new Translation(); diff --git a/libraries/MTConnect.NET-JSON/Devices/JsonTranslationDataSet.cs b/libraries/MTConnect.NET-JSON/Devices/JsonTranslationDataSet.cs index 3296fe9c1..1d5c31d05 100644 --- a/libraries/MTConnect.NET-JSON/Devices/JsonTranslationDataSet.cs +++ b/libraries/MTConnect.NET-JSON/Devices/JsonTranslationDataSet.cs @@ -9,20 +9,42 @@ namespace MTConnect.Devices.Json { + /// + /// JSON serialization surrogate for a TranslationDataSet, the + /// variant of a translation whose offsets are references to data items + /// rather than inline numbers. Converts to and from the strongly-typed + /// model. + /// public class JsonTranslationDataSet { + /// + /// Reference to the data item or value supplying the X offset. + /// [JsonPropertyName("x")] public string X { get; set; } + /// + /// Reference to the data item or value supplying the Y offset. + /// [JsonPropertyName("y")] public string Y { get; set; } + /// + /// Reference to the data item or value supplying the Z offset. + /// [JsonPropertyName("z")] public string Z { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonTranslationDataSet() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonTranslationDataSet(ITranslationDataSet dataSet) { if (dataSet != null) @@ -34,6 +56,10 @@ public JsonTranslationDataSet(ITranslationDataSet dataSet) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public ITranslationDataSet ToTranslationDataSet() { var dataSet = new TranslationDataSet(); diff --git a/libraries/MTConnect.NET-JSON/Formatters/JsonEntityFormatter.cs b/libraries/MTConnect.NET-JSON/Formatters/JsonEntityFormatter.cs index 5dc3452e7..05732067f 100644 --- a/libraries/MTConnect.NET-JSON/Formatters/JsonEntityFormatter.cs +++ b/libraries/MTConnect.NET-JSON/Formatters/JsonEntityFormatter.cs @@ -23,13 +23,29 @@ namespace MTConnect.Formatters { + /// + /// that serializes and deserializes + /// individual MTConnect entities (devices, observations, and assets) to + /// and from JSON using the Json surrogate types. + /// public class JsonEntityFormatter : IEntityFormatter { + /// + /// The identifier of this formatter, JSON. + /// public string Id => "JSON"; + /// + /// The MIME content type produced by this formatter, + /// application/json. + /// public string ContentType => "application/json"; + /// + /// Serializes a device to a JSON stream, honoring the + /// indentOutput option. + /// public FormatWriteResult Format(IDevice device, IEnumerable> options = null) { if (device != null) @@ -46,6 +62,12 @@ public FormatWriteResult Format(IDevice device, IEnumerable + /// Serializes a single observation to a JSON stream, selecting the + /// sample, event, or condition surrogate by the observation's category + /// and honoring the categoryOutput and instanceIdOutput + /// options. + /// public FormatWriteResult Format(IObservation observation, IEnumerable> options = null) { if (observation != null) @@ -97,6 +119,12 @@ public FormatWriteResult Format(IObservation observation, IEnumerable + /// Serializes a collection of observations to a JSON array stream, + /// selecting the appropriate surrogate per observation by category and + /// honoring the categoryOutput and instanceIdOutput + /// options. + /// public FormatWriteResult Format(IEnumerable observations, IEnumerable> options = null) { if (!observations.IsNullOrEmpty()) @@ -153,6 +181,11 @@ public FormatWriteResult Format(IEnumerable observations, IEnumera return FormatWriteResult.Error(); } + /// + /// Serializes an asset to a JSON stream, selecting the surrogate that + /// matches the asset's type and falling back to direct serialization + /// for unrecognized types. + /// public FormatWriteResult Format(IAsset asset, IEnumerable> options = null) { if (asset != null) @@ -179,6 +212,10 @@ public FormatWriteResult Format(IAsset asset, IEnumerable + /// Deserializes a device from a JSON stream, returning an + /// unsuccessful result if the content cannot be parsed. + /// public FormatReadResult CreateDevice(Stream content, IEnumerable> options = null) { var messages = new List(); @@ -198,6 +235,10 @@ public FormatReadResult CreateDevice(Stream content, IEnumerable(); } + /// + /// Deserializes a component from a JSON stream, returning an + /// unsuccessful result if the content cannot be parsed. + /// public FormatReadResult CreateComponent(Stream content, IEnumerable> options = null) { var messages = new List(); @@ -217,6 +258,10 @@ public FormatReadResult CreateComponent(Stream content, IEnumerable< return new FormatReadResult(); } + /// + /// Deserializes a composition from a JSON stream, returning an + /// unsuccessful result if the content cannot be parsed. + /// public FormatReadResult CreateComposition(Stream content, IEnumerable> options = null) { var messages = new List(); @@ -236,6 +281,10 @@ public FormatReadResult CreateComposition(Stream content, IEnumera return new FormatReadResult(); } + /// + /// Deserializes a data item from a JSON stream, returning an + /// unsuccessful result if the content cannot be parsed. + /// public FormatReadResult CreateDataItem(Stream content, IEnumerable> options = null) { var messages = new List(); @@ -255,6 +304,11 @@ public FormatReadResult CreateDataItem(Stream content, IEnumerable(); } + /// + /// Deserializes an asset of the given type from a JSON stream, + /// selecting the surrogate that matches + /// and collecting any parse errors in the result. + /// public FormatReadResult CreateAsset(string assetType, Stream content, IEnumerable> options = null) { var messages = new List(); @@ -281,7 +335,7 @@ public FormatReadResult CreateAsset(string assetType, Stream content, IE { switch (assetType) { - case "CuttingTool": + case "CuttingTool": asset = JsonSerializer.Deserialize(json).ToCuttingToolAsset(); break; diff --git a/libraries/MTConnect.NET-JSON/Formatters/JsonInputFormatter.cs b/libraries/MTConnect.NET-JSON/Formatters/JsonInputFormatter.cs index 58f0d1587..0d47e7361 100644 --- a/libraries/MTConnect.NET-JSON/Formatters/JsonInputFormatter.cs +++ b/libraries/MTConnect.NET-JSON/Formatters/JsonInputFormatter.cs @@ -13,13 +13,28 @@ namespace MTConnect.Formatters { + /// + /// that serializes and deserializes input + /// payloads (device definitions, observation groups, and asset groups) to + /// and from JSON using the Json input surrogate types. + /// public class JsonInputFormatter : IInputFormatter { + /// + /// The identifier of this formatter, JSON. + /// public string Id => "JSON"; + /// + /// The MIME content type produced by this formatter, + /// application/json. + /// public string ContentType => "application/json"; + /// + /// Serializes a device input to a JSON stream. + /// public FormatWriteResult Format(IDeviceInput device, IEnumerable> options = null) { if (device != null) @@ -34,6 +49,10 @@ public FormatWriteResult Format(IDeviceInput device, IEnumerable + /// Serializes a collection of observation inputs to a JSON stream, + /// grouping observations sharing a device and timestamp. + /// public FormatWriteResult Format(IEnumerable observations, IEnumerable> options = null) { if (!observations.IsNullOrEmpty()) @@ -48,6 +67,10 @@ public FormatWriteResult Format(IEnumerable observations, IEn return FormatWriteResult.Error(); } + /// + /// Serializes a collection of asset inputs to a JSON stream as an + /// input asset group. + /// public FormatWriteResult Format(IEnumerable assets, IEnumerable> options = null) { if (!assets.IsNullOrEmpty()) @@ -67,6 +90,10 @@ public FormatWriteResult Format(IEnumerable assets, IEnumerable + /// Deserializes a device from JSON byte content, returning an + /// unsuccessful result if the content cannot be parsed. + /// public FormatReadResult CreateDevice(byte[] content, IEnumerable> options = null) { var messages = new List(); @@ -86,6 +113,10 @@ public FormatReadResult CreateDevice(byte[] content, IEnumerable(); } + /// + /// Deserializes observation inputs from JSON byte content, sorting + /// the groups by timestamp and flattening their observations. + /// public FormatReadResult> CreateObservations(byte[] content, IEnumerable> options = null) { var messages = new List(); @@ -110,6 +141,9 @@ public FormatReadResult> CreateObservations(byte[ return new FormatReadResult>(); } + /// + /// Deserializes assets from JSON byte content as an input asset group. + /// public FormatReadResult> CreateAssets(byte[] content, IEnumerable> options = null) { var messages = new List(); diff --git a/libraries/MTConnect.NET-JSON/Formatters/JsonResponseDocumentFormatter.cs b/libraries/MTConnect.NET-JSON/Formatters/JsonResponseDocumentFormatter.cs index a3c20d54a..3983d24ff 100644 --- a/libraries/MTConnect.NET-JSON/Formatters/JsonResponseDocumentFormatter.cs +++ b/libraries/MTConnect.NET-JSON/Formatters/JsonResponseDocumentFormatter.cs @@ -17,13 +17,29 @@ namespace MTConnect.Formatters { + /// + /// that serializes and + /// deserializes complete MTConnect response documents (devices, streams, + /// assets, and errors) to and from JSON using the Json surrogate types. + /// public class JsonResponseDocumentFormatter : IResponseDocumentFormatter { + /// + /// The identifier of this formatter, JSON. + /// public string Id => "JSON"; + /// + /// The MIME content type produced by this formatter, + /// application/json. + /// public string ContentType => "application/json"; + /// + /// Serializes an MTConnectDevices response document to a JSON stream, + /// honoring the indentOutput option. + /// public FormatWriteResult Format(IDevicesResponseDocument document, IEnumerable> options = null) { // Read Indent Option passed to Formatter @@ -40,6 +56,10 @@ public FormatWriteResult Format(IDevicesResponseDocument document, IEnumerable + /// Serializes an MTConnectStreams response document to a JSON stream, + /// honoring the indentOutput option. + /// public FormatWriteResult Format(ref IStreamsResponseOutputDocument document, IEnumerable> options = null) { // Read Indent Option passed to Formatter @@ -56,6 +76,10 @@ public FormatWriteResult Format(ref IStreamsResponseOutputDocument document, IEn return FormatWriteResult.Error(); } + /// + /// Serializes an MTConnectAssets response document to a JSON stream, + /// honoring the indentOutput option. + /// public FormatWriteResult Format(IAssetsResponseDocument document, IEnumerable> options = null) { // Read Indent Option passed to Formatter @@ -72,6 +96,10 @@ public FormatWriteResult Format(IAssetsResponseDocument document, IEnumerable + /// Serializes an MTConnectError response document to a JSON stream, + /// honoring the indentOutput option. + /// public FormatWriteResult Format(IErrorResponseDocument document, IEnumerable> options = null) { // Read Indent Option passed to Formatter @@ -89,6 +117,10 @@ public FormatWriteResult Format(IErrorResponseDocument document, IEnumerable + /// Deserializes an MTConnectDevices response document from a JSON + /// stream. + /// public FormatReadResult CreateDevicesResponseDocument(Stream content, IEnumerable> options = null) { // Read Document @@ -98,6 +130,10 @@ public FormatReadResult CreateDevicesResponseDocument( return new FormatReadResult(document.ToDocument(), success); } + /// + /// Deserializes an MTConnectStreams response document from a JSON + /// stream. + /// public FormatReadResult CreateStreamsResponseDocument(Stream content, IEnumerable> options = null) { // Read Document @@ -107,6 +143,10 @@ public FormatReadResult CreateStreamsResponseDocument( return new FormatReadResult(document.ToStreamsDocument(), success); } + /// + /// Deserializes an MTConnectAssets response document from a JSON + /// stream. + /// public FormatReadResult CreateAssetsResponseDocument(Stream content, IEnumerable> options = null) { // Read Document @@ -116,6 +156,10 @@ public FormatReadResult CreateAssetsResponseDocument(St return new FormatReadResult(document, success); } + /// + /// Deserializes an MTConnectError response document from a JSON + /// stream. + /// public FormatReadResult CreateErrorResponseDocument(Stream content, IEnumerable> options = null) { // Read Document diff --git a/libraries/MTConnect.NET-JSON/Input/JsonInputAssetGroup.cs b/libraries/MTConnect.NET-JSON/Input/JsonInputAssetGroup.cs index 6e91390d4..d527ffc2e 100644 --- a/libraries/MTConnect.NET-JSON/Input/JsonInputAssetGroup.cs +++ b/libraries/MTConnect.NET-JSON/Input/JsonInputAssetGroup.cs @@ -16,24 +16,48 @@ namespace MTConnect.Mqtt { + /// + /// JSON serialization surrogate for a group of asset inputs partitioned by + /// asset type. Used to carry multiple assets of different types in a single + /// JSON payload over transports such as MQTT. + /// public class JsonInputAssetGroup { + /// + /// The ComponentConfigurationParameters assets in the group. + /// [JsonPropertyName("componentConfigurationParameters")] public List ComponentConfigurationParameters { get; set; } + /// + /// The CuttingTool assets in the group. + /// [JsonPropertyName("cuttingTool")] public List CuttingTools { get; set; } + /// + /// The File assets in the group. + /// [JsonPropertyName("file")] public List Files { get; set; } + /// + /// The RawMaterial assets in the group. + /// [JsonPropertyName("rawMaterials")] public List RawMaterials { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonInputAssetGroup() { } - public JsonInputAssetGroup(IEnumerable assets) + /// + /// Initializes the surrogate from a collection of asset inputs, + /// dispatching each by its asset type to the matching surrogate list. + /// + public JsonInputAssetGroup(IEnumerable assets) { if (!assets.IsNullOrEmpty()) { @@ -85,6 +109,11 @@ public JsonInputAssetGroup(IEnumerable assets) } + /// + /// Flattens the type-partitioned surrogates of + /// into a single asset collection by + /// converting each surrogate to its strongly-typed asset. + /// public static IEnumerable ToAssets(JsonInputAssetGroup inputAssetGroup) { var assets = new List(); diff --git a/libraries/MTConnect.NET-JSON/Input/JsonInputObservation.cs b/libraries/MTConnect.NET-JSON/Input/JsonInputObservation.cs index 403f2cf80..90d9d41d8 100644 --- a/libraries/MTConnect.NET-JSON/Input/JsonInputObservation.cs +++ b/libraries/MTConnect.NET-JSON/Input/JsonInputObservation.cs @@ -7,23 +7,48 @@ namespace MTConnect.Mqtt { + /// + /// JSON serialization surrogate for a single observation input within a + /// . Carries the data item key and + /// its observation values as a string dictionary, allowing all + /// representations to share a uniform on-the-wire shape. + /// public class JsonInputObservation { + /// + /// The data item key (id or name) the observation reports against. + /// [JsonPropertyName("dataItem")] public string DataItem { get; set; } + /// + /// The observation values keyed by MTConnect value key (for example + /// Result, ResetTriggered, Level). + /// [JsonPropertyName("values")] public Dictionary Values { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonInputObservation() { } + /// + /// Initializes the surrogate directly from a data item key and value + /// dictionary. + /// public JsonInputObservation(string dataItemKey, Dictionary values) { DataItem = dataItemKey; Values = values; } + /// + /// Initializes the surrogate from a strongly-typed + /// , copying its non-empty value entries + /// into . + /// public JsonInputObservation(IObservationInput observation) { if (observation != null && !observation.Values.IsNullOrEmpty()) diff --git a/libraries/MTConnect.NET-JSON/Input/JsonInputObservationGroup.cs b/libraries/MTConnect.NET-JSON/Input/JsonInputObservationGroup.cs index b341981b9..19c9c16c9 100644 --- a/libraries/MTConnect.NET-JSON/Input/JsonInputObservationGroup.cs +++ b/libraries/MTConnect.NET-JSON/Input/JsonInputObservationGroup.cs @@ -9,18 +9,37 @@ namespace MTConnect.Mqtt { + /// + /// JSON serialization surrogate for a group of observation inputs sharing + /// a single timestamp. Used to batch observations recorded at the same + /// instant in a single JSON payload over transports such as MQTT. + /// public class JsonInputObservationGroup { + /// + /// The timestamp at which the observations in the group were + /// recorded. + /// [JsonPropertyName("timestamp")] public DateTime Timestamp { get; set; } + /// + /// The observations sharing . + /// [JsonPropertyName("observations")] public List Observations { get; set; } = new List(); + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonInputObservationGroup() { } - public JsonInputObservationGroup(IObservationInput observation) + /// + /// Initializes the surrogate as a single-observation group at the + /// observation's timestamp. + /// + public JsonInputObservationGroup(IObservationInput observation) { if (observation != null) { @@ -32,6 +51,11 @@ public JsonInputObservationGroup(IObservationInput observation) } } + /// + /// Partitions by distinct timestamp + /// and returns one group per timestamp, or null when the input is + /// empty. + /// public static IEnumerable Create(IEnumerable observations) { if (!observations.IsNullOrEmpty()) @@ -62,6 +86,10 @@ public static IEnumerable Create(IEnumerable + /// Converts the observations in this group to strongly-typed + /// observation inputs, applying to each. + /// public IEnumerable ToObservationInputs() { var observations = new List(); diff --git a/libraries/MTConnect.NET-JSON/JsonFunctions.cs b/libraries/MTConnect.NET-JSON/JsonFunctions.cs index 1a1a09432..908940911 100644 --- a/libraries/MTConnect.NET-JSON/JsonFunctions.cs +++ b/libraries/MTConnect.NET-JSON/JsonFunctions.cs @@ -8,8 +8,20 @@ namespace MTConnect { + /// + /// JSON serialization helpers shared by the MTConnect JSON surrogate + /// types. Provides the default and indented + /// presets, ISO 8601 timestamp formatting, and convenience methods for + /// serializing to a string, byte array, or stream. + /// public static class JsonFunctions { + /// + /// The default used by MTConnect + /// JSON serialization: compact output, default-valued properties + /// omitted on write (on net5+), numbers read from strings (on net5+), + /// case-insensitive property names, and a depth limit of 1000. + /// public static JsonSerializerOptions DefaultOptions { get @@ -27,6 +39,10 @@ public static JsonSerializerOptions DefaultOptions } } + /// + /// The indented variant of , used when the + /// formatter's indentOutput option is set. + /// public static JsonSerializerOptions IndentOptions { get @@ -45,11 +61,19 @@ public static JsonSerializerOptions IndentOptions } + /// + /// Formats as a round-trip ISO 8601 + /// string (the o format). + /// public static string GetTimestamp(DateTime timestamp) { return timestamp.ToString("o"); } + /// + /// Formats as a round-trip ISO 8601 + /// string, normalizing to UTC when the offset is zero. + /// public static string GetTimestamp(DateTimeOffset timestamp) { if (timestamp.Offset != TimeSpan.Zero) @@ -62,6 +86,11 @@ public static string GetTimestamp(DateTimeOffset timestamp) } } + /// + /// Serializes to a JSON string using the MTConnect + /// default options, optionally indented and optionally extended with a + /// custom converter. Returns null on any serialization error. + /// public static string Convert(object obj, JsonConverter converter = null, bool indented = false) { if (obj != null) @@ -89,6 +118,12 @@ public static string Convert(object obj, JsonConverter converter = null, bool in return null; } + /// + /// Serializes to UTF-8 encoded JSON bytes using + /// the MTConnect default options, optionally indented and optionally + /// extended with a custom converter. Returns null on any serialization + /// error. + /// public static byte[] ConvertBytes(object obj, JsonConverter converter = null, bool indented = false) { if (obj != null) @@ -116,6 +151,12 @@ public static byte[] ConvertBytes(object obj, JsonConverter converter = null, bo return null; } + /// + /// Serializes to a JSON stream using the + /// MTConnect default options, optionally indented and optionally + /// extended with a custom converter. Returns null on any serialization + /// error. + /// public static Stream ConvertStream(object obj, JsonConverter converter = null, bool indented = false) { if (obj != null) diff --git a/libraries/MTConnect.NET-JSON/Streams/JsonCell.cs b/libraries/MTConnect.NET-JSON/Streams/JsonCell.cs index 03507ec64..05440057e 100644 --- a/libraries/MTConnect.NET-JSON/Streams/JsonCell.cs +++ b/libraries/MTConnect.NET-JSON/Streams/JsonCell.cs @@ -6,17 +6,35 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for a TABLE-observation Cell, a + /// single column value within a table entry. Constructs from a + /// strongly-typed . + /// public class JsonCell { + /// + /// The column key. + /// [JsonPropertyName("key")] public string Key { get; set; } + /// + /// The cell value. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCell() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonCell(ITableCell cell) { if (cell != null) diff --git a/libraries/MTConnect.NET-JSON/Streams/JsonComponentStream.cs b/libraries/MTConnect.NET-JSON/Streams/JsonComponentStream.cs index 065091f64..32bda827f 100644 --- a/libraries/MTConnect.NET-JSON/Streams/JsonComponentStream.cs +++ b/libraries/MTConnect.NET-JSON/Streams/JsonComponentStream.cs @@ -9,23 +9,50 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for a ComponentStream, the + /// observations reported for a single component within a device stream. + /// Mirrors the on-the-wire shape so the JSON serializer can read and write + /// it, then converts to and from the strongly-typed + /// model. + /// public class JsonComponentStream { + /// + /// The MTConnect type of the component the observations belong to. + /// [JsonPropertyName("component")] public string Component { get; set; } + /// + /// Reference to the id of the component the observations belong + /// to. + /// [JsonPropertyName("componentId")] public string ComponentId { get; set; } + /// + /// The name of the component the observations belong to. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The native name of the component the observations belong to. + /// [JsonPropertyName("nativeName")] public string NativeName { get; set; } + /// + /// The UUID of the component the observations belong to. + /// [JsonPropertyName("uuid")] public string Uuid { get; set; } + /// + /// The combined sample, event, and condition observations converted to + /// their strongly-typed form. Not serialized. + /// [JsonIgnore] public List Observations { @@ -52,18 +79,37 @@ public List Observations } } + /// + /// The sample (SAMPLE category) observations reported for the + /// component. + /// [JsonPropertyName("samples")] public IEnumerable Samples { get; set; } + /// + /// The event (EVENT category) observations reported for the component. + /// [JsonPropertyName("events")] public IEnumerable Events { get; set; } + /// + /// The condition (CONDITION category) observations reported for the + /// component. + /// [JsonPropertyName("condition")] public IEnumerable Conditions { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonComponentStream() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , partitioning the observations + /// into samples, events, and conditions by category. + /// public JsonComponentStream(IComponentStreamOutput componentStream) { if (componentStream != null) @@ -116,6 +162,11 @@ public JsonComponentStream(IComponentStreamOutput componentStream) } + /// + /// Converts this surrogate to a strongly-typed + /// , merging the samples, events, and + /// conditions back into a single observation collection. + /// public ComponentStream ToComponentStream() { var componentStream = new ComponentStream(); @@ -165,5 +216,5 @@ public ComponentStream ToComponentStream() return componentStream; } - } + } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-JSON/Streams/JsonCondition.cs b/libraries/MTConnect.NET-JSON/Streams/JsonCondition.cs index 20dfe0929..934125d62 100644 --- a/libraries/MTConnect.NET-JSON/Streams/JsonCondition.cs +++ b/libraries/MTConnect.NET-JSON/Streams/JsonCondition.cs @@ -8,23 +8,53 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for a CONDITION-category observation, + /// extending with the condition-specific + /// properties. Converts to and from the strongly-typed + /// model. + /// public class JsonCondition : JsonObservation { + /// + /// The condition level (NORMAL, WARNING, FAULT, or UNAVAILABLE). + /// [JsonPropertyName("level")] public string Level { get; set; } + /// + /// The severity of the condition as reported by the native data + /// source. + /// [JsonPropertyName("nativeSeverity")] public string NativeSeverity { get; set; } + /// + /// The qualifier (for example HIGH or LOW) further classifying the + /// condition. + /// [JsonPropertyName("qualifier")] public string Qualifier { get; set; } + /// + /// The statistical operation associated with the condition, when + /// reported. + /// [JsonPropertyName("statistic")] public string Statistic { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonCondition() { } + /// + /// Initializes the surrogate from a strongly-typed condition + /// , mapping the condition message to + /// and optionally emitting the + /// category and instance id. + /// public JsonCondition(IObservation observation, bool categoryOutput = false, bool instanceIdOutput = false) { var condition = observation as ConditionObservation; @@ -48,6 +78,12 @@ public JsonCondition(IObservation observation, bool categoryOutput = false, bool } } + /// + /// Initializes the surrogate from a strongly-typed + /// , reading the condition message, + /// level, native code, native severity, and qualifier from the + /// observation's values. + /// public JsonCondition(IObservationOutput condition) { if (condition != null) @@ -84,6 +120,11 @@ public JsonCondition(IObservationOutput condition) } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing the category, level, + /// and qualifier enumerations. + /// public IConditionObservation ToCondition() { var condition = new ConditionObservation(); diff --git a/libraries/MTConnect.NET-JSON/Streams/JsonDeviceStream.cs b/libraries/MTConnect.NET-JSON/Streams/JsonDeviceStream.cs index ef684d97f..5936f0977 100644 --- a/libraries/MTConnect.NET-JSON/Streams/JsonDeviceStream.cs +++ b/libraries/MTConnect.NET-JSON/Streams/JsonDeviceStream.cs @@ -7,20 +7,43 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for a DeviceStream, the + /// observations reported for a single device. Mirrors the on-the-wire + /// shape so the JSON serializer can read and write it, then converts to + /// and from the strongly-typed model. + /// public class JsonDeviceStream { + /// + /// The name of the device the observations belong to. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The UUID of the device the observations belong to. + /// [JsonPropertyName("uuid")] public string Uuid { get; set; } + /// + /// The per-component observation streams of the device. + /// [JsonPropertyName("componentStream")] public List ComponentStreams { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonDeviceStream() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , including only component streams + /// that contain at least one observation. + /// public JsonDeviceStream(IDeviceStreamOutput deviceStream) { if (deviceStream != null) @@ -43,6 +66,10 @@ public JsonDeviceStream(IDeviceStreamOutput deviceStream) } + /// + /// Converts this surrogate to a strongly-typed + /// , converting each component stream. + /// public DeviceStream ToDeviceStream() { var deviceStream = new DeviceStream(); diff --git a/libraries/MTConnect.NET-JSON/Streams/JsonEntry.cs b/libraries/MTConnect.NET-JSON/Streams/JsonEntry.cs index d7c8f5b25..fec13707d 100644 --- a/libraries/MTConnect.NET-JSON/Streams/JsonEntry.cs +++ b/libraries/MTConnect.NET-JSON/Streams/JsonEntry.cs @@ -7,23 +7,46 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for a single entry of a DATA_SET or TABLE + /// observation. A data-set entry carries a scalar value, while a table + /// entry instead carries a collection of cells. + /// public class JsonEntry { + /// + /// The key identifying the entry within its data set or table. + /// [JsonPropertyName("key")] public string Key { get; set; } + /// + /// Whether the entry has been removed from the data set or table. + /// [JsonPropertyName("removed")] public bool Removed { get; set; } + /// + /// The entry value for a data-set entry; unused for table entries. + /// [JsonPropertyName("value")] public string Value { get; set; } + /// + /// The cells of a table entry; unused for data-set entries. + /// [JsonPropertyName("cells")] public IEnumerable Cells { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonEntry() { } + /// + /// Initializes the surrogate from a strongly-typed data-set entry. + /// public JsonEntry(IDataSetEntry entry) { if (entry != null) @@ -34,6 +57,10 @@ public JsonEntry(IDataSetEntry entry) } } + /// + /// Initializes the surrogate from a strongly-typed table entry, + /// converting each of its cells. + /// public JsonEntry(ITableEntry entry) { if (entry != null) diff --git a/libraries/MTConnect.NET-JSON/Streams/JsonEvent.cs b/libraries/MTConnect.NET-JSON/Streams/JsonEvent.cs index b968d85ca..67909d1fb 100644 --- a/libraries/MTConnect.NET-JSON/Streams/JsonEvent.cs +++ b/libraries/MTConnect.NET-JSON/Streams/JsonEvent.cs @@ -8,10 +8,25 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for an EVENT-category observation, + /// extending with event-specific projection + /// of data-set and table payloads. Converts to and from the strongly-typed + /// model. + /// public class JsonEvent : JsonObservation { + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonEvent() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , optionally emitting the category and + /// instance id, and projecting data-set or table payloads into the + /// property. + /// public JsonEvent(IObservation observation, bool categoryOutput = false, bool instanceIdOutput = false) { if (observation != null) @@ -47,6 +62,11 @@ public JsonEvent(IObservation observation, bool categoryOutput = false, bool ins } } + /// + /// Initializes the surrogate from a strongly-typed + /// , reconstructing the data-set or + /// table payload from the observation's raw values. + /// public JsonEvent(IObservationOutput observation) { if (observation != null) @@ -85,6 +105,11 @@ public JsonEvent(IObservationOutput observation) } + /// + /// Converts this surrogate to a strongly-typed + /// ; currently delegates to + /// for all representations. + /// public IEventObservation ToEvent() { if (Representation == DataItemRepresentation.DATA_SET.ToString()) @@ -103,6 +128,11 @@ public IEventObservation ToEvent() return ToEventValue(); } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing the category and reset + /// trigger enumerations. + /// public IEventValueObservation ToEventValue() { var e = new EventValueObservation(); diff --git a/libraries/MTConnect.NET-JSON/Streams/JsonObservation.cs b/libraries/MTConnect.NET-JSON/Streams/JsonObservation.cs index 629cb3a0a..b4ce9ca8a 100644 --- a/libraries/MTConnect.NET-JSON/Streams/JsonObservation.cs +++ b/libraries/MTConnect.NET-JSON/Streams/JsonObservation.cs @@ -8,60 +8,128 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for an MTConnect observation reported in a + /// component stream. Carries the shape common to samples, events, and + /// conditions across all representations (VALUE, DATA_SET, TABLE, and + /// TIME_SERIES), with the representation-specific payload exposed through + /// , , or . + /// public class JsonObservation { + /// + /// Reference to the id of the data item the observation + /// reports. + /// [JsonPropertyName("dataItemId")] public string DataItemId { get; set; } + /// + /// The name of the data item the observation reports. + /// [JsonPropertyName("name")] public string Name { get; set; } + /// + /// The category of the observation (SAMPLE, EVENT, or CONDITION). + /// [JsonPropertyName("category")] public string Category { get; set; } + /// + /// The representation of the observation (for example VALUE, DATA_SET, + /// TABLE, or TIME_SERIES). + /// [JsonPropertyName("representation")] public string Representation { get; set; } + /// + /// The MTConnect type of the data item the observation reports. + /// [JsonPropertyName("type")] public string Type { get; set; } + /// + /// The subtype further qualifying . + /// [JsonPropertyName("subType")] public string SubType { get; set; } + /// + /// Reference to the id of the composition the observation + /// originates from. + /// [JsonPropertyName("compositionId")] public string CompositionId { get; set; } + /// + /// The timestamp at which the observation was recorded. + /// [JsonPropertyName("timestamp")] public DateTime Timestamp { get; set; } + /// + /// The sequence number assigned to the observation by the agent. + /// [JsonPropertyName("sequence")] public ulong Sequence { get; set; } + /// + /// The instance identifier of the agent that produced the observation. + /// [JsonPropertyName("instanceId")] public ulong InstanceId { get; set; } + /// + /// Indicates whether a resettable observation's accumulated value was + /// reset on this observation. + /// [JsonPropertyName("resetTriggered")] public string ResetTriggered { get; set; } + /// + /// The reported value, for a VALUE representation. + /// [JsonPropertyName("result")] public string Result { get; set; } + /// + /// The reported samples, for a TIME_SERIES representation. + /// [JsonPropertyName("samples")] public IEnumerable Samples { get; set; } + /// + /// The reported entries, for a DATA_SET or TABLE representation. + /// [JsonPropertyName("entries")] public IEnumerable Entries { get; set; } + /// + /// The number of entries or samples reported, for a DATA_SET, TABLE, + /// or TIME_SERIES representation. + /// [JsonPropertyName("count")] public long? Count { get; set; } + /// + /// The native code of a condition observation as reported by the data + /// source. + /// [JsonPropertyName("nativeCode")] public string NativeCode { get; set; } + /// + /// The asset type, for an asset-changed or asset-removed observation. + /// [JsonPropertyName("assetType")] public string AssetType { get; set; } + /// + /// Creates the surrogate entries for a DATA_SET observation from its + /// strongly-typed entries, or null when there are none. + /// public static IEnumerable CreateEntries(IEnumerable entries) { if (!entries.IsNullOrEmpty()) @@ -77,6 +145,10 @@ public static IEnumerable CreateEntries(IEnumerable en return null; } + /// + /// Creates the surrogate entries for a TABLE observation from its + /// strongly-typed entries, or null when there are none. + /// public static IEnumerable CreateEntries(IEnumerable entries) { if (!entries.IsNullOrEmpty()) @@ -92,6 +164,10 @@ public static IEnumerable CreateEntries(IEnumerable entr return null; } + /// + /// Creates the string-formatted samples for a TIME_SERIES observation + /// from its strongly-typed sample values, or null when there are none. + /// public static IEnumerable CreateTimeSeriesSamples(IEnumerable samples) { if (!samples.IsNullOrEmpty()) diff --git a/libraries/MTConnect.NET-JSON/Streams/JsonSample.cs b/libraries/MTConnect.NET-JSON/Streams/JsonSample.cs index 356e54237..d8ab83645 100644 --- a/libraries/MTConnect.NET-JSON/Streams/JsonSample.cs +++ b/libraries/MTConnect.NET-JSON/Streams/JsonSample.cs @@ -9,20 +9,46 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for a SAMPLE-category observation, + /// extending with the sample-specific + /// properties. Converts to and from the strongly-typed + /// model. + /// public class JsonSample : JsonObservation { + /// + /// The rate, in samples per second, at which the values were sampled + /// for a TIME_SERIES representation. + /// [JsonPropertyName("sampleRate")] public double? SampleRate { get; set; } + /// + /// The statistical operation (for example AVERAGE or MAXIMUM) applied + /// to the reported value. + /// [JsonPropertyName("statistic")] public string Statistic { get; set; } + /// + /// The duration, in seconds, the statistic was computed over. + /// [JsonPropertyName("duration")] public double? Duration { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonSample() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , optionally emitting the category and + /// instance id, and projecting data-set, table, or time-series payloads + /// into the corresponding properties. + /// public JsonSample(IObservation observation, bool categoryOutput = false, bool instanceIdOutput = false) { if (observation != null) @@ -67,6 +93,11 @@ public JsonSample(IObservation observation, bool categoryOutput = false, bool in } } + /// + /// Initializes the surrogate from a strongly-typed + /// , reconstructing the data-set, + /// table, or time-series payload from the observation's raw values. + /// public JsonSample(IObservationOutput observation) { if (observation != null) @@ -116,6 +147,11 @@ public JsonSample(IObservationOutput observation) } } + /// + /// Converts this surrogate to a strongly-typed + /// ; currently delegates to + /// for all representations. + /// public ISampleObservation ToSample() { if (Representation == DataItemRepresentation.DATA_SET.ToString()) @@ -134,6 +170,11 @@ public ISampleObservation ToSample() return ToSampleValue(); } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing the category, reset + /// trigger, and statistic enumerations. + /// public ISampleValueObservation ToSampleValue() { var sample = new SampleValueObservation(); diff --git a/libraries/MTConnect.NET-JSON/Streams/JsonStreamsDocument.cs b/libraries/MTConnect.NET-JSON/Streams/JsonStreamsDocument.cs index 125118a87..458c94252 100644 --- a/libraries/MTConnect.NET-JSON/Streams/JsonStreamsDocument.cs +++ b/libraries/MTConnect.NET-JSON/Streams/JsonStreamsDocument.cs @@ -25,8 +25,16 @@ public class JsonStreamsDocument public List Streams { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonStreamsDocument() { } + /// + /// Initializes the surrogate from a strongly-typed + /// , converting the header + /// and each device stream. + /// public JsonStreamsDocument(IStreamsResponseOutputDocument streamsDocument) { if (streamsDocument != null) @@ -48,6 +56,11 @@ public JsonStreamsDocument(IStreamsResponseOutputDocument streamsDocument) } + /// + /// Converts this surrogate to a strongly-typed + /// , converting the header and + /// each device stream. + /// public IStreamsResponseDocument ToStreamsDocument() { var streamsDocument = new StreamsResponseDocument(); diff --git a/libraries/MTConnect.NET-JSON/Streams/JsonStreamsHeader.cs b/libraries/MTConnect.NET-JSON/Streams/JsonStreamsHeader.cs index c2ee22557..9958c0c2c 100644 --- a/libraries/MTConnect.NET-JSON/Streams/JsonStreamsHeader.cs +++ b/libraries/MTConnect.NET-JSON/Streams/JsonStreamsHeader.cs @@ -7,41 +7,86 @@ namespace MTConnect.Streams.Json { + /// + /// JSON serialization surrogate for the Header of an + /// MTConnectStreams document. Mirrors the on-the-wire shape so the JSON + /// serializer can read and write it, then converts to and from the + /// strongly-typed model. + /// public class JsonStreamsHeader { + /// + /// The instance identifier of the agent, which changes whenever the + /// agent's buffer is cleared. + /// [JsonPropertyName("instanceId")] public ulong InstanceId { get; set; } + /// + /// The MTConnect schema version of the document. + /// [JsonPropertyName("version")] public string Version { get; set; } + /// + /// The identifier of the agent that produced the document. + /// [JsonPropertyName("sender")] public string Sender { get; set; } + /// + /// The maximum number of observations the agent's buffer can hold. + /// [JsonPropertyName("bufferSize")] public ulong BufferSize { get; set; } + /// + /// The sequence number of the oldest observation still in the buffer. + /// [JsonPropertyName("firstSequence")] public ulong FirstSequence { get; set; } + /// + /// The sequence number of the newest observation in the buffer. + /// [JsonPropertyName("lastSequence")] public ulong LastSequence { get; set; } + /// + /// The sequence number the next observation will be assigned. + /// [JsonPropertyName("nextSequence")] public ulong NextSequence { get; set; } + /// + /// The timestamp of the most recent change to the device model. + /// [JsonPropertyName("deviceModelChangeTime")] public string DeviceModelChangeTime { get; set; } + /// + /// Whether the document was produced for testing rather than + /// production use. + /// [JsonPropertyName("testIndicator")] public bool TestIndicator { get; set; } + /// + /// The time the document was created. + /// [JsonPropertyName("creationTime")] public DateTime CreationTime { get; set; } + /// + /// Initializes an empty instance for JSON deserialization. + /// public JsonStreamsHeader() { } + /// + /// Initializes the surrogate from a strongly-typed + /// . + /// public JsonStreamsHeader(IMTConnectStreamsHeader header) { if (header != null) @@ -60,6 +105,10 @@ public JsonStreamsHeader(IMTConnectStreamsHeader header) } + /// + /// Converts this surrogate to a strongly-typed + /// . + /// public virtual IMTConnectStreamsHeader ToStreamsHeader() { var header = new MTConnectStreamsHeader(); diff --git a/libraries/MTConnect.NET-MQTT/Clients/MTConnectMqttClient.cs b/libraries/MTConnect.NET-MQTT/Clients/MTConnectMqttClient.cs index 0d2890cf3..391c8dca5 100644 --- a/libraries/MTConnect.NET-MQTT/Clients/MTConnectMqttClient.cs +++ b/libraries/MTConnect.NET-MQTT/Clients/MTConnectMqttClient.cs @@ -51,8 +51,15 @@ public class MTConnectMqttClient : IMTConnectClient, IMTConnectEntityClient, IDi private long _lastResponse; + /// Raw-message event handler delegate; raised for each MQTT publish received with the unprocessed topic and payload. + /// The MQTT topic the message was published on. + /// The raw payload bytes exactly as received from the broker. public delegate void MTConnectMqttEventHandler(string topic, byte[] payload); + /// Typed-entity event handler delegate; raised by the client after it has reassembled an MTConnect entity from the topic stream. + /// The MTConnect entity type (e.g. , , ) the handler receives. + /// The UUID of the device the entity belongs to. + /// The reassembled entity. public delegate void MTConnectMqttEventHandler(string deviceUuid, T item); /// @@ -203,6 +210,11 @@ public MTConnectMqttClient(IMTConnectMqttClientConfiguration configuration, stri } + /// + /// Starts the background MQTT worker that connects to the broker, subscribes to the + /// configured device topic tree, and reassembles incoming entities. Returns immediately; + /// is raised once the broker session is established. + /// public void Start() { _stop = new CancellationTokenSource(); @@ -212,6 +224,10 @@ public void Start() _ = Task.Run(Worker, _stop.Token); } + /// + /// Signals the worker to exit and drop the broker session. is + /// raised once the disconnect completes. + /// public void Stop() { ClientStopping?.Invoke(this, new EventArgs()); @@ -219,6 +235,7 @@ public void Stop() if (_stop != null) _stop.Cancel(); } + /// Disposes the underlying . should be called first; does not stop the worker on its own. public void Dispose() { if (_mqttClient != null) _mqttClient.Dispose(); diff --git a/libraries/MTConnect.NET-MQTT/Clients/MTConnectMqttExpandedClient.cs b/libraries/MTConnect.NET-MQTT/Clients/MTConnectMqttExpandedClient.cs index 3ed2958f4..d05f0301b 100644 --- a/libraries/MTConnect.NET-MQTT/Clients/MTConnectMqttExpandedClient.cs +++ b/libraries/MTConnect.NET-MQTT/Clients/MTConnectMqttExpandedClient.cs @@ -24,6 +24,15 @@ namespace MTConnect.Clients { + /// + /// MQTT client tuned for the cppagent's expanded topic layout where each MTConnect + /// entity (device, observation, condition, asset) is published to its own deep topic rather + /// than as a packaged response document. The client subscribes to a configurable set of topic + /// filters, parses each message into the matching strongly-typed entity, and raises the + /// appropriate , , or + /// event. Multi-agent broker topologies are supported through a + /// per-agent heartbeat timer. + /// public class MTConnectMqttExpandedClient : IMTConnectEntityClient, IDisposable { private const string _defaultTopic = "MTConnect/#"; @@ -72,6 +81,10 @@ public class MTConnectMqttExpandedClient : IMTConnectEntityClient, IDisposable private MTConnectMqttConnectionStatus _connectionStatus; + /// Typed-entity event handler delegate; raised by the expanded client after a topic payload has been parsed back into an entity. + /// The MTConnect entity type carried to the handler (device, observation, asset). + /// UUID of the device the entity belongs to (derived from the topic). + /// The reassembled entity. public delegate void MTConnectMqttEventHandler(string deviceUuid, T item); @@ -80,24 +93,34 @@ public class MTConnectMqttExpandedClient : IMTConnectEntityClient, IDisposable /// public int ReconnectionInterval { get; set; } + /// The MQTT broker hostname or IP address the client connects to. public string Server => _server; + /// The MQTT broker TCP port the client connects to. public int Port => _port; + /// The MQTT Quality of Service level the client requests for its subscriptions. public int Qos => _qos; + /// The reconnect interval in milliseconds; the client retries the connection at this cadence after a drop. public int Interval => _interval; + /// The list of MQTT topic filters the client subscribes to (defaults to MTConnect/#). public IEnumerable Topics => _topics; + /// Current broker session status. public MTConnectMqttConnectionStatus ConnectionStatus => _connectionStatus; + /// Raised after the broker session has been established and subscriptions are active. public event EventHandler Connected; + /// Raised when the broker session is dropped (by the client, the broker, or a transport failure). public event EventHandler Disconnected; + /// Raised whenever transitions; carries the new status. public event EventHandler ConnectionStatusChanged; + /// Raised when an exception is thrown while attempting to open or maintain the broker session. public event EventHandler ConnectionError; /// @@ -105,10 +128,13 @@ public class MTConnectMqttExpandedClient : IMTConnectEntityClient, IDisposable /// public event EventHandler InternalError; + /// Raised for each device document received on the MTConnect/Devices/{uuid}/Device topic, with the device parsed into an . public event EventHandler DeviceReceived; + /// Raised for each observation parsed from an MTConnect/Devices/{uuid}/Observations/... publish. public event EventHandler ObservationReceived; + /// Raised for each asset parsed from an MTConnect/Devices/{uuid}/Assets/{type}/{assetId} publish. public event EventHandler AssetReceived; /// @@ -132,6 +158,18 @@ public class MTConnectMqttExpandedClient : IMTConnectEntityClient, IDisposable public event EventHandler ClientStopped; + /// + /// Constructs the expanded client with broker-connection parameters supplied directly. + /// Wires the MQTT message dispatcher to either a single-device handler (when + /// is set) or the multi-device handler that triages by + /// topic. + /// + /// MQTT broker hostname or IP address. + /// MQTT broker TCP port; defaults to 1883. + /// Reconnect interval in milliseconds (also used for the broker keep-alive); 0 leaves it at the MQTTnet default. + /// When supplied, limits subscriptions to a single device's topic subtree. + /// Optional explicit topic filters; defaults to MTConnect/#. + /// MQTT QoS level (0/1/2) requested on subscribe; defaults to 1. public MTConnectMqttExpandedClient(string server, int port = 1883, int interval = 0, string deviceUuid = null, IEnumerable topics = null, int qos = 1) { ReconnectionInterval = 10000; @@ -156,6 +194,14 @@ public MTConnectMqttExpandedClient(string server, int port = 1883, int interval } } + /// + /// Constructs the expanded client from a configuration object. Pulls the broker + /// connection settings (server, port, credentials, QoS, TLS) and the optional device + /// scope from ; the topic filters are still supplied + /// separately and default to MTConnect/#. + /// + /// Broker connection settings; null leaves all fields at defaults. + /// Optional explicit topic filters; defaults to MTConnect/#. public MTConnectMqttExpandedClient(IMTConnectMqttClientConfiguration configuration, IEnumerable topics = null) { ReconnectionInterval = 10000; @@ -193,6 +239,7 @@ public MTConnectMqttExpandedClient(IMTConnectMqttClientConfiguration configurati } + /// Starts the background worker that connects to the broker, applies subscriptions, and dispatches incoming messages. Returns immediately. public void Start() { _stop = new CancellationTokenSource(); @@ -202,6 +249,7 @@ public void Start() _ = Task.Run(Worker, _stop.Token); } + /// Signals the worker to stop and disconnect from the broker. is raised once the session has closed. public void Stop() { ClientStopping?.Invoke(this, new EventArgs()); @@ -209,6 +257,7 @@ public void Stop() if (_stop != null) _stop.Cancel(); } + /// Disposes the underlying . Call first; this does not cancel the worker on its own. public void Dispose() { if (_mqttClient != null) _mqttClient.Dispose(); diff --git a/libraries/MTConnect.NET-MQTT/Configurations/IMTConnectMqttClientConfiguration.cs b/libraries/MTConnect.NET-MQTT/Configurations/IMTConnectMqttClientConfiguration.cs index adbc60e23..80e55924f 100644 --- a/libraries/MTConnect.NET-MQTT/Configurations/IMTConnectMqttClientConfiguration.cs +++ b/libraries/MTConnect.NET-MQTT/Configurations/IMTConnectMqttClientConfiguration.cs @@ -5,38 +5,60 @@ namespace MTConnect.Configurations { + /// + /// The settings an MTConnect MQTT client ( + /// and the expanded variant) needs to connect to an upstream MQTT broker that fronts an + /// MTConnect agent. Covers broker address, MQTT credentials, QoS, TLS/PEM options, retry + /// behaviour, and the topic-tree prefix the agent publishes under. + /// public interface IMTConnectMqttClientConfiguration { + /// The MQTT broker hostname or IP address the client connects to. string Server { get; set; } + /// The MQTT broker TCP port (typically 1883 plain, 8883 TLS). int Port { get; set; } + /// Reconnect/health-check interval in milliseconds; the client retries the connection at this cadence after a drop. int Interval { get; set; } + /// UUID of the MTConnect device to subscribe to; null or empty subscribes to all devices under . string DeviceUuid { get; set; } + /// MQTT username for credential-based brokers; null or empty connects anonymously. string Username { get; set; } + /// MQTT password paired with . string Password { get; set; } + /// The MQTT client identifier; brokers require this to be unique per concurrent connection. string ClientId { get; set; } + /// The MQTT Quality of Service level (0, 1, or 2) requested for subscriptions and publishes. int Qos { get; set; } + /// Strongly-typed TLS settings (certificate path, password, client certificate); overrides the loose // fields when set. TlsConfiguration Tls { get; set; } + /// Path to a PEM-encoded certificate authority bundle used to verify the broker certificate when is true. string CertificateAuthority { get; set; } + /// Path to a PEM-encoded client certificate presented to the broker. string PemCertificate { get; set; } + /// Path to the PEM-encoded private key for . string PemPrivateKey { get; set; } + /// When true, the connection is upgraded to MQTT-over-TLS; certificate material is taken from or the loose PEM fields. bool UseTls { get; set; } + /// When true, broker certificates that fail validation (unknown CA, hostname mismatch) are still accepted; intended for self-signed development brokers. bool AllowUntrustedCertificates { get; set; } + /// Initial back-off delay in milliseconds between automatic reconnect attempts after a transport failure. int RetryInterval { get; set; } + /// The MQTT topic prefix the client expects (e.g. MTConnect); subscriptions are rooted at this prefix. string TopicPrefix { get; set; } } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-MQTT/Configurations/IMTConnectMqttDocumentServerConfiguration.cs b/libraries/MTConnect.NET-MQTT/Configurations/IMTConnectMqttDocumentServerConfiguration.cs index 548ccf91d..291b40bc7 100644 --- a/libraries/MTConnect.NET-MQTT/Configurations/IMTConnectMqttDocumentServerConfiguration.cs +++ b/libraries/MTConnect.NET-MQTT/Configurations/IMTConnectMqttDocumentServerConfiguration.cs @@ -1,8 +1,14 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Configurations { + /// + /// Settings consumed by that publish + /// the full MTConnect response documents (Probe, Current, Sample, Asset) over MQTT rather + /// than individual observation topics. Configures only the publish cadence; the topic layout + /// is defined by the concrete configuration class. + /// public interface IMTConnectMqttDocumentServerConfiguration { /// diff --git a/libraries/MTConnect.NET-MQTT/Configurations/IMTConnectMqttEntityServerConfiguration.cs b/libraries/MTConnect.NET-MQTT/Configurations/IMTConnectMqttEntityServerConfiguration.cs index c49229d53..5f93c7335 100644 --- a/libraries/MTConnect.NET-MQTT/Configurations/IMTConnectMqttEntityServerConfiguration.cs +++ b/libraries/MTConnect.NET-MQTT/Configurations/IMTConnectMqttEntityServerConfiguration.cs @@ -1,23 +1,23 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Configurations { + /// + /// Settings consumed by that publish + /// individual MTConnect entities (devices, observations, assets) under per-entity topics + /// rather than as packaged response documents. Configures the topic prefix, the serialisation + /// format, and the MQTT QoS for all entity publishes. + /// public interface IMTConnectMqttEntityServerConfiguration { - /// - /// - /// + /// The MQTT topic prefix the server publishes under (e.g. MTConnect). string TopicPrefix { get; } - /// - /// - /// + /// The serialisation format used for each entity payload (e.g. JSON, XML). string DocumentFormat { get; } - /// - /// - /// + /// The MQTT Quality of Service level (0, 1, or 2) applied to every publish. int Qos { get; set; } } } diff --git a/libraries/MTConnect.NET-MQTT/Configurations/MTConnectMqttClientConfiguration.cs b/libraries/MTConnect.NET-MQTT/Configurations/MTConnectMqttClientConfiguration.cs index 1381e1c20..ae4167e6f 100644 --- a/libraries/MTConnect.NET-MQTT/Configurations/MTConnectMqttClientConfiguration.cs +++ b/libraries/MTConnect.NET-MQTT/Configurations/MTConnectMqttClientConfiguration.cs @@ -6,57 +6,84 @@ namespace MTConnect.Configurations { + /// + /// Default implementation deserialised from + /// the application JSON/YAML configuration. See the interface for the semantics of each + /// property; this class only adds the serialiser bindings and the conventional defaults + /// applied by the parameterless constructor. + /// public class MTConnectMqttClientConfiguration : IMTConnectMqttClientConfiguration { + /// [JsonPropertyName("server")] public string Server { get; set; } + /// [JsonPropertyName("port")] public int Port { get; set; } + /// [JsonPropertyName("interval")] public int Interval { get; set; } + /// [JsonPropertyName("deviceUuid")] public string DeviceUuid { get; set; } + /// [JsonPropertyName("username")] public string Username { get; set; } + /// [JsonPropertyName("password")] public string Password { get; set; } + /// [JsonPropertyName("clientId")] public string ClientId { get; set; } + /// [JsonPropertyName("qos")] public int Qos { get; set; } + /// [JsonPropertyName("tls")] public TlsConfiguration Tls { get; set; } + /// [JsonPropertyName("certificateAuthority")] public string CertificateAuthority { get; set; } + /// [JsonPropertyName("pemCertificate")] public string PemCertificate { get; set; } + /// [JsonPropertyName("pemPrivateKey")] public string PemPrivateKey { get; set; } + /// [JsonPropertyName("allowUntrustedCertificates")] public bool AllowUntrustedCertificates { get; set; } + /// [JsonPropertyName("useTls")] public bool UseTls { get; set; } + /// [JsonPropertyName("retryInterval")] public int RetryInterval { get; set; } + /// [JsonPropertyName("topicPrefix")] public string TopicPrefix { get; set; } + /// + /// Initialises the configuration with the MQTT-defaults expected by an MTConnect MQTT + /// client: localhost broker on port 1883, QoS 1, five-second retry back-off, and + /// the MTConnect topic prefix. + /// public MTConnectMqttClientConfiguration() { Server = "localhost"; @@ -66,4 +93,4 @@ public MTConnectMqttClientConfiguration() TopicPrefix = "MTConnect"; } } -} \ No newline at end of file +} diff --git a/libraries/MTConnect.NET-MQTT/Configurations/MTConnectMqttDocumentServerConfiguration.cs b/libraries/MTConnect.NET-MQTT/Configurations/MTConnectMqttDocumentServerConfiguration.cs index ce466391b..57bef798d 100644 --- a/libraries/MTConnect.NET-MQTT/Configurations/MTConnectMqttDocumentServerConfiguration.cs +++ b/libraries/MTConnect.NET-MQTT/Configurations/MTConnectMqttDocumentServerConfiguration.cs @@ -1,26 +1,43 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Configurations { + /// + /// Default implementation. Extends + /// the interface contract with the topic-tree layout the server uses: a common prefix and + /// per-document-type leaf segments for Probe, Current, Sample, and Asset publishes. + /// public class MTConnectMqttDocumentServerConfiguration : IMTConnectMqttDocumentServerConfiguration { + /// public int CurrentInterval { get; set; } + /// public int SampleInterval { get; set; } + /// The MQTT topic prefix the server publishes under (e.g. MTConnect). public string TopicPrefix { get; set; } + /// The leaf segment used for probe response publishes; the full topic is {TopicPrefix}/{ProbeTopic}/{deviceUuid}. public string ProbeTopic { get; set; } + /// The leaf segment used for current response publishes; the full topic is {TopicPrefix}/{CurrentTopic}/{deviceUuid}. public string CurrentTopic { get; set; } + /// The leaf segment used for sample response publishes; the full topic is {TopicPrefix}/{SampleTopic}/{deviceUuid}. public string SampleTopic { get; set; } + /// The leaf segment used for asset publishes; the full topic is {TopicPrefix}/{AssetTopic}/{deviceUuid}/{assetId}. public string AssetTopic { get; set; } + /// + /// Initialises the configuration with the conventional defaults: a 5-second Current + /// interval, a 500 ms Sample interval, the MTConnect topic prefix, and the + /// Probe/Current/Sample/Asset leaf segments. + /// public MTConnectMqttDocumentServerConfiguration() { CurrentInterval = 5000; diff --git a/libraries/MTConnect.NET-MQTT/Configurations/MTConnectMqttEntityServerConfiguration.cs b/libraries/MTConnect.NET-MQTT/Configurations/MTConnectMqttEntityServerConfiguration.cs index 379206678..a2d347647 100644 --- a/libraries/MTConnect.NET-MQTT/Configurations/MTConnectMqttEntityServerConfiguration.cs +++ b/libraries/MTConnect.NET-MQTT/Configurations/MTConnectMqttEntityServerConfiguration.cs @@ -1,17 +1,26 @@ -// Copyright (c) 2024 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2024 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Configurations { + /// + /// Default implementation used by the + /// MQTT entity server. The parameterless constructor applies the defaults expected by the + /// reference broker: MTConnect topic prefix, JSON entity serialisation, and QoS 0. + /// public class MTConnectMqttEntityServerConfiguration : IMTConnectMqttEntityServerConfiguration { + /// public string TopicPrefix { get; set; } + /// public string DocumentFormat { get; set; } + /// public int Qos { get; set; } + /// Initialises the configuration with the conventional defaults: MTConnect topic prefix, JSON entity format, and MQTT QoS 0. public MTConnectMqttEntityServerConfiguration() { TopicPrefix = "MTConnect"; diff --git a/libraries/MTConnect.NET-MQTT/Input/MTConnectMqttInputDevices.cs b/libraries/MTConnect.NET-MQTT/Input/MTConnectMqttInputDevices.cs index 462e29206..b973ef580 100644 --- a/libraries/MTConnect.NET-MQTT/Input/MTConnectMqttInputDevices.cs +++ b/libraries/MTConnect.NET-MQTT/Input/MTConnectMqttInputDevices.cs @@ -1,17 +1,27 @@ -using MTConnect.Devices; +using MTConnect.Devices; using System.Collections.Generic; using System.Text.Json.Serialization; namespace MTConnect.Mqtt { + /// + /// Payload published over MQTT to announce a set of devices to a downstream MTConnect agent. + /// The map keys are device UUIDs and the values are the serialised device documents in the + /// chosen MTConnect format; consumers replay this against their device cache so an agent can + /// reconstruct the upstream device model without polling. + /// public class MTConnectMqttInputDevices { + /// Map of device UUID to the serialised MTConnect device document for that UUID. [JsonPropertyName("devices")] public Dictionary Devices { get; set; } + /// Creates an empty container for serialiser-driven deserialisation. public MTConnectMqttInputDevices() { } + /// Reserved single-device constructor; currently kept for API parity with the multi-device overload pending implementation in upstream releases. + /// The device whose UUID and document would be encoded. public MTConnectMqttInputDevices(IDevice device) { if (device != null && !string.IsNullOrEmpty(device.Uuid)) @@ -20,6 +30,8 @@ public MTConnectMqttInputDevices(IDevice device) } } + /// Reserved many-device constructor; currently kept for API parity with the single-device overload pending implementation in upstream releases. + /// The devices whose UUIDs and documents would be encoded. public MTConnectMqttInputDevices(IEnumerable devices) { if (!devices.IsNullOrEmpty()) diff --git a/libraries/MTConnect.NET-MQTT/Input/MTConnectMqttInputObservation.cs b/libraries/MTConnect.NET-MQTT/Input/MTConnectMqttInputObservation.cs index ca3649f25..39d2ea47d 100644 --- a/libraries/MTConnect.NET-MQTT/Input/MTConnectMqttInputObservation.cs +++ b/libraries/MTConnect.NET-MQTT/Input/MTConnectMqttInputObservation.cs @@ -1,19 +1,32 @@ -using System.Collections.Generic; +using System.Collections.Generic; using System.Text.Json.Serialization; namespace MTConnect.Mqtt { + /// + /// JSON payload for a single MTConnect observation published to or consumed from MQTT. The + /// property holds the DataItem key (id or name) and + /// is the value-key/value-string map that the agent feeds straight into an + /// . The shape is intentionally minimal so the + /// timestamp can be supplied externally by the containing . + /// public class MTConnectMqttInputObservation { + /// The DataItem key (id or name) the observation applies to. [JsonPropertyName("dataItem")] public string DataItem { get; set; } + /// The value-key/value map (e.g. Result, NativeCode) carried by the observation. [JsonPropertyName("values")] public Dictionary Values { get; set; } + /// Creates an empty container for serialiser-driven deserialisation. public MTConnectMqttInputObservation() { } + /// Constructs a populated observation payload with a DataItem key and its value map. + /// The DataItem key (id or name) the observation applies to. + /// The value-key/value map carried by the observation. public MTConnectMqttInputObservation(string dataItemKey, Dictionary values) { DataItem = dataItemKey; diff --git a/libraries/MTConnect.NET-MQTT/Input/MTConnectMqttInputObservations.cs b/libraries/MTConnect.NET-MQTT/Input/MTConnectMqttInputObservations.cs index ff0fc29e9..951f496e3 100644 --- a/libraries/MTConnect.NET-MQTT/Input/MTConnectMqttInputObservations.cs +++ b/libraries/MTConnect.NET-MQTT/Input/MTConnectMqttInputObservations.cs @@ -8,15 +8,28 @@ namespace MTConnect.Mqtt { + /// + /// MQTT-side container that groups a batch of + /// values under a single timestamp. Downstream agents call + /// to flatten the batch into the internal form and feed it + /// to the observation buffer. + /// public class MTConnectMqttInputObservations { + /// Wall-clock timestamp applied to every observation in on conversion. [JsonPropertyName("timestamp")] public DateTime Timestamp { get; set; } + /// The observations carried by this batch; each is converted to an with applied. [JsonPropertyName("observations")] public List Observations { get; set; } = new List(); + /// + /// Flattens the batch into a list of instances, one per + /// member of , with applied (in Unix + /// time) to each. Observations missing a DataItem key or values are silently skipped. + /// public IEnumerable ToObservationInputs() { var observations = new List(); diff --git a/libraries/MTConnect.NET-MQTT/MTConnect.NET-MQTT.csproj b/libraries/MTConnect.NET-MQTT/MTConnect.NET-MQTT.csproj index e58afec56..b38908076 100644 --- a/libraries/MTConnect.NET-MQTT/MTConnect.NET-MQTT.csproj +++ b/libraries/MTConnect.NET-MQTT/MTConnect.NET-MQTT.csproj @@ -52,6 +52,19 @@ + + + + + + + + diff --git a/libraries/MTConnect.NET-MQTT/MTConnectMqttBroker.cs b/libraries/MTConnect.NET-MQTT/MTConnectMqttBroker.cs index 0b2fc6a97..6f50ec427 100644 --- a/libraries/MTConnect.NET-MQTT/MTConnectMqttBroker.cs +++ b/libraries/MTConnect.NET-MQTT/MTConnectMqttBroker.cs @@ -16,6 +16,14 @@ namespace MTConnect.Mqtt { + /// + /// Bridges an in-process to an MQTTnet broker, publishing every + /// device addition, observation, and asset received by the agent as MQTT messages under the + /// configured topic prefix. Hosts a heartbeat timer that emits the agent's + /// HeartbeatTimestamp topic on a fixed interval and, optionally, per-interval + /// observation buckets so consumers can subscribe to coarse-grained snapshots without + /// processing every individual publish. + /// public class MTConnectMqttBroker : IHostedService { private const int _retryInterval = 5000; @@ -34,25 +42,42 @@ public class MTConnectMqttBroker : IHostedService private readonly System.Timers.Timer _heartbeatTimer = new System.Timers.Timer(); + /// Heartbeat interval in milliseconds; the broker emits the agent's HeartbeatTimestamp publish at this cadence. public int HeartbeatInterval => _heartbeatInterval; + /// Topic layout (flat or hierarchy) used for observation publishes; defaults to . public MTConnectMqttFormat Format { get; set; } + /// Optional topic prefix used in place of the default MTConnect; when null the standard prefix is applied by . public string TopicPrefix { get; set; } + /// When true, retained publishes are used so newly connecting clients see the latest agent/device/observation state immediately. public bool RetainMessages { get; set; } + /// Raised by the underlying when a downstream MQTT client connects. public event EventHandler ClientConnected; + /// Raised by the underlying when a downstream MQTT client disconnects. public event EventHandler ClientDisconnected; + /// Raised after each successful publish; the argument is the topic name. public event EventHandler MessageSent; + /// Raised when the broker's connection to its underlying transport fails. public event EventHandler ConnectionError; + /// Raised when a publish fails after the connection has been established. public event EventHandler PublishError; + /// + /// Subscribes to the agent's add events and prepares the broker for hosting. The broker + /// is not started until is called by the .NET hosting layer. + /// + /// The agent to mirror over MQTT; its add events are observed. + /// The MQTTnet server instance the broker publishes through; ownership stays with the caller. + /// Optional list of interval-bucket lengths in milliseconds; if supplied, the broker emits batched observation topics for each interval. + /// Heartbeat publish cadence in milliseconds; defaults to one second. public MTConnectMqttBroker(IMTConnectAgent mtconnectAgent, MqttServer mqttServer, IEnumerable observationIntervals = null, int heartbeatInterval = 1000) { _mtconnectAgent = mtconnectAgent; @@ -86,6 +111,11 @@ public MTConnectMqttBroker(IMTConnectAgent mtconnectAgent, MqttServer mqttServer } + /// + /// entry point. Spawns the broker worker on the thread pool, + /// starts the heartbeat timer, and starts one timer per configured observation interval + /// that flushes buffered observations under the interval-bucketed topic on each tick. + /// public async Task StartAsync(CancellationToken cancellationToken) { _stop = new CancellationTokenSource(); @@ -115,6 +145,11 @@ public async Task StartAsync(CancellationToken cancellationToken) } } + /// + /// shutdown hook. Cancels the worker, stops the heartbeat + /// timer, disposes the interval-bucket timers, and awaits a graceful shutdown of the + /// underlying . + /// public async Task StopAsync(CancellationToken cancellationToken) { if (_stop != null) _stop.Cancel(); diff --git a/libraries/MTConnect.NET-MQTT/MTConnectMqttConnectionStatus.cs b/libraries/MTConnect.NET-MQTT/MTConnectMqttConnectionStatus.cs index f7489c5ef..c6c6d1a3f 100644 --- a/libraries/MTConnect.NET-MQTT/MTConnectMqttConnectionStatus.cs +++ b/libraries/MTConnect.NET-MQTT/MTConnectMqttConnectionStatus.cs @@ -1,11 +1,20 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect { + /// + /// Tracks whether an MTConnect MQTT client or broker currently has an active session with its + /// remote peer. Used by status events on + /// and so consumers can react to connect + /// and disconnect transitions without inspecting the underlying MQTTnet client. + /// public enum MTConnectMqttConnectionStatus { + /// No MQTT session is currently established; pending publishes are queued or dropped depending on configuration. Disconnected, + + /// An MQTT session has been negotiated; subscriptions are active and publishes flow through immediately. Connected } } diff --git a/libraries/MTConnect.NET-MQTT/MTConnectMqttDocumentServer.cs b/libraries/MTConnect.NET-MQTT/MTConnectMqttDocumentServer.cs index 15174f0a4..2914fc06a 100644 --- a/libraries/MTConnect.NET-MQTT/MTConnectMqttDocumentServer.cs +++ b/libraries/MTConnect.NET-MQTT/MTConnectMqttDocumentServer.cs @@ -11,11 +11,27 @@ namespace MTConnect { + /// + /// Publishes complete MTConnect response documents (Probe, Current, Sample, Asset) over MQTT + /// on behalf of an in-process agent. The server emits a Probe per device at start, then runs + /// a worker loop that publishes Current documents on the configured cadence and incremental + /// Sample documents based on the last observation sequence. Asset documents are published + /// whenever the agent raises an asset-added event. Consumers subscribe to the topic tree + /// described by and the document-type + /// constants on this class. + /// public class MTConnectMqttDocumentServer { + /// Default leaf segment for Probe response publishes; combined with the configuration's topic prefix. public const string ProbeTopic = "Probe"; + + /// Default leaf segment for Current response publishes; combined with the configuration's topic prefix. public const string CurrentTopic = "Current"; + + /// Default leaf segment for Sample response publishes; combined with the configuration's topic prefix. public const string SampleTopic = "Sample"; + + /// Default leaf segment for Asset response publishes; combined with the configuration's topic prefix. public const string AssetTopic = "Asset"; private readonly IMTConnectAgentBroker _mtconnectAgent; @@ -25,15 +41,27 @@ public class MTConnectMqttDocumentServer private bool _sampleStarted = false; + /// Raised whenever the server prepares a Probe document for a device; subscribers serialise and publish the document to the broker. public event MTConnectMqttResponseHandler ProbeReceived; + /// Raised on each tick of the current-publish loop, once per device with the most recent MTConnectStreams snapshot. public event MTConnectMqttResponseHandler CurrentReceived; + /// Raised whenever new observations beyond the last published sequence become available; carries the incremental MTConnectStreams document. public event MTConnectMqttResponseHandler SampleReceived; + /// Raised whenever the agent reports a new or updated asset; carries the asset response document for downstream publishing. public event MTConnectMqttResponseHandler AssetReceived; + /// + /// Hooks into the agent's device/asset add events and prepares the worker state. If + /// is null a fresh + /// with its built-in defaults is + /// used. + /// + /// The agent broker to read response documents from. + /// Publish cadence and topic-layout settings. public MTConnectMqttDocumentServer(IMTConnectAgentBroker mtconnectAgent, IMTConnectMqttDocumentServerConfiguration configuration) { _mtconnectAgent = mtconnectAgent; @@ -45,6 +73,11 @@ public MTConnectMqttDocumentServer(IMTConnectAgentBroker mtconnectAgent, IMTConn } + /// + /// Emits one initial Probe document per device by raising , + /// then launches the background worker that publishes Current documents on the + /// configured . + /// public void Start() { _stop = new CancellationTokenSource(); @@ -65,6 +98,7 @@ public void Start() _ = Task.Run(CurrentWorker, _stop.Token); } + /// Cancels the worker tasks. The agent's event subscriptions remain wired; call this before disposing the server. public void Stop() { if (_stop != null) _stop.Cancel(); diff --git a/libraries/MTConnect.NET-MQTT/MTConnectMqttEntityServer.cs b/libraries/MTConnect.NET-MQTT/MTConnectMqttEntityServer.cs index ac5a5929e..298a92696 100644 --- a/libraries/MTConnect.NET-MQTT/MTConnectMqttEntityServer.cs +++ b/libraries/MTConnect.NET-MQTT/MTConnectMqttEntityServer.cs @@ -17,18 +17,37 @@ namespace MTConnect.Clients { + /// + /// Publishes individual MTConnect entities (devices, observations, assets) over MQTT under + /// their dedicated topics rather than as packaged response documents. Each Publish* + /// method comes in two flavours: an overload for outbound publishes + /// to an external broker, and an overload that injects the message + /// directly into an embedded broker via . + /// public class MTConnectMqttEntityServer { private readonly IMTConnectMqttEntityServerConfiguration _configuration; + /// The MQTT topic prefix used for every publish (sourced from the configuration). public string TopicPrefix => _configuration.TopicPrefix; + /// Raised after each successful publish with the topic of the message that was sent. public event EventHandler MessageSent; + + /// Raised when a publish completes but the broker reports a non-success result; the argument is the topic that failed. public event EventHandler SendError; + + /// Raised when an publish throws (transport failure, malformed payload). public event EventHandler ClientError; + + /// Raised when an inject throws (the embedded broker rejected the message). public event EventHandler ServerError; + /// Constructs an entity server with a fresh configuration populated from the supplied loose arguments. + /// Topic prefix to use; null or empty keeps the default. + /// Entity serialisation format; defaults to JSON. + /// MQTT Quality of Service level applied to every publish. public MTConnectMqttEntityServer(string topicPrefix = null, string documentFormat = DocumentFormat.JSON, int qos = 0) { var configuration = new MTConnectMqttEntityServerConfiguration(); @@ -38,6 +57,8 @@ public MTConnectMqttEntityServer(string topicPrefix = null, string documentForma _configuration = configuration; } + /// Constructs an entity server from an existing configuration object; a null argument falls back to a freshly-initialised default configuration. + /// The configuration providing topic prefix, document format, and QoS. public MTConnectMqttEntityServer(IMTConnectMqttEntityServerConfiguration configuration) { _configuration = configuration; @@ -45,6 +66,12 @@ public MTConnectMqttEntityServer(IMTConnectMqttEntityServerConfiguration configu } + /// + /// Publishes a single device document to {TopicPrefix}/Devices/{uuid}/Device via + /// the supplied . The message is retained so newly + /// connecting clients see the latest device model. Raises , + /// , or depending on the outcome. + /// public async Task PublishDevice(IMqttClient mqttClient, IDevice device) { if (mqttClient != null && mqttClient.IsConnected && device != null) @@ -69,6 +96,11 @@ public async Task PublishDevice(IMqttClient mqttClient, IDevice device) } } + /// + /// Injects a single device document into an embedded using + /// , avoiding the network round-trip when the + /// publisher hosts the broker itself. Raises on failure. + /// public async Task PublishDevice(MqttServer mqttServer, IDevice device) { if (mqttServer != null && device != null) @@ -111,6 +143,12 @@ private MqttApplicationMessage CreateMessage(IDevice device) } + /// + /// Publishes a single observation to + /// {TopicPrefix}/Devices/{deviceUuid}/Observations/{dataItemId} via the supplied + /// . Returns the broker's publish result so callers can + /// inspect acknowledgement state when QoS > 0 is in effect. + /// public async Task PublishObservation(IMqttClient mqttClient, IObservation observation) { if (mqttClient != null && mqttClient.IsConnected && observation != null) @@ -137,6 +175,11 @@ public async Task PublishObservation(IMqttClient mqttCl return null; } + /// + /// Publishes a batch of observations that share the same DataItem (and therefore the same + /// topic) via the supplied . The topic is derived from the + /// first observation; remaining observations contribute to the serialised payload only. + /// public async Task PublishObservations(IMqttClient mqttClient, IEnumerable observations) { if (mqttClient != null && mqttClient.IsConnected && !observations.IsNullOrEmpty()) @@ -163,6 +206,7 @@ public async Task PublishObservations(IMqttClient mqttC return null; } + /// Injects a single observation into an embedded without a network round-trip. Raises on failure. public async Task PublishObservation(MqttServer mqttServer, IObservation observation) { if (mqttServer != null && observation != null) @@ -181,6 +225,7 @@ public async Task PublishObservation(MqttServer mqttServer, IObservation observa } } + /// Injects a batch of observations (sharing the same DataItem topic) into an embedded . Raises on failure. public async Task PublishObservations(MqttServer mqttServer, IEnumerable observations) { if (mqttServer != null && !observations.IsNullOrEmpty()) @@ -263,6 +308,11 @@ private MqttApplicationMessage CreateMessage(IEnumerable observati } + /// + /// Publishes a single asset to {TopicPrefix}/Devices/{deviceUuid}/Assets/{assetId} + /// via the supplied . The message is retained so consumers + /// joining after the publish still see the asset. + /// public async Task PublishAsset(IMqttClient mqttClient, IAsset asset) { if (mqttClient != null && mqttClient.IsConnected && asset != null) @@ -287,6 +337,7 @@ public async Task PublishAsset(IMqttClient mqttClient, IAsset asset) } } + /// Injects a single asset into an embedded without a network round-trip. Raises on failure. public async Task PublishAsset(MqttServer mqttServer, IAsset asset) { if (mqttServer != null && asset != null) diff --git a/libraries/MTConnect.NET-MQTT/MTConnectMqttFormat.cs b/libraries/MTConnect.NET-MQTT/MTConnectMqttFormat.cs index 75ab4d0be..154cca4cb 100644 --- a/libraries/MTConnect.NET-MQTT/MTConnectMqttFormat.cs +++ b/libraries/MTConnect.NET-MQTT/MTConnectMqttFormat.cs @@ -1,11 +1,29 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect { + /// + /// Selects how observation topics are laid out under each device when the MTConnect MQTT + /// broker publishes data items. The two modes are wire-compatible with each other but + /// represent very different consumer subscription patterns. + /// public enum MTConnectMqttFormat { + /// + /// Flat layout: every observation is published at + /// MTConnect/Devices/{deviceUuid}/Observations/{dataItemId}. Subscribers see all + /// data items under one branch and must inspect each payload to learn the type. + /// Flat, + + /// + /// Hierarchy layout: each observation is published under a path that mirrors the device + /// model (container type, container id, category, type, optional sub-type). Subscribers + /// can wildcard on a single type (for example + /// MTConnect/Devices/+/Observations/.../Samples/Temperature/#) without reading + /// every payload. + /// Hierarchy } } diff --git a/libraries/MTConnect.NET-MQTT/MTConnectMqttMessage.cs b/libraries/MTConnect.NET-MQTT/MTConnectMqttMessage.cs index f5f631e67..feb833e98 100644 --- a/libraries/MTConnect.NET-MQTT/MTConnectMqttMessage.cs +++ b/libraries/MTConnect.NET-MQTT/MTConnectMqttMessage.cs @@ -13,6 +13,14 @@ namespace MTConnect.Mqtt { + /// + /// Factory helpers that translate MTConnect entities (agent metadata, devices, assets, and + /// observations) into the matching objects with the + /// canonical topic layout used by the MTConnect MQTT broker. The methods cover the + /// MTConnect/Agents/{uuid}/Information message, the heartbeat timestamp, device and + /// asset publishes, and individual observation publishes in either flat or hierarchy + /// topic format. + /// public static class MTConnectMqttMessage { private static MqttApplicationMessage CreateMessage(string topic, string payload, bool retain = false) @@ -45,6 +53,17 @@ private static MqttApplicationMessage CreateMessage(string topic, Stream payload return null; } + /// + /// Builds the MTConnect/Agents/{uuid}/Information MQTT message that announces the + /// agent's identity (UUID, instance id, version, sender), its + /// DeviceModelChangeTime, the heartbeat interval, the list of observation + /// intervals it publishes on, and the UUIDs of the devices it owns. Returns a single + /// message wrapped in a list so the caller can extend it without changing the signature. + /// + /// The agent to describe; null returns null. + /// The interval-bucket lengths (ms) on which the agent publishes batched observation topics. + /// Heartbeat interval in milliseconds; consumers use this to time out the agent if no HeartbeatTimestamp updates arrive. + /// If true, the message is published with the MQTT retain flag so newly connecting clients get the current information immediately. public static IEnumerable Create(IMTConnectAgent agent, IEnumerable observationIntervals, int heartbeat, bool retain = false) { if (agent != null) @@ -78,7 +97,7 @@ public static IEnumerable Create(IMTConnectAgent agent, } catch { } - + //// UUID //var topic = $"MTConnect/Agents/{agent.Uuid}/UUID"; @@ -146,6 +165,13 @@ public static IEnumerable Create(IMTConnectAgent agent, // return null; //} + /// + /// Builds the heartbeat publish, an MTConnect/Agents/{uuid}/HeartbeatTimestamp + /// message carrying the current Unix-epoch timestamp in milliseconds. The agent is + /// expected to emit this on every heartbeat tick so consumers can detect a stalled agent. + /// + /// The agent owning the heartbeat; null returns null. + /// The current timestamp in Windows ticks (100 ns units); converted to milliseconds for the payload. public static IEnumerable CreateHeartbeat(IMTConnectAgent agent, long timestamp) { if (agent != null) @@ -165,6 +191,16 @@ public static IEnumerable CreateHeartbeat(IMTConnectAgen return null; } + /// + /// Builds the device-publish messages: an MTConnect/Devices/{deviceUuid}/AgentUuid + /// retained pointer back to the owning agent, and an + /// MTConnect/Devices/{deviceUuid}/Device message containing the serialised device + /// model in . + /// + /// The device to publish; null or empty returns null. + /// The UUID of the agent the device belongs to; published as the back-pointer payload. + /// The document format used to serialise the device model (defaults to XML). + /// If true, the device message itself is published with the MQTT retain flag (the agent UUID pointer is always retained). public static IEnumerable Create(IDevice device, string agentUuid, string documentFormatterId = DocumentFormat.XML, bool retain = false) { if (device != null && !string.IsNullOrEmpty(documentFormatterId)) @@ -201,6 +237,15 @@ public static IEnumerable Create(IDevice device, string return null; } + /// + /// Builds the two asset publishes for an MTConnect asset: one at + /// MTConnect/Assets/{type}/{assetId} (asset-type-scoped) and one at + /// MTConnect/Devices/{deviceUuid}/Assets/{type}/{assetId} (device-scoped). Both + /// carry the same serialised payload in the requested . + /// + /// The asset to publish; null returns null. + /// The document format used to serialise the asset (defaults to XML). + /// If true, both messages are published with the MQTT retain flag. public static IEnumerable Create(IAsset asset, string documentFormatterId = DocumentFormat.XML, bool retain = false) { if (asset != null) @@ -220,6 +265,18 @@ public static IEnumerable Create(IAsset asset, string do return null; } + /// + /// Builds the publish for a single MTConnect observation. The topic is computed by + /// from the data item type, sub-type, category, and + /// container; the payload is the observation serialised with the entity formatter, + /// always including category and instance-id options because MQTT consumers cannot + /// otherwise recover those properties from the topic alone. + /// + /// The observation; null returns null. The observation must have a device UUID, a data item with a container, and at least one value. + /// Flat or hierarchy topic layout. + /// The document format used to serialise the observation (defaults to XML). + /// If true, the publish is retained (used for the last-known-value channel). + /// When non-zero, identifies the observation-interval bucket the publish belongs to and is reflected in the topic. public static MqttApplicationMessage Create(IObservation observation, MTConnectMqttFormat format, string documentFormatterId = DocumentFormat.XML, bool retain = false, int interval = 0) { if (observation != null && !string.IsNullOrEmpty(observation.DeviceUuid) && observation.DataItem != null && observation.DataItem.Container != null && !observation.Values.IsNullOrEmpty()) @@ -242,6 +299,16 @@ public static MqttApplicationMessage Create(IObservation observation, MTConnectM return null; } + /// + /// Builds a publish for a batch of observations that all share the same data item (and + /// therefore the same MQTT topic). The first observation is inspected to derive the + /// topic; the payload is the formatter's serialisation of the whole batch. + /// + /// The observation batch; null or empty returns null. + /// Flat or hierarchy topic layout. + /// The document format used to serialise the observations (defaults to XML). + /// If true, the publish is retained. + /// When non-zero, identifies the observation-interval bucket the publish belongs to. public static MqttApplicationMessage Create(IEnumerable observations, MTConnectMqttFormat format, string documentFormatterId = DocumentFormat.XML, bool retain = false, int interval = 0) { if (!observations.IsNullOrEmpty()) diff --git a/libraries/MTConnect.NET-MQTT/MTConnectMqttRelay.cs b/libraries/MTConnect.NET-MQTT/MTConnectMqttRelay.cs index 8b0154f43..f743821a0 100644 --- a/libraries/MTConnect.NET-MQTT/MTConnectMqttRelay.cs +++ b/libraries/MTConnect.NET-MQTT/MTConnectMqttRelay.cs @@ -18,6 +18,15 @@ namespace MTConnect.Mqtt { + /// + /// Connects an in-process to a remote MQTT broker, forwarding + /// device, observation, and asset additions as publishes under the configured topic prefix. + /// Unlike the relay does not host its own broker; it owns + /// an and reconnects with exponential back-off (controlled by + /// ) if the broker drops. The relay also drives a heartbeat timer + /// and optional observation-interval buckets so consumers can subscribe to coarse-grained + /// snapshots in addition to per-observation publishes. + /// public class MTConnectMqttRelay : IDisposable { private const string _documentFormat = "JSON"; @@ -38,10 +47,13 @@ public class MTConnectMqttRelay : IDisposable private readonly System.Timers.Timer _heartbeatTimer = new System.Timers.Timer(); + /// The remote MQTT broker hostname or IP the relay connects to. public string Server => _configuration.Server; + /// The remote MQTT broker TCP port the relay connects to. public int Port => _configuration.Port; + /// MQTT Quality of Service level applied to every publish from the relay. public int Qos => _configuration.Qos; /// @@ -49,27 +61,46 @@ public class MTConnectMqttRelay : IDisposable /// public int RetryInterval => _configuration.RetryInterval; + /// Heartbeat publish cadence in milliseconds; the relay emits the agent's HeartbeatTimestamp publish at this rate. public int HeartbeatInterval => _heartbeatInterval; + /// Topic layout (flat or hierarchy) used for observation publishes; defaults to . public MTConnectMqttFormat Format { get; set; } + /// Topic prefix used for all publishes (sourced from the client configuration). public string TopicPrefix => _configuration.TopicPrefix; + /// When true, publishes carry the MQTT retain flag so consumers see the most recent values on connect. public bool RetainMessages { get; set; } + /// When true, broker TLS certificates that fail validation are still accepted; sourced from the client configuration. public bool AllowUntrustedCertificates => _configuration.AllowUntrustedCertificates; + /// Raised once the relay establishes its session with the remote broker. public event EventHandler Connected; + /// Raised when the broker session is dropped (either by the relay, the broker, or a transport failure). public event EventHandler Disconnected; + /// Raised after each successful publish; the argument is the topic name. public event EventHandler MessageSent; + /// Raised when establishing or maintaining the broker session throws. public event EventHandler ConnectionError; + /// Raised when an individual publish throws after the session has been established. public event EventHandler PublishError; + /// + /// Wires the relay to 's add events and prepares the + /// MQTT client and heartbeat/observation-interval timers. Construction is non-blocking; + /// the broker connection is opened on . + /// + /// The agent whose additions are forwarded to MQTT. + /// Broker connection settings; null falls back to a fresh . + /// Optional list of interval-bucket lengths in milliseconds for batched observation publishes. + /// Heartbeat publish cadence in milliseconds; defaults to one second. public MTConnectMqttRelay(IMTConnectAgent mtconnectAgent, IMTConnectMqttClientConfiguration configuration, IEnumerable observationIntervals = null, int heartbeatInterval = 1000) { _mtconnectAgent = mtconnectAgent; @@ -100,6 +131,11 @@ public MTConnectMqttRelay(IMTConnectAgent mtconnectAgent, IMTConnectMqttClientCo } + /// + /// Opens the broker session on a background task, starts the heartbeat timer, and + /// schedules any observation-interval bucket timers. The method returns immediately; + /// is raised when the broker session is up. + /// public void Start() { _stop = new CancellationTokenSource(); @@ -126,6 +162,11 @@ public void Start() } } + /// + /// Cancels the relay worker, stops the heartbeat timer, disposes the observation-interval + /// bucket timers, and tears down the broker session. is raised + /// once the session has been closed. + /// public void Stop() { if (_stop != null) _stop.Cancel(); @@ -266,6 +307,7 @@ private async Task Worker() } while (!_stop.Token.IsCancellationRequested); } + /// Disposes the underlying . Call first to release the heartbeat and bucket timers. public void Dispose() { if (_mqttClient != null) _mqttClient.Dispose(); diff --git a/libraries/MTConnect.NET-MQTT/MTConnectMqttResponseHandler.cs b/libraries/MTConnect.NET-MQTT/MTConnectMqttResponseHandler.cs index 6db7014ae..d2acb042e 100644 --- a/libraries/MTConnect.NET-MQTT/MTConnectMqttResponseHandler.cs +++ b/libraries/MTConnect.NET-MQTT/MTConnectMqttResponseHandler.cs @@ -1,9 +1,19 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. using MTConnect.Devices; namespace MTConnect { + /// + /// Callback used by the MTConnect MQTT client to deliver a parsed response document back to + /// application code, paired with the originating . The generic parameter + /// is one of the MTConnect response document + /// interfaces (devices, streams, assets); the handler is invoked once the client has + /// reassembled the document from the relevant MQTT topics. + /// + /// The MTConnect response document type carried to the handler. + /// The device the document pertains to (may be null for agent-scoped documents). + /// The reassembled response document. public delegate void MTConnectMqttResponseHandler(IDevice device, TResponseDocument responseDocument); } diff --git a/libraries/MTConnect.NET-MQTT/README.md b/libraries/MTConnect.NET-MQTT/README.md index fd3e75922..101af0a63 100644 --- a/libraries/MTConnect.NET-MQTT/README.md +++ b/libraries/MTConnect.NET-MQTT/README.md @@ -3,6 +3,8 @@ # MTConnect.NET-MQTT MTConnect.NET-MQTT is an extension library to MTConnect.NET that provides an MQTT Broker & Client interface to an IMTConnectAgentBroker interface. +For module-level reference (broker, relay, adapter), see [docs/modules](../../docs/modules/). + ## Nuget
diff --git a/libraries/MTConnect.NET-Protobuf/README.md b/libraries/MTConnect.NET-Protobuf/README.md new file mode 100644 index 000000000..8cc7cda43 --- /dev/null +++ b/libraries/MTConnect.NET-Protobuf/README.md @@ -0,0 +1,25 @@ +![MTConnect.NET Logo](https://raw.githubusercontent.com/TrakHound/MTConnect.NET/master/img/mtconnect-net-03-md.png) + +# MTConnect.NET-Protobuf +MTConnect.NET-Protobuf is an extension library to MTConnect.NET that is intended to provide reading and writing of MTConnect Response Documents using the Protocol Buffers (Protobuf) binary wire format. + +>**Note:** This library is a placeholder and is currently under active development. It does not yet expose a public API. Contributions and feedback are welcome via [GitHub Issues](https://github.com/TrakHound/MTConnect.NET/issues). + +For the XML and JSON format libraries that are production-ready today, see [MTConnect.NET-XML](../MTConnect.NET-XML/) and [MTConnect.NET-JSON-cppagent](../MTConnect.NET-JSON-cppagent/). + +## Overview +Protocol Buffers is a language-neutral, platform-neutral binary serialization format developed by Google. When complete, this library will provide a compact, high-throughput alternative to the XML and JSON response document formats for scenarios where bandwidth or parse latency is critical—for example, high-frequency MQTT or direct TCP data paths. + +## Related Libraries +- [MTConnect.NET-Common](../MTConnect.NET-Common/) — Core MTConnect entity model +- [MTConnect.NET-XML](../MTConnect.NET-XML/) — XML response document format (production-ready) +- [MTConnect.NET-JSON](../MTConnect.NET-JSON/) — JSON response document format +- [MTConnect.NET-JSON-cppagent](../MTConnect.NET-JSON-cppagent/) — JSON (cppagent) response document format (production-ready) + +## Contribution / Feedback +- Please use the [Issues](https://github.com/TrakHound/MTConnect.NET/issues) tab to create issues for specific problems that you may encounter +- Please feel free to use the [Pull Requests](https://github.com/TrakHound/MTConnect.NET/pulls) tab for any suggested improvements to the source code +- For any other questions or feedback, please contact TrakHound directly at **info@trakhound.com**. + +## License +This library and its source code is licensed under the [MIT License](https://choosealicense.com/licenses/mit/) and is free to use and distribute. diff --git a/libraries/MTConnect.NET-SHDR/Adapters/AgentClient.cs b/libraries/MTConnect.NET-SHDR/Adapters/AgentClient.cs index 032ca0329..f7cfd117b 100644 --- a/libraries/MTConnect.NET-SHDR/Adapters/AgentClient.cs +++ b/libraries/MTConnect.NET-SHDR/Adapters/AgentClient.cs @@ -21,6 +21,7 @@ public class AgentClient public TcpClient TcpClient { get; set; } + /// Constructs the connection wrapper with a unique and the already-open bound to the agent. public AgentClient(string id, TcpClient tcpClient) { Id = id; diff --git a/libraries/MTConnect.NET-SHDR/Adapters/AgentClientConnectionListener.cs b/libraries/MTConnect.NET-SHDR/Adapters/AgentClientConnectionListener.cs index 1d2e1c979..982068a70 100644 --- a/libraries/MTConnect.NET-SHDR/Adapters/AgentClientConnectionListener.cs +++ b/libraries/MTConnect.NET-SHDR/Adapters/AgentClientConnectionListener.cs @@ -13,14 +13,19 @@ namespace MTConnect.Adapters { + /// Delegate raised when an MTConnect agent opens a TCP connection to the SHDR adapter; is the per-connection identifier the listener assigns. public delegate void AgentConnectedHandler(string id, TcpClient client); + /// Delegate raised when an agent's TCP connection is closed or times out. public delegate void AgentDisconnectedHandler(string id); + /// Delegate raised for each PING received from or PONG sent to the agent identified by . public delegate void AgentResponseHandler(string id); + /// Delegate raised when the underlying throws (port in use, socket error). public delegate void AgentListenerErrorHandler(Exception exception); + /// Delegate raised when the heartbeat loop for a specific agent connection throws; the connection is normally torn down afterwards. public delegate void AgentConnectionErrorHandler(string id, Exception exception); @@ -44,19 +49,26 @@ public class AgentClientConnectionListener public int Heartbeat { get; set; } + /// Raised when a new agent TCP connection is accepted. public event AgentConnectedHandler ClientConnected; + /// Raised when an agent connection closes; the per-connection id is no longer valid afterwards. public event AgentDisconnectedHandler ClientDisconnected; + /// Raised for each SHDR PING received from a connected agent. public event AgentResponseHandler ClientPingReceived; + /// Raised after the listener writes the matching SHDR PONG back to the connected agent. public event AgentResponseHandler ClientPongSent; + /// Raised when the underlying throws (typically a port-in-use or socket failure). public event AgentListenerErrorHandler ListenerErrorReceived; + /// Raised when an individual agent connection's heartbeat loop throws. public event AgentConnectionErrorHandler ConnectionErrorReceived; + /// Constructs the listener with the TCP to bind to and the heartbeat interval in milliseconds. public AgentClientConnectionListener(int port, int heartbeat) { Port = port; @@ -64,25 +76,27 @@ public AgentClientConnectionListener(int port, int heartbeat) } + /// Starts the listener on a background task. The supplied token also triggers when cancelled. public void Start(CancellationToken cancel) { _stop = new CancellationTokenSource(); cancel.Register(() => { Stop(); }); - _= Task.Run(() => ClientListener(_stop.Token)); + _ = Task.Run(() => ClientListener(_stop.Token)); } + /// Stops the listener, closes every connected agent socket, and clears the connection table. public void Stop() { if (_stop != null) _stop.Cancel(); if (_listener != null) { - try - { - _listener.Stop(); + try + { + _listener.Stop(); } - catch (SocketException ex) + catch (SocketException ex) { if (ListenerErrorReceived != null) ListenerErrorReceived.Invoke(ex); } @@ -127,7 +141,7 @@ private async Task ClientListener(CancellationToken cancel) if (ClientConnected != null) ClientConnected.Invoke(clientId, client); // Start new Ping / Pong Task - _= Task.Run(() => HeartbeatConnection(clientId, client, cancel)); + _ = Task.Run(() => HeartbeatConnection(clientId, client, cancel)); } } catch (SocketException ex) diff --git a/libraries/MTConnect.NET-SHDR/Adapters/ItemQueue.cs b/libraries/MTConnect.NET-SHDR/Adapters/ItemQueue.cs index c26481757..4e157311b 100644 --- a/libraries/MTConnect.NET-SHDR/Adapters/ItemQueue.cs +++ b/libraries/MTConnect.NET-SHDR/Adapters/ItemQueue.cs @@ -45,7 +45,7 @@ public IEnumerable Take(int count = 1) foreach (var item in items) { - x.Add(item.Value); + x.Add(item.Value); } // Remove Items from Queue diff --git a/libraries/MTConnect.NET-SHDR/Adapters/ShdrAdapter.cs b/libraries/MTConnect.NET-SHDR/Adapters/ShdrAdapter.cs index 08c5ea70b..c34172cd6 100644 --- a/libraries/MTConnect.NET-SHDR/Adapters/ShdrAdapter.cs +++ b/libraries/MTConnect.NET-SHDR/Adapters/ShdrAdapter.cs @@ -30,9 +30,11 @@ public class ShdrAdapter private CancellationTokenSource _stop; + /// Exposes the internal cancellation source to subclasses so they can hook custom shutdown work onto the same token used by the adapter listener and worker threads. protected CancellationTokenSource StopToken => _stop; + /// The underlying that buffers SHDR observations and serialises them onto each connected agent's socket. protected IMTConnectAdapter Adapter => _adapter; @@ -129,6 +131,7 @@ public class ShdrAdapter public event EventHandler> ConnectionError; + /// Creates an SHDR adapter that listens on with the supplied interval (milliseconds), no device-key scope, duplicate filtering enabled, and timestamps emitted on every line. public ShdrAdapter(int port = 7878, int heartbeat = 10000) { FilterDuplicates = true; @@ -152,6 +155,7 @@ public ShdrAdapter(int port = 7878, int heartbeat = 10000) _connectionListener.ConnectionErrorReceived += ClientConnectionError; } + /// Creates an SHDR adapter scoped to , listening on with the supplied interval; lines targeting other devices are skipped. public ShdrAdapter(string deviceKey, int port = 7878, int heartbeat = 10000) { FilterDuplicates = true; @@ -176,6 +180,7 @@ public ShdrAdapter(string deviceKey, int port = 7878, int heartbeat = 10000) _connectionListener.ConnectionErrorReceived += ClientConnectionError; } + /// Creates an SHDR adapter from , pulling device key, port, heartbeat, and the IgnoreTimestamps flag from the configuration object. public ShdrAdapter(ShdrAdapterClientConfiguration configuration) { FilterDuplicates = true; @@ -205,6 +210,7 @@ public ShdrAdapter(ShdrAdapterClientConfiguration configuration) } } + /// Protected constructor used by interval and queue subclasses to wire the optional flush (milliseconds) and to opt in to the queue-buffer mode via . protected ShdrAdapter(int port = 7878, int heartbeat = 10000, int? interval = null, bool bufferEnabled = false) { FilterDuplicates = true; @@ -228,6 +234,7 @@ protected ShdrAdapter(int port = 7878, int heartbeat = 10000, int? interval = nu _connectionListener.ConnectionErrorReceived += ClientConnectionError; } + /// Protected device-keyed variant of the interval/queue constructor; see for the and semantics. protected ShdrAdapter(string deviceKey, int port = 7878, int heartbeat = 10000, int? interval = null, bool bufferEnabled = false) { FilterDuplicates = true; @@ -252,6 +259,7 @@ protected ShdrAdapter(string deviceKey, int port = 7878, int heartbeat = 10000, _connectionListener.ConnectionErrorReceived += ClientConnectionError; } + /// Protected configuration-driven variant of the interval/queue constructor; see for the and semantics. protected ShdrAdapter(ShdrAdapterClientConfiguration configuration, int? interval = null, bool bufferEnabled = false) { FilterDuplicates = true; @@ -311,8 +319,10 @@ public void Stop() } + /// Override-point invoked at the tail end of , after the listener and underlying adapter have been started. protected virtual void OnStart() { } + /// Override-point invoked at the tail end of , after the listener and underlying adapter have been signalled to stop. protected virtual void OnStop() { } @@ -428,8 +438,10 @@ public bool SendLast(long timestamp = 0) } + /// Override-point invoked after completes; subclasses can use it to record diagnostics or refresh derived state. protected virtual void OnChangedSent() { } + /// Override-point invoked after completes (typically once per reconnect); subclasses can use it to clear sent flags or trigger follow-up publishes. protected virtual void OnLastSent() { } #endregion @@ -536,6 +548,7 @@ private bool WriteDevices(IEnumerable devices) } + /// Writes a fully-formatted SHDR (terminator included) to every connected agent and returns true when at least one write succeeded. protected bool WriteLine(string line) { if (!string.IsNullOrEmpty(line)) @@ -556,7 +569,7 @@ protected bool WriteLine(string line) return success; } } - catch { } + catch { } } return false; @@ -688,29 +701,35 @@ private static IEnumerable SplitLines(string line) #region "DataItems" + /// Override-point invoked when an SHDR data-item observation is added to the buffered queue; subclasses can use it to tap, log, or rewrite observations before they are flushed. protected virtual void OnDataItemAdd(ShdrDataItem dataItem) { } + /// Adds a scalar Sample/Event observation for with and the current Unix time as the timestamp. public void AddDataItem(string dataItemKey, object value) { AddDataItem(dataItemKey, value, UnixDateTime.Now); } + /// Adds a scalar Sample/Event observation with an explicit (converted to Unix UTC time). public void AddDataItem(string dataItemKey, object value, DateTime timestamp) { AddDataItem(dataItemKey, value, timestamp.ToUnixUtcTime()); } + /// Adds a scalar Sample/Event observation with an explicit Unix-time (milliseconds since epoch). public void AddDataItem(string dataItemKey, object value, long timestamp) { AddDataItem(new ShdrDataItem(dataItemKey, value, timestamp)); } + /// Adds a pre-built to the buffered queue. public void AddDataItem(ShdrDataItem dataItem) { AddDataItem((IObservationInput)dataItem); } + /// Adds a batch of objects to the buffered queue. public void AddDataItems(IEnumerable dataItems) { if (!dataItems.IsNullOrEmpty()) @@ -722,32 +741,38 @@ public void AddDataItems(IEnumerable dataItems) } } + /// Adds an arbitrary to the buffered queue (used by SHDR data set/table/time-series observations that all flow through the same buffer). public void AddDataItem(IObservationInput observation) { _adapter.AddObservation(observation); } + /// Immediately writes a scalar Sample/Event observation to every connected agent and returns true when all writes succeeded. public bool SendDataItem(string dataItemKey, object value) { return SendDataItem(dataItemKey, value, UnixDateTime.Now); } + /// Sends a scalar Sample/Event observation with an explicit (converted to Unix UTC time). public bool SendDataItem(string dataItemKey, object value, DateTime timestamp) { return SendDataItem(dataItemKey, value, timestamp.ToUnixUtcTime()); } + /// Sends a scalar Sample/Event observation with an explicit Unix-time . public bool SendDataItem(string dataItemKey, object value, long timestamp) { return SendDataItem(new ShdrDataItem(dataItemKey, value, timestamp)); } + /// Sends a pre-built immediately. public bool SendDataItem(ShdrDataItem dataItem) { return SendDataItem((IObservationInput)dataItem); } + /// Sends a batch of objects immediately; returns true only when every observation was written successfully. public bool SendDataItems(IEnumerable dataItems) { var success = true; @@ -765,6 +790,7 @@ public bool SendDataItems(IEnumerable dataItems) return false; } + /// Sends an arbitrary immediately; the common entry point used by the data-set/table/time-series send overloads. public bool SendDataItem(IObservationInput observation) { return _adapter.SendObservation(observation); @@ -774,44 +800,53 @@ public bool SendDataItem(IObservationInput observation) #region "Messages" + /// Override-point invoked when an SHDR Message event is added to the buffered queue. protected virtual void OnMessageAdd(ShdrMessage message) { } + /// Adds a Message event for with the supplied text using the current Unix time. public void AddMessage(string messageId, string value) { AddMessage(messageId, value, UnixDateTime.Now); } + /// Adds a Message event with an explicit (converted to Unix UTC time). public void AddMessage(string messageId, string value, DateTime timestamp) { AddMessage(messageId, value, timestamp.ToUnixUtcTime()); } + /// Adds a Message event with an explicit Unix-time . public void AddMessage(string messageId, string value, long timestamp) { AddMessage(new ShdrMessage(messageId, value, timestamp)); } + /// Adds a Message event with a controller-supplied using the current Unix time. public void AddMessage(string messageId, string value, string nativeCode) { AddMessage(messageId, value, nativeCode, UnixDateTime.Now); } + /// Adds a Message event with native code and explicit (converted to Unix UTC time). public void AddMessage(string messageId, string value, string nativeCode, DateTime timestamp) { AddMessage(messageId, value, nativeCode, timestamp.ToUnixUtcTime()); } + /// Adds a Message event with native code and an explicit Unix-time . public void AddMessage(string messageId, string value, string nativeCode, long timestamp) { AddMessage(new ShdrMessage(messageId, value, nativeCode, timestamp)); } + /// Adds a pre-built to the buffered queue. public void AddMessage(ShdrMessage message) { _adapter.AddObservation(message); } + /// Adds a batch of Message events to the buffered queue. public void AddMessages(IEnumerable messages) { if (!messages.IsNullOrEmpty()) @@ -824,41 +859,49 @@ public void AddMessages(IEnumerable messages) } + /// Immediately writes a Message event using the current Unix time. public bool SendMessage(string dataItemId, string value) { return SendMessage(dataItemId, value, UnixDateTime.Now); } + /// Sends a Message event with an explicit . public bool SendMessage(string dataItemId, string value, DateTime timestamp) { return SendMessage(dataItemId, value, timestamp.ToUnixUtcTime()); } + /// Sends a Message event with an explicit Unix-time . public bool SendMessage(string dataItemId, string value, long timestamp) { return SendMessage(new ShdrMessage(dataItemId, value, timestamp)); } + /// Sends a Message event with a controller-supplied using the current Unix time. public bool SendMessage(string dataItemId, string value, string nativeCode) { return SendMessage(dataItemId, value, nativeCode, UnixDateTime.Now); } + /// Sends a Message event with native code and explicit . public bool SendMessage(string dataItemId, string value, string nativeCode, DateTime timestamp) { return SendMessage(dataItemId, value, nativeCode, timestamp.ToUnixUtcTime()); } + /// Sends a Message event with native code and an explicit Unix-time . public bool SendMessage(string dataItemId, string value, string nativeCode, long timestamp) { return SendMessage(new ShdrMessage(dataItemId, value, nativeCode, timestamp)); } + /// Sends a pre-built immediately. public bool SendMessage(ShdrMessage message) { return _adapter.SendObservation(message); } + /// Sends a batch of Message events immediately; returns true when every message wrote successfully. public bool SendMessages(IEnumerable messages) { var success = true; @@ -880,9 +923,11 @@ public bool SendMessages(IEnumerable messages) #region "Conditions" + /// Override-point invoked when an SHDR Condition is added to the buffered queue. protected virtual void OnConditionAdd(ShdrCondition condition) { } + /// Adds every fault state of to the buffered queue; the SHDR adapter emits one line per fault state so multi-state conditions remain individually addressable. public void AddCondition(ShdrCondition condition) { if (condition != null && !condition.FaultStates.IsNullOrEmpty()) @@ -894,6 +939,7 @@ public void AddCondition(ShdrCondition condition) } } + /// Adds a batch of objects, flattening each into its fault states. public void AddConditions(IEnumerable conditions) { if (!conditions.IsNullOrEmpty()) @@ -906,6 +952,7 @@ public void AddConditions(IEnumerable conditions) } + /// Immediately writes the first fault state of to every connected agent; the early-return behaviour exists to match the original send-on-first-state contract. public bool SendCondition(ShdrCondition condition) { if (condition != null && !condition.FaultStates.IsNullOrEmpty()) @@ -919,6 +966,7 @@ public bool SendCondition(ShdrCondition condition) return false; } + /// Sends a batch of objects immediately; returns true when every send succeeded. public bool SendConditions(IEnumerable conditions) { var success = true; @@ -940,14 +988,17 @@ public bool SendConditions(IEnumerable conditions) #region "TimeSeries" + /// Override-point invoked when an SHDR TimeSeries observation is added to the buffered queue. protected virtual void OnTimeSeriesAdd(ShdrTimeSeries timeSeries) { } + /// Adds a TimeSeries observation to the buffered queue. public void AddTimeSeries(ShdrTimeSeries timeSeries) { _adapter.AddObservation(timeSeries); } + /// Adds a batch of TimeSeries observations to the buffered queue. public void AddTimeSeries(IEnumerable timeSeries) { if (!timeSeries.IsNullOrEmpty()) @@ -960,11 +1011,13 @@ public void AddTimeSeries(IEnumerable timeSeries) } + /// Immediately writes a TimeSeries observation to every connected agent. public bool SendTimeSeries(ShdrTimeSeries timeSeries) { return _adapter.SendObservation(timeSeries); } + /// Sends a batch of TimeSeries observations immediately; returns true only when every observation was written successfully. public bool SendTimeSeries(IEnumerable timeSeries) { var success = true; @@ -986,14 +1039,17 @@ public bool SendTimeSeries(IEnumerable timeSeries) #region "DataSet" + /// Override-point invoked when an SHDR DataSet observation is added to the buffered queue. protected virtual void OnDataSetAdd(ShdrDataSet dataSet) { } + /// Adds a DataSet observation to the buffered queue. public void AddDataSet(ShdrDataSet dataSet) { _adapter.AddObservation(dataSet); } + /// Adds a batch of DataSet observations to the buffered queue. public void AddDataSets(IEnumerable dataSets) { if (!dataSets.IsNullOrEmpty()) @@ -1006,11 +1062,13 @@ public void AddDataSets(IEnumerable dataSets) } + /// Immediately writes a DataSet observation to every connected agent. public bool SendDataSet(ShdrDataSet dataSet) { return _adapter.SendObservation(dataSet); } + /// Sends a batch of DataSet observations immediately; returns true only when every observation was written successfully. public bool SendDataSets(IEnumerable dataSets) { var success = true; @@ -1032,14 +1090,17 @@ public bool SendDataSets(IEnumerable dataSets) #region "Table" + /// Override-point invoked when an SHDR Table observation is added to the buffered queue. protected virtual void OnTableAdd(ShdrTable table) { } + /// Adds a Table observation to the buffered queue. public void AddTable(ShdrTable table) { _adapter.AddObservation(table); } + /// Adds a batch of Table observations to the buffered queue. public void AddTables(IEnumerable tables) { if (!tables.IsNullOrEmpty()) @@ -1052,11 +1113,13 @@ public void AddTables(IEnumerable tables) } + /// Immediately writes a Table observation to every connected agent. public bool SendTable(ShdrTable table) { return _adapter.SendObservation(table); } + /// Sends a batch of Table observations immediately; returns true only when every observation was written successfully. public bool SendTables(IEnumerable tables) { var success = true; @@ -1079,6 +1142,7 @@ public bool SendTables(IEnumerable tables) #region "Assets" + /// Override-point invoked when an SHDR Asset is staged for publish; subclasses can rewrite or annotate the asset before it is serialised onto the wire. protected virtual void OnAssetAdd(ShdrAsset asset) { } diff --git a/libraries/MTConnect.NET-SHDR/Adapters/ShdrAdapterClient.cs b/libraries/MTConnect.NET-SHDR/Adapters/ShdrAdapterClient.cs index 3fc88bdb1..dc581c02f 100644 --- a/libraries/MTConnect.NET-SHDR/Adapters/ShdrAdapterClient.cs +++ b/libraries/MTConnect.NET-SHDR/Adapters/ShdrAdapterClient.cs @@ -12,19 +12,21 @@ namespace MTConnect.Adapters { - /// - /// A client to connect to MTConnect Adapters using TCP and communicating using the SHDR Protocol - /// - public class ShdrAdapterClient : ShdrClient + /// + /// A client to connect to MTConnect Adapters using TCP and communicating using the SHDR Protocol + /// + public class ShdrAdapterClient : ShdrClient { private readonly IShdrAdapterClientConfiguration _configuration; private readonly IMTConnectAgent _agent; private IDevice _device; + /// The device the SHDR client feeds observations into; replaced when the upstream adapter pushes a new device document. public IDevice Device => _device; + /// Constructs an adapter-client wired to and using the supplied 's hostname/port; is appended to the auto-generated when supplied. public ShdrAdapterClient( IShdrAdapterClientConfiguration configuration, IMTConnectAgent agent, @@ -46,6 +48,7 @@ public ShdrAdapterClient( } } + /// Overload that lets the caller override the configuration's hostname and port with explicit values (useful for multi-adapter setups that share a single configuration template). public ShdrAdapterClient( IShdrAdapterClientConfiguration configuration, IMTConnectAgent agent, @@ -67,6 +70,7 @@ int port } + /// Marks every DataItem of the bound device Unavailable when the adapter connection drops, so the agent's last-value cache reflects the loss of upstream telemetry. protected override void OnDisconnect() { if (_device != null) @@ -77,6 +81,7 @@ protected override void OnDisconnect() } + /// Resolves against the bound device's model so the SHDR parser can inspect the DataItem's representation and Constraints before dispatching the observation. protected override IDataItem OnGetDataItem(string dataItemKey) { if (_device != null && !string.IsNullOrEmpty(dataItemKey)) @@ -89,6 +94,7 @@ protected override IDataItem OnGetDataItem(string dataItemKey) } + /// Forwards a parsed scalar Sample/Event DataItem observation to the agent, applying the configuration's IgnoreTimestamps, ConvertUnits, and IgnoreObservationCase overrides. protected override void OnDataItemReceived(ShdrDataItem dataItem) { if (_device != null && _configuration != null) @@ -109,6 +115,7 @@ protected override void OnDataItemReceived(ShdrDataItem dataItem) } } + /// Forwards a parsed Condition fault state to the agent, applying the configuration's IgnoreTimestamps override. protected override void OnConditionFaultStateReceived(ShdrFaultState faultState) { if (_device != null) @@ -121,6 +128,7 @@ protected override void OnConditionFaultStateReceived(ShdrFaultState faultState) } } + /// Forwards a parsed Message event to the agent, applying the configuration's IgnoreTimestamps override. protected override void OnMessageReceived(ShdrMessage message) { if (_device != null) @@ -133,6 +141,7 @@ protected override void OnMessageReceived(ShdrMessage message) } } + /// Forwards a parsed Table observation to the agent, applying the configuration's IgnoreTimestamps, ConvertUnits, and IgnoreObservationCase overrides. protected override void OnTableReceived(ShdrTable table) { if (_device != null) @@ -153,6 +162,7 @@ protected override void OnTableReceived(ShdrTable table) } } + /// Forwards a parsed DataSet observation to the agent, applying the configuration's IgnoreTimestamps, ConvertUnits, and IgnoreObservationCase overrides. protected override void OnDataSetReceived(ShdrDataSet dataSet) { if (_device != null) @@ -173,6 +183,7 @@ protected override void OnDataSetReceived(ShdrDataSet dataSet) } } + /// Forwards a parsed TimeSeries observation to the agent, applying the configuration's IgnoreTimestamps and ConvertUnits overrides. protected override void OnTimeSeriesReceived(ShdrTimeSeries timeSeries) { if (_device != null) @@ -190,6 +201,7 @@ protected override void OnTimeSeriesReceived(ShdrTimeSeries timeSeries) } + /// Forwards a parsed asset to the agent, applying the configuration's IgnoreTimestamps override. protected override void OnAssetReceived(IAsset asset) { if (_device != null) @@ -202,6 +214,7 @@ protected override void OnAssetReceived(IAsset asset) } } + /// Removes the asset identified by from the agent at ; the timestamp is zeroed when the configuration's IgnoreTimestamps is set so the agent uses its own clock. protected override void OnRemoveAssetReceived(string assetId, long timestamp) { if (_device != null) @@ -217,6 +230,7 @@ protected override void OnRemoveAssetReceived(string assetId, long timestamp) } } + /// Removes every asset of from the agent at ; IgnoreTimestamps zeroes the timestamp so the agent uses its own clock. protected override void OnRemoveAllAssetsReceived(string assetType, long timestamp) { if (_device != null) @@ -233,6 +247,7 @@ protected override void OnRemoveAllAssetsReceived(string assetType, long timesta } + /// Replaces the bound device with and registers it with the agent; subsequent observations are routed against this new device. protected override void OnDeviceReceived(IDevice device) { if (device != null) diff --git a/libraries/MTConnect.NET-SHDR/Adapters/ShdrIntervalAdapter.cs b/libraries/MTConnect.NET-SHDR/Adapters/ShdrIntervalAdapter.cs index dd9c6f6d9..adbe87502 100644 --- a/libraries/MTConnect.NET-SHDR/Adapters/ShdrIntervalAdapter.cs +++ b/libraries/MTConnect.NET-SHDR/Adapters/ShdrIntervalAdapter.cs @@ -15,10 +15,13 @@ public class ShdrIntervalAdapter : ShdrAdapter private const int _defaultInterval = 100; + /// Creates an interval-mode adapter without a device key, on the supplied , with the supplied , and the supplied flush (defaults to 100 ms). public ShdrIntervalAdapter(int port = 7878, int heartbeat = 10000, int interval = _defaultInterval) : base(port, heartbeat, interval) { } + /// Creates an interval-mode adapter scoped to , on the supplied , with the supplied , and the supplied flush . public ShdrIntervalAdapter(string deviceKey, int port = 7878, int heartbeat = 10000, int interval = _defaultInterval) : base(deviceKey, port, heartbeat, interval) { } + /// Creates an interval-mode adapter from an with the supplied flush . public ShdrIntervalAdapter(ShdrAdapterClientConfiguration configuration, int interval = _defaultInterval) : base(configuration, interval) { } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-SHDR/Adapters/ShdrIntervalQueueAdapter.cs b/libraries/MTConnect.NET-SHDR/Adapters/ShdrIntervalQueueAdapter.cs index 3e1606caf..1dff38717 100644 --- a/libraries/MTConnect.NET-SHDR/Adapters/ShdrIntervalQueueAdapter.cs +++ b/libraries/MTConnect.NET-SHDR/Adapters/ShdrIntervalQueueAdapter.cs @@ -15,13 +15,17 @@ public class ShdrIntervalQueueAdapter : ShdrAdapter private const int _defaultInterval = 100; + /// Creates an interval-queue adapter without a device key, on the supplied , with the supplied and flush (defaults to 100 ms). public ShdrIntervalQueueAdapter(int port = 7878, int heartbeat = 10000, int interval = _defaultInterval) : base(port, heartbeat, interval, true) { } + /// Creates an interval-queue adapter scoped to , on the supplied , with the supplied and flush . public ShdrIntervalQueueAdapter(string deviceKey, int port = 7878, int heartbeat = 10000, int interval = _defaultInterval) : base(deviceKey, port, heartbeat, interval, true) { } + /// Creates an interval-queue adapter from an with the supplied flush . public ShdrIntervalQueueAdapter(ShdrAdapterClientConfiguration configuration, int interval = _defaultInterval) : base(configuration, interval, true) { } + /// Forces an immediate flush of the buffered SHDR lines to every connected agent, bypassing the interval timer; returns true when the send succeeded. public bool SendBuffer() { return Adapter.SendBuffer(); diff --git a/libraries/MTConnect.NET-SHDR/Adapters/ShdrQueueAdapter.cs b/libraries/MTConnect.NET-SHDR/Adapters/ShdrQueueAdapter.cs index f1c690533..b806d01ee 100644 --- a/libraries/MTConnect.NET-SHDR/Adapters/ShdrQueueAdapter.cs +++ b/libraries/MTConnect.NET-SHDR/Adapters/ShdrQueueAdapter.cs @@ -12,13 +12,17 @@ namespace MTConnect.Adapters /// public class ShdrQueueAdapter : ShdrAdapter { + /// Creates a queue-mode adapter without a device key, on the supplied , with the supplied interval in milliseconds. public ShdrQueueAdapter(int port = 7878, int heartbeat = 10000) : base(port, heartbeat, null, true) { } + /// Creates a queue-mode adapter scoped to , on the supplied , with the supplied . public ShdrQueueAdapter(string deviceKey, int port = 7878, int heartbeat = 10000) : base(deviceKey, port, heartbeat, null, true) { } + /// Creates a queue-mode adapter from an . public ShdrQueueAdapter(ShdrAdapterClientConfiguration configuration) : base(configuration, null, true) { } + /// Flushes the buffered SHDR lines to every connected agent in a single batch; returns true when the send succeeded. public bool SendBuffer() { return Adapter.SendBuffer(); diff --git a/libraries/MTConnect.NET-SHDR/Configurations/ShdrAdapterClientConfiguration.cs b/libraries/MTConnect.NET-SHDR/Configurations/ShdrAdapterClientConfiguration.cs index 7c6816f30..c4c180f87 100644 --- a/libraries/MTConnect.NET-SHDR/Configurations/ShdrAdapterClientConfiguration.cs +++ b/libraries/MTConnect.NET-SHDR/Configurations/ShdrAdapterClientConfiguration.cs @@ -48,6 +48,7 @@ public class ShdrAdapterClientConfiguration : ShdrClientConfiguration, IShdrAdap public bool IgnoreHeartbeatOnChange { get; set; } + /// Initialises the SHDR adapter-client configuration with the conventional defaults: connection state is not auto-marked Available, native timestamps are honoured, units are converted to the canonical MTConnect units, observation case is ignored when matching DataItem ids, connection information is emitted on the agent device, and heartbeat PINGs are suppressed while data is arriving. public ShdrAdapterClientConfiguration() { AvailableOnConnection = false; diff --git a/libraries/MTConnect.NET-SHDR/Configurations/ShdrClientConfiguration.cs b/libraries/MTConnect.NET-SHDR/Configurations/ShdrClientConfiguration.cs index 7560e9d59..21af63614 100644 --- a/libraries/MTConnect.NET-SHDR/Configurations/ShdrClientConfiguration.cs +++ b/libraries/MTConnect.NET-SHDR/Configurations/ShdrClientConfiguration.cs @@ -10,6 +10,7 @@ namespace MTConnect.Configurations /// public class ShdrClientConfiguration : IShdrClientConfiguration { + /// The wildcard literal (*) used in DeviceKey when the SHDR client accepts data for any device. public const string DeviceKeyWildcard = "*"; @@ -65,6 +66,7 @@ public string Id public int ReconnectInterval { get; set; } + /// Initialises the configuration with the conventional defaults expected by an SHDR client: device-key wildcard, localhost on port 7878, a 5-second heartbeat, a 600 ms legacy-silence timeout, and a 10-second reconnect interval. public ShdrClientConfiguration() { DeviceKey = DeviceKeyWildcard; diff --git a/libraries/MTConnect.NET-SHDR/Devices/ShdrAdapterComponent.cs b/libraries/MTConnect.NET-SHDR/Devices/ShdrAdapterComponent.cs index fe9fa64b1..b0f05fca4 100644 --- a/libraries/MTConnect.NET-SHDR/Devices/ShdrAdapterComponent.cs +++ b/libraries/MTConnect.NET-SHDR/Devices/ShdrAdapterComponent.cs @@ -12,6 +12,7 @@ namespace MTConnect.Devices.Components /// public class ShdrAdapterComponent : AdapterComponent { + /// The SHDR endpoint URI (hostname:port) that this adapter component represents on the agent device. public string Uri { get; set; } diff --git a/libraries/MTConnect.NET-SHDR/README.md b/libraries/MTConnect.NET-SHDR/README.md index 5e2533528..011729c3c 100644 --- a/libraries/MTConnect.NET-SHDR/README.md +++ b/libraries/MTConnect.NET-SHDR/README.md @@ -3,6 +3,8 @@ # MTConnect.NET-SHDR Classes to handle the SHDR Agent Adapter Protocol associated with the MTConnect Standard. +For the SHDR wire-format reference and module pages, see [docs/wire-formats/shdr](../../docs/wire-formats/shdr.md) and [docs/modules](../../docs/modules/). + ## Nuget
diff --git a/libraries/MTConnect.NET-SHDR/Shdr/ShdrAsset.cs b/libraries/MTConnect.NET-SHDR/Shdr/ShdrAsset.cs index b68c17c9f..411dc314d 100644 --- a/libraries/MTConnect.NET-SHDR/Shdr/ShdrAsset.cs +++ b/libraries/MTConnect.NET-SHDR/Shdr/ShdrAsset.cs @@ -14,9 +14,16 @@ namespace MTConnect.Shdr /// public class ShdrAsset { + /// The SHDR designator that introduces a multi-line asset publish (@ASSET@|assetId|assetType|--multiline--...). public const string AssetDesignator = "@ASSET@"; + + /// The SHDR designator that signals removal of a single asset by id (@REMOVE_ASSET@|assetId). public const string AssetRemoveDesignator = "@REMOVE_ASSET@"; + + /// The SHDR designator that signals removal of every asset of a given type (@REMOVE_ALL_ASSETS@|assetType). public const string AssetRemoveAllDesignator = "@REMOVE_ALL_ASSETS@"; + + /// The SHDR designator that updates an existing asset (@UPDATE_ASSET@|assetId|...). public const string AssetUpdateDesignator = "@UPDATE_ASSET@"; private static readonly string AssetIdPattern = $"{AssetDesignator}\\|(.*)\\|.*\\|--multiline--"; @@ -119,8 +126,10 @@ public byte[] ChangeIdWithTimestamp } + /// Creates an empty SHDR asset record for builder-style population. public ShdrAsset() { } + /// Creates an SHDR asset from its identifier, type, XML representation, and optional Unix-time ; the XML is parsed eagerly to populate . public ShdrAsset(string assetId, string assetType, string xml, long timestamp = 0) { AssetId = assetId; @@ -132,6 +141,7 @@ public ShdrAsset(string assetId, string assetType, string xml, long timestamp = Timestamp = timestamp; } + /// Creates an SHDR asset wrapping the supplied ; populates the id, type, and timestamp from the asset. public ShdrAsset(IAsset asset) { if (asset != null) @@ -150,8 +160,11 @@ public ShdrAsset(IAsset asset) } + /// Serialises the asset using the multi-line SHDR encoding. public override string ToString() => ToString(true); + /// Serialises the asset to its SHDR textual form, optionally using the multi-line encoding that wraps the XML body between matching --multiline--id markers. + /// When true emits the multi-line form; when false produces a single-line representation suitable for compact log diffing. public string ToString(bool multiline = false) { if (!string.IsNullOrEmpty(AssetId) && !string.IsNullOrEmpty(Xml)) @@ -240,6 +253,7 @@ public static string RemoveAll(string assetType, long timestamp = 0) #region "Detect" + /// Returns true when begins with the token (with or without a leading ISO timestamp). public static bool IsAssetLine(string input) { if (!string.IsNullOrEmpty(input)) @@ -265,6 +279,7 @@ public static bool IsAssetLine(string input) return false; } + /// Returns true when is an asset line that opens a multi-line block (the line ends with --multiline--id). public static bool IsAssetMultilineBegin(string input) { if (IsAssetLine(input)) @@ -290,6 +305,7 @@ public static bool IsAssetMultilineBegin(string input) } + /// Returns true when closes the multi-line block whose opener carried the matching . public static bool IsAssetMultilineEnd(string multilineId, string input) { if (!string.IsNullOrEmpty(input)) @@ -307,6 +323,7 @@ public static bool IsAssetMultilineEnd(string multilineId, string input) } + /// Returns true when begins with the token (with or without a leading timestamp). public static bool IsAssetRemove(string input) { if (!string.IsNullOrEmpty(input)) @@ -332,6 +349,7 @@ public static bool IsAssetRemove(string input) } + /// Returns true when begins with the token (with or without a leading timestamp). public static bool IsAssetRemoveAll(string input) { if (!string.IsNullOrEmpty(input)) @@ -357,6 +375,7 @@ public static bool IsAssetRemoveAll(string input) } + /// Returns true when begins with the token (with or without a leading timestamp). public static bool IsAssetUpdate(string input) { if (!string.IsNullOrEmpty(input)) @@ -385,6 +404,7 @@ public static bool IsAssetUpdate(string input) #region "Read" + /// Parses the leading ISO timestamp segment of and returns it as Unix time (milliseconds since epoch); returns 0 when no timestamp is present. public static long ReadTimestamp(string input) { if (!string.IsNullOrEmpty(input)) @@ -400,6 +420,7 @@ public static long ReadTimestamp(string input) return 0; } + /// Extracts the asset id from a multi-line asset header (@ASSET@|assetId|assetType|--multiline--id); returns null when no match is found. public static string ReadAssetId(string input) { if (!string.IsNullOrEmpty(input)) @@ -428,6 +449,7 @@ public static string ReadAssetId(string input) return null; } + /// Extracts the asset type from a multi-line asset header; returns null when no match is found. public static string ReadAssetType(string input) { if (!string.IsNullOrEmpty(input)) @@ -456,6 +478,7 @@ public static string ReadAssetType(string input) return null; } + /// Extracts the multi-line block id that follows the --multiline-- marker on an asset header; returns null when no match is found. public static string ReadAssetMultilineId(string input) { if (!string.IsNullOrEmpty(input)) @@ -484,6 +507,7 @@ public static string ReadAssetMultilineId(string input) return null; } + /// Extracts the target asset id from a @REMOVE_ASSET@|assetId SHDR line; returns null when no match is found. public static string ReadRemoveAssetId(string input) { if (!string.IsNullOrEmpty(input)) @@ -510,6 +534,7 @@ public static string ReadRemoveAssetId(string input) return null; } + /// Extracts the target asset type from a @REMOVE_ALL_ASSETS@|type SHDR line; returns null when no match is found. public static string ReadRemoveAllAssetType(string input) { if (!string.IsNullOrEmpty(input)) @@ -537,6 +562,7 @@ public static string ReadRemoveAllAssetType(string input) } + /// Parses an SHDR asset-publish line back into an instance, lifting any leading timestamp; returns null when does not match the expected layout. public static ShdrAsset FromString(string input) { if (!string.IsNullOrEmpty(input)) @@ -604,6 +630,7 @@ private static ShdrAsset FromLine(string input, long timestamp = 0) #endregion + /// Formats a Unix-time as the ISO 8601 string used in the SHDR timestamp field, honouring when supplied or falling back to UTC. Returns an empty string when is non-positive. protected static string GetTimestampString(long timestamp, TimeZoneInfo timeZoneInfo = null) { if (timestamp > 0) diff --git a/libraries/MTConnect.NET-SHDR/Shdr/ShdrClient.cs b/libraries/MTConnect.NET-SHDR/Shdr/ShdrClient.cs index 7f6ef7136..e3506f425 100644 --- a/libraries/MTConnect.NET-SHDR/Shdr/ShdrClient.cs +++ b/libraries/MTConnect.NET-SHDR/Shdr/ShdrClient.cs @@ -21,10 +21,19 @@ namespace MTConnect.Shdr /// public class ShdrClient { + /// The literal SHDR PING command (* PING\n) sent to the adapter to probe for a heartbeat PONG response. public const string PingMessage = "* PING\n"; + + /// The read buffer size in bytes used when consuming the adapter socket; sized at 1 MB to accommodate multi-line device documents. public const int BufferSize = 1048576; // 1 MB + + /// Default heartbeat interval (in milliseconds) the client expects to see PONG responses at; 10 seconds. public const int DefaultPongHeartbeat = 10000; // 10 seconds + + /// Default TCP send/receive timeout (in milliseconds); 30 seconds. public const int DefaultConnectionTimeout = 30000; // 30 seconds + + /// Default delay (in milliseconds) before attempting to reconnect after the adapter connection is lost; 10 seconds. public const int DefaultReconnectInterval = 10000; // 10 seconds private TcpClient _client; @@ -32,7 +41,7 @@ public class ShdrClient private CancellationTokenSource _stop; private int _heartbeat = DefaultPongHeartbeat; - + /// /// The unique ID of the Client Connection /// @@ -113,12 +122,14 @@ public class ShdrClient public event EventHandler CommandReceived; + /// Creates an unconfigured SHDR client with a fresh random and the heartbeat-on-change suppression enabled. public ShdrClient() { Id = StringFunctions.RandomString(10); IgnoreHeartbeatOnChange = true; } + /// Creates an SHDR client connecting to : with optional timeout and reconnect overrides. public ShdrClient(string hostname, int port, int connectionTimeout = DefaultConnectionTimeout, int reconnectInterval = DefaultReconnectInterval) { Id = StringFunctions.RandomString(10); @@ -129,6 +140,7 @@ public ShdrClient(string hostname, int port, int connectionTimeout = DefaultConn IgnoreHeartbeatOnChange = true; } + /// Creates an SHDR client scoped to a single device key on : with optional timeout and reconnect overrides. public ShdrClient(string hostname, int port, string deviceKey, int connectionTimeout = DefaultConnectionTimeout, int reconnectInterval = DefaultReconnectInterval) { Id = StringFunctions.RandomString(10); @@ -140,6 +152,7 @@ public ShdrClient(string hostname, int port, string deviceKey, int connectionTim IgnoreHeartbeatOnChange = true; } + /// Creates an SHDR client populated from ; a null configuration falls back to the parameterless defaults. public ShdrClient(ShdrClientConfiguration configuration) { Id = StringFunctions.RandomString(10); @@ -157,45 +170,60 @@ public ShdrClient(ShdrClientConfiguration configuration) } + /// Launches the listen-and-reconnect loop on a background task. Returns immediately; is raised once the adapter socket is established. public void Start() { _stop = new CancellationTokenSource(); - _= Task.Run(() => ListenForAdapter(_stop.Token)); + _ = Task.Run(() => ListenForAdapter(_stop.Token)); } + /// Signals the background loop to exit and disconnect from the adapter. public void Stop() { if (_stop != null) _stop.Cancel(); } + /// Override-point called immediately after the TCP connection to the adapter is established (before any data is read). protected virtual void OnConnect() { } + /// Override-point called when the adapter connection drops (clean shutdown, timeout, or transport error). protected virtual void OnDisconnect() { } + /// Override-point that resolves a DataItem id/name to the live ; consumed by the SHDR parser to determine the observation representation. protected virtual IDataItem OnGetDataItem(string dataItemKey) { return null; } + /// Override-point called for every parsed scalar Sample/Event observation. protected virtual void OnDataItemReceived(ShdrDataItem dataItem) { } + /// Override-point called for every parsed Condition fault state. protected virtual void OnConditionFaultStateReceived(ShdrFaultState faultState) { } + /// Override-point called for every parsed Message event. protected virtual void OnMessageReceived(ShdrMessage message) { } + /// Override-point called for every parsed DataSet observation. protected virtual void OnDataSetReceived(ShdrDataSet dataSet) { } + /// Override-point called for every parsed Table observation. protected virtual void OnTableReceived(ShdrTable table) { } + /// Override-point called for every parsed TimeSeries observation. protected virtual void OnTimeSeriesReceived(ShdrTimeSeries timeSeries) { } + /// Override-point called when an asset publish (@ASSET@) has been parsed and reassembled. protected virtual void OnAssetReceived(IAsset asset) { } + /// Override-point called when a @REMOVE_ASSET@ SHDR line targeting at has been parsed. protected virtual void OnRemoveAssetReceived(string assetId, long timestamp) { } + /// Override-point called when a @REMOVE_ALL_ASSETS@ SHDR line targeting at has been parsed. protected virtual void OnRemoveAllAssetsReceived(string assetType, long timestamp) { } + /// Override-point called when a multi-line @DEVICE@ document has been reassembled and parsed back into an . protected virtual void OnDeviceReceived(IDevice device) { } @@ -341,7 +369,7 @@ private async Task ListenForAdapter(CancellationToken cancel) private bool ProcessResponse(ref char[] chars, int length) { var response = new string(chars, 0, length); - + if (response.Contains("\n")) { var lines = response.Split('\n'); @@ -672,7 +700,7 @@ private static AddressFamily GetIpAddressType(string input) } } - return AddressFamily.InterNetwork; + return AddressFamily.InterNetwork; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-SHDR/Shdr/ShdrCondition.cs b/libraries/MTConnect.NET-SHDR/Shdr/ShdrCondition.cs index 37079a96c..c25b19739 100644 --- a/libraries/MTConnect.NET-SHDR/Shdr/ShdrCondition.cs +++ b/libraries/MTConnect.NET-SHDR/Shdr/ShdrCondition.cs @@ -113,11 +113,13 @@ public byte[] ChangeIdWithTimestamp private ShdrCondition() { } + /// Creates a Condition observation scoped to a single DataItem key with no fault states yet recorded. public ShdrCondition(string dataItemKey) { DataItemKey = dataItemKey; } + /// Creates a Condition observation with an initial fault state at and an optional Unix-time . public ShdrCondition(string dataItemKey, ConditionLevel level, long timestamp = 0) { DataItemKey = dataItemKey; @@ -125,6 +127,7 @@ public ShdrCondition(string dataItemKey, ConditionLevel level, long timestamp = AddFaultState(new ShdrFaultState(timestamp, level)); } + /// Creates a Condition observation with an initial fault state at and an explicit . public ShdrCondition(string dataItemKey, ConditionLevel level, DateTime timestamp) { DataItemKey = dataItemKey; @@ -132,6 +135,7 @@ public ShdrCondition(string dataItemKey, ConditionLevel level, DateTime timestam AddFaultState(new ShdrFaultState(timestamp, level)); } + /// Clones the supplied into an SHDR-flavoured condition, lifting each fault state into a . public ShdrCondition(IConditionObservationInput conditionObservation) { if (conditionObservation != null) @@ -152,6 +156,7 @@ public ShdrCondition(IConditionObservationInput conditionObservation) } } + /// Copy-constructs a Condition from , duplicating its list. public ShdrCondition(ShdrCondition condition) { if (condition != null) @@ -467,6 +472,7 @@ public void AddFaultState(ShdrFaultState faultState) } + /// Removes only the fault states whose equals ; useful for clearing a single alarm code without dropping the rest of the condition state. public void ClearFaultStates(string nativeCode) { lock (_lock) @@ -489,6 +495,7 @@ public void ClearFaultStates(string nativeCode) _changeIdWithTimestamp = null; } + /// Removes every fault state currently associated with the condition (does not flip ; use to set the condition to UNAVAILABLE). public void ClearFaultStates() { lock (_lock) _faultStates = null; diff --git a/libraries/MTConnect.NET-SHDR/Shdr/ShdrDataItem.cs b/libraries/MTConnect.NET-SHDR/Shdr/ShdrDataItem.cs index 5ebd45bb2..47d3e98fc 100644 --- a/libraries/MTConnect.NET-SHDR/Shdr/ShdrDataItem.cs +++ b/libraries/MTConnect.NET-SHDR/Shdr/ShdrDataItem.cs @@ -24,6 +24,7 @@ public class ShdrDataItem : ObservationInput /// internal bool IsSent { get; set; } + /// The observation's primary value (); the name CDATA mirrors the historical XML element it serialises to. public string CDATA { get => GetValue(ValueKeys.Result); @@ -31,14 +32,17 @@ public string CDATA } + /// Creates an empty SHDR data-item observation for builder-style population. public ShdrDataItem() { } + /// Creates an SHDR data-item observation scoped to a single DataItem key. public ShdrDataItem(string dataItemKey) { DataItemKey = dataItemKey; Timestamp = 0; } + /// Creates an SHDR data-item observation with the supplied DataItem key and value (rendered via ). public ShdrDataItem(string dataItemKey, object value) { DataItemKey = dataItemKey; @@ -49,6 +53,7 @@ public ShdrDataItem(string dataItemKey, object value) Timestamp = 0; } + /// Creates an SHDR data-item observation with an explicit Unix-time (milliseconds since epoch). public ShdrDataItem(string dataItemKey, object value, long timestamp) { DataItemKey = dataItemKey; @@ -59,6 +64,7 @@ public ShdrDataItem(string dataItemKey, object value, long timestamp) Timestamp = timestamp; } + /// Creates an SHDR data-item observation with an explicit ; converted to Unix UTC time during construction. public ShdrDataItem(string dataItemKey, object value, DateTime timestamp) { DataItemKey = dataItemKey; @@ -70,6 +76,7 @@ public ShdrDataItem(string dataItemKey, object value, DateTime timestamp) } + /// Clones the supplied into an SHDR-flavoured data-item observation. public ShdrDataItem(IObservationInput observation) { if (observation != null) @@ -114,7 +121,7 @@ public override string ToString() { return $"|{target}|{value}{resetTriggered}"; } - } + } } return null; @@ -127,7 +134,7 @@ private static string ToString(ShdrDataItem dataItem, bool ignoreTimestamp = fal var valueString = dataItem.GetValue(ValueKeys.Result); if (valueString != null) { - var target = dataItem.DataItemKey; + var target = dataItem.DataItemKey; if (!string.IsNullOrEmpty(dataItem.DeviceKey)) target = $"{dataItem.DeviceKey}:{target}"; var value = valueString.Replace("|", @"\|").Trim(); @@ -155,6 +162,7 @@ private static string ToString(ShdrDataItem dataItem, bool ignoreTimestamp = fal return ""; } + /// Converts a batch of objects to a multi-line SHDR payload by wrapping each one as an and grouping by device and timestamp; returns null when the batch is empty. public static string ToString(IEnumerable observations) { if (!observations.IsNullOrEmpty()) @@ -280,7 +288,7 @@ public static string ToString(IEnumerable dataItems, bool ignoreTi } } } - } + } } // Convert list of lines to single string with new line terminator diff --git a/libraries/MTConnect.NET-SHDR/Shdr/ShdrDataSet.cs b/libraries/MTConnect.NET-SHDR/Shdr/ShdrDataSet.cs index 2686df55d..e815a4617 100644 --- a/libraries/MTConnect.NET-SHDR/Shdr/ShdrDataSet.cs +++ b/libraries/MTConnect.NET-SHDR/Shdr/ShdrDataSet.cs @@ -24,19 +24,24 @@ public class ShdrDataSet : DataSetObservationInput internal bool IsSent { get; set; } + /// Creates an empty SHDR data-set observation for builder-style population. public ShdrDataSet() { } + /// Creates an SHDR data-set observation scoped to a single DataItem key (no entries set). + /// The DataItem id or name the data-set applies to. public ShdrDataSet(string dataItemKey) { DataItemKey = dataItemKey; } + /// Creates an SHDR data-set observation with the supplied DataItem key and entry set. public ShdrDataSet(string dataItemKey, IEnumerable entries) { DataItemKey = dataItemKey; Entries = entries; } + /// Creates an SHDR data-set observation with an explicit Unix-time (milliseconds since epoch). public ShdrDataSet(string dataItemKey, IEnumerable entries, long timestamp) { DataItemKey = dataItemKey; @@ -44,6 +49,7 @@ public ShdrDataSet(string dataItemKey, IEnumerable entries, long Timestamp = timestamp; } + /// Creates an SHDR data-set observation with an explicit ; converted to Unix time during construction. public ShdrDataSet(string dataItemKey, IEnumerable entries, DateTime timestamp) { DataItemKey = dataItemKey; @@ -51,6 +57,7 @@ public ShdrDataSet(string dataItemKey, IEnumerable entries, DateT Timestamp = timestamp.ToUnixTime(); } + /// Clones the supplied into an SHDR-flavoured observation. public ShdrDataSet(DataSetObservationInput dataSetObservation) { if (dataSetObservation != null) diff --git a/libraries/MTConnect.NET-SHDR/Shdr/ShdrDataSetEntry.cs b/libraries/MTConnect.NET-SHDR/Shdr/ShdrDataSetEntry.cs index f244c927c..d1fff46c3 100644 --- a/libraries/MTConnect.NET-SHDR/Shdr/ShdrDataSetEntry.cs +++ b/libraries/MTConnect.NET-SHDR/Shdr/ShdrDataSetEntry.cs @@ -6,10 +6,17 @@ namespace MTConnect.Shdr { + /// + /// SHDR-flavoured that adds round-tripping to and from the + /// key=value token form used inside SHDR data-set lines (a removed entry is encoded as + /// key= with an empty value). + /// public class ShdrDataSetEntry : DataSetEntry { + /// Creates an empty entry for serialiser-driven construction. public ShdrDataSetEntry() { } + /// Creates an entry with an explicit key, value, and removed flag; is rendered via . public ShdrDataSetEntry(string key, object value, bool removed = false) { Key = key; @@ -17,6 +24,7 @@ public ShdrDataSetEntry(string key, object value, bool removed = false) Removed = removed; } + /// Clones the supplied into a new SHDR-flavoured entry. public ShdrDataSetEntry(IDataSetEntry entry) { if (entry != null) @@ -27,6 +35,7 @@ public ShdrDataSetEntry(IDataSetEntry entry) } } + /// Serialises the entry to its SHDR key=value textual form (or key= when removed); returns the empty string when is empty. public override string ToString() { if (!string.IsNullOrEmpty(Key)) @@ -44,6 +53,7 @@ public override string ToString() return ""; } + /// Parses a single SHDR key=value segment back into an entry; returns null when is empty or does not match the expected pattern. public static ShdrDataSetEntry FromString(string segment) { if (!string.IsNullOrEmpty(segment)) diff --git a/libraries/MTConnect.NET-SHDR/Shdr/ShdrDevice.cs b/libraries/MTConnect.NET-SHDR/Shdr/ShdrDevice.cs index 9864b644e..9a73d25a2 100644 --- a/libraries/MTConnect.NET-SHDR/Shdr/ShdrDevice.cs +++ b/libraries/MTConnect.NET-SHDR/Shdr/ShdrDevice.cs @@ -14,8 +14,13 @@ namespace MTConnect.Shdr /// public class ShdrDevice { + /// The SHDR designator that introduces a multi-line device document publish (@DEVICE@|uuid|type|--multiline--...). public const string DeviceDesignator = "@DEVICE@"; + + /// The SHDR designator that signals removal of a single device by UUID (@REMOVE_DEVICE@|uuid). public const string DeviceRemoveDesignator = "@REMOVE_DEVICE@"; + + /// The SHDR designator that signals removal of every device of a given type (@REMOVE_ALL_DEVICE@|type). public const string DeviceRemoveAllDesignator = "@REMOVE_ALL_DEVICE@"; private static string DeviceUuidPattern = $"{DeviceDesignator}\\|(.*)\\|.*\\|--multiline--"; @@ -65,8 +70,10 @@ public string ChangeId } + /// Creates an empty SHDR device record for builder-style population. public ShdrDevice() { } + /// Creates an SHDR device from a UUID and the device's XML representation; the XML is parsed eagerly to populate . public ShdrDevice(string deviceUuid, string xml) { DeviceUuid = deviceUuid; @@ -76,6 +83,7 @@ public ShdrDevice(string deviceUuid, string xml) Xml = xml; } + /// Creates an SHDR device wrapping the supplied ; if its is empty a fresh GUID is assigned. public ShdrDevice(IDevice device) { if (device != null) @@ -87,8 +95,11 @@ public ShdrDevice(IDevice device) } + /// Serialises the device using the multi-line SHDR encoding. public override string ToString() => ToString(true); + /// Serialises the device to its SHDR textual form, optionally using the multi-line encoding that wraps the XML body between matching --multiline--id markers. + /// When true emits the multi-line form; when false produces a single-line representation that suppresses the embedded XML body. public string ToString(bool multiline = false) { if (!string.IsNullOrEmpty(DeviceUuid)) @@ -211,6 +222,7 @@ public static string RemoveAll(string deviceType, long timestamp = 0) #region "Detect" + /// Returns true when begins with the token, identifying it as an SHDR device line. public static bool IsDeviceLine(string input) { if (!string.IsNullOrEmpty(input)) @@ -227,6 +239,7 @@ public static bool IsDeviceLine(string input) return false; } + /// Returns true when is a device line that opens a multi-line block (the line ends with --multiline--id). public static bool IsDeviceMultilineBegin(string input) { if (IsDeviceLine(input)) @@ -237,6 +250,7 @@ public static bool IsDeviceMultilineBegin(string input) return false; } + /// Returns true when closes the multi-line block whose opener carried the matching . public static bool IsDeviceMultilineEnd(string multilineId, string input) { if (!string.IsNullOrEmpty(input)) @@ -253,6 +267,7 @@ public static bool IsDeviceMultilineEnd(string multilineId, string input) return false; } + /// Returns true when begins with the token. public static bool IsDeviceRemove(string input) { if (!string.IsNullOrEmpty(input)) @@ -267,6 +282,7 @@ public static bool IsDeviceRemove(string input) return false; } + /// Returns true when begins with the token. public static bool IsDeviceRemoveAll(string input) { if (!string.IsNullOrEmpty(input)) @@ -285,6 +301,7 @@ public static bool IsDeviceRemoveAll(string input) #region "Read" + /// Parses the leading ISO timestamp segment of and returns it as Unix time (milliseconds since epoch); returns 0 when no timestamp is present. public static long ReadTimestamp(string input) { if (!string.IsNullOrEmpty(input)) @@ -300,6 +317,7 @@ public static long ReadTimestamp(string input) return 0; } + /// Extracts the DeviceUuid field from a multi-line device header (@DEVICE@|uuid|type|--multiline--id); returns null when no match is found. public static string ReadDeviceUuid(string input) { if (!string.IsNullOrEmpty(input)) @@ -328,6 +346,7 @@ public static string ReadDeviceUuid(string input) return null; } + /// Extracts the device type field from a multi-line device header; returns null when no match is found. public static string ReadDeviceType(string input) { if (!string.IsNullOrEmpty(input)) @@ -356,6 +375,7 @@ public static string ReadDeviceType(string input) return null; } + /// Extracts the multi-line block id that follows the --multiline-- marker; returns null when no match is found. public static string ReadDeviceMultilineId(string input) { if (!string.IsNullOrEmpty(input)) @@ -370,6 +390,7 @@ public static string ReadDeviceMultilineId(string input) return null; } + /// Extracts the target UUID from a @REMOVE_DEVICE@|uuid SHDR line; returns null when no match is found. public static string ReadRemoveDeviceUuid(string input) { if (!string.IsNullOrEmpty(input)) @@ -396,6 +417,7 @@ public static string ReadRemoveDeviceUuid(string input) return null; } + /// Extracts the target device type from a @REMOVE_ALL_DEVICE@|type SHDR line; returns null when no match is found. public static string ReadRemoveAllDeviceType(string input) { if (!string.IsNullOrEmpty(input)) @@ -423,6 +445,7 @@ public static string ReadRemoveAllDeviceType(string input) } + /// Parses an SHDR device-publish line back into an instance; returns null when is empty or does not match the expected layout. public static ShdrDevice FromString(string input) { if (!string.IsNullOrEmpty(input)) diff --git a/libraries/MTConnect.NET-SHDR/Shdr/ShdrFaultState.cs b/libraries/MTConnect.NET-SHDR/Shdr/ShdrFaultState.cs index f5a34b6af..cc4748a0b 100644 --- a/libraries/MTConnect.NET-SHDR/Shdr/ShdrFaultState.cs +++ b/libraries/MTConnect.NET-SHDR/Shdr/ShdrFaultState.cs @@ -100,8 +100,10 @@ public string Message internal bool IsSent { get; set; } + /// Creates an empty fault-state record for builder-style population. public ShdrFaultState() { } + /// Creates a fault state with the supplied level and optional native code/severity, qualifier, condition id, and message. public ShdrFaultState( ConditionLevel level, string message = null, @@ -119,6 +121,7 @@ public ShdrFaultState( if (!string.IsNullOrEmpty(message)) Message = message; } + /// Creates a fault state with an explicit Unix-time (milliseconds since epoch). public ShdrFaultState( long timestamp, ConditionLevel level, @@ -138,6 +141,7 @@ public ShdrFaultState( Timestamp = timestamp; } + /// Creates a fault state with an explicit ; converted to Unix time during construction. public ShdrFaultState( DateTime timestamp, ConditionLevel level, @@ -157,6 +161,7 @@ public ShdrFaultState( Timestamp = timestamp.ToUnixTime(); } + /// Clones the supplied condition-fault-state observation input into an SHDR-flavoured record. public ShdrFaultState(IConditionFaultStateObservationInput conditionObservation) { if (conditionObservation != null) @@ -185,7 +190,7 @@ public override string ToString() var target = DataItemKey; if (!string.IsNullOrEmpty(DeviceKey)) target = $"{DeviceKey}:{target}"; - + string identifier; if (!string.IsNullOrEmpty(NativeCode)) { @@ -198,7 +203,7 @@ public override string ToString() // If no ConditionId or NativeCode specified, then create hash of Message if (string.IsNullOrEmpty(identifier)) identifier = Message?.ToMD5Hash(); - + var message = !string.IsNullOrEmpty(Message) ? Message.Replace("|", @"\|") : ""; var qualifier = Qualifier != ConditionQualifier.NOT_SPECIFIED ? Qualifier.ToString() : ""; diff --git a/libraries/MTConnect.NET-SHDR/Shdr/ShdrLine.cs b/libraries/MTConnect.NET-SHDR/Shdr/ShdrLine.cs index 16e0b6d3b..7e71fb9fb 100644 --- a/libraries/MTConnect.NET-SHDR/Shdr/ShdrLine.cs +++ b/libraries/MTConnect.NET-SHDR/Shdr/ShdrLine.cs @@ -13,7 +13,10 @@ namespace MTConnect.Shdr /// public static class ShdrLine { + /// The SHDR field separator (pipe) used between fields within an SHDR line. public const char PipeDelimiter = '|'; + + /// The SHDR line terminator (CR LF) appended to every line written to the adapter socket. public const string LineTerminator = "\r\n"; private const string _emptySingleEntryPattern = @"([^=\s]+)\={0,1}$"; diff --git a/libraries/MTConnect.NET-SHDR/Shdr/ShdrMessage.cs b/libraries/MTConnect.NET-SHDR/Shdr/ShdrMessage.cs index a462f399f..74c46518f 100644 --- a/libraries/MTConnect.NET-SHDR/Shdr/ShdrMessage.cs +++ b/libraries/MTConnect.NET-SHDR/Shdr/ShdrMessage.cs @@ -27,14 +27,17 @@ public string NativeCode } + /// Creates an empty MESSAGE-typed event for builder-style population. public ShdrMessage() { } + /// Creates a MESSAGE event scoped to a single DataItem key with no value yet set. public ShdrMessage(string dataItemKey) { DataItemKey = dataItemKey; Timestamp = 0; } + /// Creates a MESSAGE event with the supplied DataItem key and text value. public ShdrMessage(string dataItemKey, string value) { DataItemKey = dataItemKey; @@ -45,6 +48,7 @@ public ShdrMessage(string dataItemKey, string value) Timestamp = 0; } + /// Creates a MESSAGE event with the supplied DataItem key, text value, and native code. public ShdrMessage(string dataItemKey, string value, string nativeCode) { DataItemKey = dataItemKey; @@ -55,6 +59,7 @@ public ShdrMessage(string dataItemKey, string value, string nativeCode) Timestamp = 0; } + /// Creates a MESSAGE event with an explicit Unix-time (milliseconds since epoch). public ShdrMessage(string dataItemKey, string value, long timestamp) { DataItemKey = dataItemKey; @@ -65,6 +70,7 @@ public ShdrMessage(string dataItemKey, string value, long timestamp) Timestamp = timestamp; } + /// Creates a MESSAGE event with native code and an explicit Unix-time . public ShdrMessage(string dataItemKey, string value, string nativeCode, long timestamp) { DataItemKey = dataItemKey; @@ -75,6 +81,7 @@ public ShdrMessage(string dataItemKey, string value, string nativeCode, long tim Timestamp = timestamp; } + /// Creates a MESSAGE event with an explicit ; converted to Unix UTC time during construction. public ShdrMessage(string dataItemKey, string value, DateTime timestamp) { DataItemKey = dataItemKey; @@ -85,6 +92,7 @@ public ShdrMessage(string dataItemKey, string value, DateTime timestamp) Timestamp = timestamp.ToUnixUtcTime(); } + /// Creates a MESSAGE event with native code and an explicit ; converted to Unix UTC time during construction. public ShdrMessage(string dataItemKey, string value, string nativeCode, DateTime timestamp) { DataItemKey = dataItemKey; @@ -95,6 +103,7 @@ public ShdrMessage(string dataItemKey, string value, string nativeCode, DateTime Timestamp = timestamp.ToUnixUtcTime(); } + /// Clones the supplied into an SHDR-flavoured MESSAGE event. public ShdrMessage(IObservationInput observation) { if (observation != null) diff --git a/libraries/MTConnect.NET-SHDR/Shdr/ShdrObservation.cs b/libraries/MTConnect.NET-SHDR/Shdr/ShdrObservation.cs index 274adb24b..3b7de0c46 100644 --- a/libraries/MTConnect.NET-SHDR/Shdr/ShdrObservation.cs +++ b/libraries/MTConnect.NET-SHDR/Shdr/ShdrObservation.cs @@ -1,4 +1,4 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. using MTConnect.Input; @@ -7,8 +7,20 @@ namespace MTConnect.Shdr { + /// + /// Helper that classifies an inbound observation by inspecting its value-key shape so the + /// SHDR adapter knows which line format to emit (or which parser to apply). The + /// classification is driven by the well-known markers: + /// Level implies a Condition, NativeCode implies a Message, and the + /// data-set/table/time-series predicates identify those payload shapes. + /// public static class ShdrObservation { + /// + /// Returns the that matches the value-key shape of + /// . Defaults to + /// when no specialised key is found. + /// public static ShdrObservationType GetObservationType(IObservationInput observation) { if (observation != null && observation.Values != null) @@ -17,7 +29,7 @@ public static ShdrObservationType GetObservationType(IObservationInput observati if (observation.Values.Any(o => o.Key == ValueKeys.NativeCode)) return ShdrObservationType.Message; if (observation.Values.Any(o => ValueKeys.IsDataSetKey(o.Key))) return ShdrObservationType.DataSet; if (observation.Values.Any(o => ValueKeys.IsTableKey(o.Key))) return ShdrObservationType.Table; - if (observation.Values.Any(o => ValueKeys.IsTimeSeriesKey(o.Key))) return ShdrObservationType.TimeSeries; + if (observation.Values.Any(o => ValueKeys.IsTimeSeriesKey(o.Key))) return ShdrObservationType.TimeSeries; } return ShdrObservationType.DataItem; diff --git a/libraries/MTConnect.NET-SHDR/Shdr/ShdrObservationType.cs b/libraries/MTConnect.NET-SHDR/Shdr/ShdrObservationType.cs index 56b1b1b0c..6c949fb0e 100644 --- a/libraries/MTConnect.NET-SHDR/Shdr/ShdrObservationType.cs +++ b/libraries/MTConnect.NET-SHDR/Shdr/ShdrObservationType.cs @@ -1,15 +1,32 @@ -// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. // TrakHound Inc. licenses this file to you under the MIT license. namespace MTConnect.Shdr { + /// + /// Classifies the kind of MTConnect observation carried by an inbound SHDR line. The SHDR + /// parser inspects the matching DataItem and tags each line with one of these values so the + /// agent can route it to the right observation type (single value, condition, message, + /// data set, table, or time series). + /// public enum ShdrObservationType { + /// A single Sample or Event observation (one DataItem id, one value). DataItem, + + /// A Condition observation with severity, native code, native severity, qualifier, and message fields. Condition, + + /// A Message DataItem observation that carries a native code in addition to the text value. Message, + + /// A DataSet observation made up of key/value entries. DataSet, + + /// A Table observation made up of rows with cell key/value pairs. Table, + + /// A TimeSeries observation whose payload is a vector of floating-point samples. TimeSeries } } diff --git a/libraries/MTConnect.NET-SHDR/Shdr/ShdrTable.cs b/libraries/MTConnect.NET-SHDR/Shdr/ShdrTable.cs index db5a8718e..92fa26e40 100644 --- a/libraries/MTConnect.NET-SHDR/Shdr/ShdrTable.cs +++ b/libraries/MTConnect.NET-SHDR/Shdr/ShdrTable.cs @@ -25,19 +25,23 @@ public class ShdrTable : TableObservationInput internal bool IsSent { get; set; } + /// Creates an empty SHDR table observation for builder-style population. public ShdrTable() { } + /// Creates an SHDR table observation scoped to a single DataItem key (no rows set). public ShdrTable(string dataItemKey) { DataItemKey = dataItemKey; } + /// Creates an SHDR table observation with the supplied DataItem key and table rows. public ShdrTable(string dataItemKey, IEnumerable entries) { DataItemKey = dataItemKey; Entries = entries; } + /// Creates an SHDR table observation with an explicit Unix-time (milliseconds since epoch). public ShdrTable(string dataItemKey, IEnumerable entries, long timestamp) { DataItemKey = dataItemKey; @@ -45,6 +49,7 @@ public ShdrTable(string dataItemKey, IEnumerable entries, long time Timestamp = timestamp; } + /// Creates an SHDR table observation with an explicit ; converted to Unix time during construction. public ShdrTable(string dataItemKey, IEnumerable entries, DateTime timestamp) { DataItemKey = dataItemKey; @@ -52,6 +57,7 @@ public ShdrTable(string dataItemKey, IEnumerable entries, DateTime Timestamp = timestamp.ToUnixTime(); } + /// Clones the supplied into an SHDR-flavoured observation. public ShdrTable(TableObservationInput tableObservation) { if (tableObservation != null) diff --git a/libraries/MTConnect.NET-SHDR/Shdr/ShdrTableCell.cs b/libraries/MTConnect.NET-SHDR/Shdr/ShdrTableCell.cs index b5c74de95..adbdd2cb8 100644 --- a/libraries/MTConnect.NET-SHDR/Shdr/ShdrTableCell.cs +++ b/libraries/MTConnect.NET-SHDR/Shdr/ShdrTableCell.cs @@ -6,16 +6,23 @@ namespace MTConnect.Shdr { + /// + /// SHDR-flavoured that adds round-tripping to and from the + /// key=value token form used inside SHDR table-row segments. + /// public class ShdrTableCell : TableCell { + /// Creates an empty cell for serialiser-driven construction. public ShdrTableCell() { } + /// Creates a cell with an explicit key and value; is rendered via . public ShdrTableCell(string key, object value) { Key = key; Value = value?.ToString(); } + /// Clones the supplied into a new SHDR-flavoured cell. public ShdrTableCell(ITableCell cell) { if (cell != null) @@ -26,6 +33,7 @@ public ShdrTableCell(ITableCell cell) } + /// Serialises the cell to its SHDR key=value textual form; returns the empty string when is empty. public override string ToString() { if (!string.IsNullOrEmpty(Key)) @@ -36,6 +44,7 @@ public override string ToString() return ""; } + /// Parses a single SHDR key=value segment back into a cell; returns null when is empty or does not match the expected pattern. public static ShdrTableCell FromString(string segment) { if (!string.IsNullOrEmpty(segment)) diff --git a/libraries/MTConnect.NET-SHDR/Shdr/ShdrTableEntry.cs b/libraries/MTConnect.NET-SHDR/Shdr/ShdrTableEntry.cs index 0d5c7869a..1e0562c3b 100644 --- a/libraries/MTConnect.NET-SHDR/Shdr/ShdrTableEntry.cs +++ b/libraries/MTConnect.NET-SHDR/Shdr/ShdrTableEntry.cs @@ -7,25 +7,36 @@ namespace MTConnect.Shdr { + /// + /// SHDR-flavoured that round-trips with the SHDR row syntax + /// rowKey={cell1=v1 cell2=v2 ...}; a removed row is encoded as rowKey= with an + /// empty value. The extra flag lets the adapter de-duplicate rows that + /// have already been transmitted in this update cycle. + /// public class ShdrTableEntry : TableEntry { + /// Adapter-local flag set once the entry has been written to the SHDR socket; used to suppress duplicate transmissions. public bool IsSent { get; set; } + /// Creates an empty entry for serialiser-driven construction. public ShdrTableEntry() { } + /// Creates a populated entry with a row key and the ordered list of cells. public ShdrTableEntry(string key, IEnumerable cells) { Key = key; Cells = cells; } + /// Creates a tombstone entry that records the removal of the row identified by . public ShdrTableEntry(string key, bool removed) { Key = key; Removed = removed; } + /// Clones the supplied into a new SHDR-flavoured entry. public ShdrTableEntry(ITableEntry entry) { if (entry != null) @@ -36,6 +47,7 @@ public ShdrTableEntry(ITableEntry entry) } } + /// Serialises the entry to its SHDR rowKey={cells} textual form (or rowKey= when removed); returns the empty string when is empty. public override string ToString() { if (!string.IsNullOrEmpty(Key)) @@ -64,6 +76,7 @@ private static string PrintCells(IEnumerable cells) return ""; } + /// Parses a single SHDR rowKey={cells} segment back into an entry; returns null when is empty or does not match the expected pattern. public static ShdrTableEntry FromString(string segment) { if (!string.IsNullOrEmpty(segment)) diff --git a/libraries/MTConnect.NET-SHDR/Shdr/ShdrTimeSeries.cs b/libraries/MTConnect.NET-SHDR/Shdr/ShdrTimeSeries.cs index c1fd22e08..dc35af3bd 100644 --- a/libraries/MTConnect.NET-SHDR/Shdr/ShdrTimeSeries.cs +++ b/libraries/MTConnect.NET-SHDR/Shdr/ShdrTimeSeries.cs @@ -24,8 +24,10 @@ public class ShdrTimeSeries : TimeSeriesObservationInput internal bool IsSent { get; set; } + /// Creates an empty SHDR time-series observation for builder-style population. public ShdrTimeSeries() { } + /// Creates an SHDR time-series observation with a DataItem key, sample vector, and sample rate (in Hz). public ShdrTimeSeries(string dataItemKey, IEnumerable samples, double sampleRate) { DataItemKey = dataItemKey; @@ -33,6 +35,7 @@ public ShdrTimeSeries(string dataItemKey, IEnumerable samples, double sa SampleRate = sampleRate; } + /// Creates an SHDR time-series observation with an explicit Unix-time (milliseconds since epoch). public ShdrTimeSeries(string dataItemKey, IEnumerable samples, double sampleRate, long timestamp) { DataItemKey = dataItemKey; @@ -41,6 +44,7 @@ public ShdrTimeSeries(string dataItemKey, IEnumerable samples, double sa Timestamp = timestamp; } + /// Creates an SHDR time-series observation with an explicit ; converted to Unix time during construction. public ShdrTimeSeries(string dataItemKey, IEnumerable samples, double sampleRate, DateTime timestamp) { DataItemKey = dataItemKey; @@ -49,6 +53,7 @@ public ShdrTimeSeries(string dataItemKey, IEnumerable samples, double sa Timestamp = timestamp.ToUnixTime(); } + /// Clones the supplied into an SHDR-flavoured observation. public ShdrTimeSeries(TimeSeriesObservationInput timeSeriesObservation) { if (timeSeriesObservation != null) diff --git a/libraries/MTConnect.NET-Services/MTConnectAdapterService.cs b/libraries/MTConnect.NET-Services/MTConnectAdapterService.cs index 05d546989..a63c8a9ca 100644 --- a/libraries/MTConnect.NET-Services/MTConnectAdapterService.cs +++ b/libraries/MTConnect.NET-Services/MTConnectAdapterService.cs @@ -25,15 +25,32 @@ public abstract class MTConnectAdapterService : ServiceBase private bool _serviceStart = DefaultServiceStart; + /// + /// Raised when the service emits an informational log message. + /// public EventHandler LogInformationReceived { get; set; } + /// + /// Raised when the service emits a warning log message. + /// public EventHandler LogWarningReceived { get; set; } + /// + /// Raised when the service emits an error log message. + /// public EventHandler LogErrorReceived { get; set; } + /// + /// Initializes the Windows Service wrapper, optionally suffixing the service name with a label to allow multiple adapter instances. + /// + /// An optional suffix appended to the service name to distinguish multiple adapters. + /// The Windows Service name; defaults to the standard adapter service name when empty. + /// The Windows Service display name; defaults to the standard name when empty. + /// The Windows Service description; defaults to the standard description when empty. + /// Whether the service starts automatically after installation. public MTConnectAdapterService(string label = null, string name = null, string displayName = null, string description = null, bool autoStart = true) - { + { _serviceName = !string.IsNullOrEmpty(name) ? name : DefaultServiceName; if (!string.IsNullOrEmpty(label)) _serviceName += "-" + label; _serviceDisplayName = !string.IsNullOrEmpty(displayName) ? displayName : DefaultServiceDisplayName; @@ -42,6 +59,10 @@ public MTConnectAdapterService(string label = null, string name = null, string d } + /// + /// Starts the adapter when the Windows Service starts, reading the configuration-file path from the service arguments. + /// + /// The service start arguments. protected override void OnStart(string[] args) { // Configuration File Path @@ -60,6 +81,9 @@ protected override void OnStart(string[] args) base.OnStart(args); } + /// + /// Stops the adapter when the Windows Service stops. + /// protected override void OnStop() { LogInformation("MTConnectAdapterService : OnStop : Service Stopping"); @@ -70,15 +94,34 @@ protected override void OnStop() } + /// + /// Hook for derived services to start the hosted adapter. The base implementation does nothing. + /// + /// The path to the adapter configuration file, or null for the default. protected virtual void StartAdapter(string configurationPath) { } + /// + /// Hook for derived services to stop the hosted adapter. The base implementation does nothing. + /// protected virtual void StopAdapter() { } + /// + /// Hook for derived services to handle an informational log message. The base implementation does nothing. + /// + /// The log message. protected virtual void OnLogInformation(string message) { } + /// + /// Hook for derived services to handle a warning log message. The base implementation does nothing. + /// + /// The log message. protected virtual void OnLogWarning(string message) { } + /// + /// Hook for derived services to handle an error log message. The base implementation does nothing. + /// + /// The log message. protected virtual void OnLogError(string message) { } @@ -101,21 +144,34 @@ private void LogError(string message) } + /// + /// Installs the adapter as a Windows Service when running on a compatible Windows platform. + /// + /// The path to the adapter configuration file, or null for the default. public void InstallService(string configurationPath = null) { if (WindowsService.IsCompatible()) WindowsInstall(configurationPath); } + /// + /// Removes the previously installed Windows Service when running on a compatible Windows platform. + /// public void RemoveService() { if (WindowsService.IsCompatible()) WindowsRemove(); } + /// + /// Starts the installed Windows Service when running on a compatible Windows platform. + /// public void StartService() { if (WindowsService.IsCompatible()) WindowsStart(); } + /// + /// Stops the running Windows Service when running on a compatible Windows platform. + /// public void StopService() { if (WindowsService.IsCompatible()) WindowsStop(); @@ -124,6 +180,10 @@ public void StopService() #region "Windows" + /// + /// Registers the adapter with the Windows Service Control Manager using the configured service identity. + /// + /// The path to the adapter configuration file, or null for the default. public void WindowsInstall(string configurationPath = null) { if (WindowsService.IsUserAdministrator()) @@ -163,6 +223,9 @@ public void WindowsInstall(string configurationPath = null) } } + /// + /// Unregisters the adapter's Windows Service from the Service Control Manager. + /// public void WindowsRemove() { if (WindowsService.IsUserAdministrator()) @@ -190,6 +253,9 @@ public void WindowsRemove() } } + /// + /// Starts the adapter's installed Windows Service through the Service Control Manager. + /// public void WindowsStart() { if (WindowsService.IsUserAdministrator()) @@ -217,6 +283,9 @@ public void WindowsStart() } } + /// + /// Stops the adapter's running Windows Service through the Service Control Manager. + /// public void WindowsStop() { if (WindowsService.IsUserAdministrator()) diff --git a/libraries/MTConnect.NET-Services/MTConnectAgentService.cs b/libraries/MTConnect.NET-Services/MTConnectAgentService.cs index a536879c5..e9aa6a4e7 100644 --- a/libraries/MTConnect.NET-Services/MTConnectAgentService.cs +++ b/libraries/MTConnect.NET-Services/MTConnectAgentService.cs @@ -25,15 +25,31 @@ public abstract class MTConnectAgentService : ServiceBase private bool _serviceStart = DefaultServiceStart; + /// + /// Raised when the service emits an informational log message. + /// public EventHandler LogInformationReceived { get; set; } + /// + /// Raised when the service emits a warning log message. + /// public EventHandler LogWarningReceived { get; set; } + /// + /// Raised when the service emits an error log message. + /// public EventHandler LogErrorReceived { get; set; } + /// + /// Initializes the Windows Service wrapper with optional name, display name, description, and auto-start setting. + /// + /// The Windows Service name; defaults to the standard agent service name when empty. + /// The Windows Service display name; defaults to the standard name when empty. + /// The Windows Service description; defaults to the standard description when empty. + /// Whether the service starts automatically after installation. public MTConnectAgentService(string name = null, string displayName = null, string description = null, bool autoStart = true) - { + { _serviceName = !string.IsNullOrEmpty(name) ? name : DefaultServiceName; _serviceDisplayName = !string.IsNullOrEmpty(displayName) ? displayName : DefaultServiceDisplayName; _serviceDescription = !string.IsNullOrEmpty(description) ? description : DefaultServiceDescription; @@ -41,6 +57,10 @@ public MTConnectAgentService(string name = null, string displayName = null, stri } + /// + /// Starts the agent when the Windows Service starts, reading the configuration-file path from the command line. + /// + /// The service start arguments. protected override void OnStart(string[] args) { // Read Command Line Args manually (they are not passed in the args variable) @@ -64,6 +84,9 @@ protected override void OnStart(string[] args) base.OnStart(args); } + /// + /// Stops the agent when the Windows Service stops. + /// protected override void OnStop() { LogInformation("MTConnectAgentService : OnStop : Service Stopping"); @@ -74,15 +97,34 @@ protected override void OnStop() } + /// + /// Hook for derived services to start the hosted agent. The base implementation does nothing. + /// + /// The path to the agent configuration file, or null for the default. protected virtual void StartAgent(string configurationPath) { } + /// + /// Hook for derived services to stop the hosted agent. The base implementation does nothing. + /// protected virtual void StopAgent() { } + /// + /// Hook for derived services to handle an informational log message. The base implementation does nothing. + /// + /// The log message. protected virtual void OnLogInformation(string message) { } + /// + /// Hook for derived services to handle a warning log message. The base implementation does nothing. + /// + /// The log message. protected virtual void OnLogWarning(string message) { } + /// + /// Hook for derived services to handle an error log message. The base implementation does nothing. + /// + /// The log message. protected virtual void OnLogError(string message) { } @@ -105,21 +147,34 @@ private void LogError(string message) } + /// + /// Installs the agent as a Windows Service when running on a compatible Windows platform. + /// + /// The path to the agent configuration file, or null for the default. public void InstallService(string configurationPath = null) { if (WindowsService.IsCompatible()) WindowsInstall(configurationPath); } + /// + /// Removes the previously installed Windows Service when running on a compatible Windows platform. + /// public void RemoveService() { if (WindowsService.IsCompatible()) WindowsRemove(); } + /// + /// Starts the installed Windows Service when running on a compatible Windows platform. + /// public void StartService() { if (WindowsService.IsCompatible()) WindowsStart(); } + /// + /// Stops the running Windows Service when running on a compatible Windows platform. + /// public void StopService() { if (WindowsService.IsCompatible()) WindowsStop(); @@ -128,6 +183,10 @@ public void StopService() #region "Windows" + /// + /// Registers the agent with the Windows Service Control Manager using the configured service identity. + /// + /// The path to the agent configuration file, or null for the default. public void WindowsInstall(string configurationPath = null) { if (WindowsService.IsUserAdministrator()) @@ -179,6 +238,9 @@ public void WindowsInstall(string configurationPath = null) } } + /// + /// Unregisters the agent's Windows Service from the Service Control Manager. + /// public void WindowsRemove() { if (WindowsService.IsUserAdministrator()) @@ -206,6 +268,9 @@ public void WindowsRemove() } } + /// + /// Starts the agent's installed Windows Service through the Service Control Manager. + /// public void WindowsStart() { if (WindowsService.IsUserAdministrator()) @@ -233,6 +298,9 @@ public void WindowsStart() } } + /// + /// Stops the agent's running Windows Service through the Service Control Manager. + /// public void WindowsStop() { if (WindowsService.IsUserAdministrator()) diff --git a/libraries/MTConnect.NET-SysML/Extensions/StringFunctions.cs b/libraries/MTConnect.NET-SysML/Extensions/StringFunctions.cs index a832d1a04..c976cc952 100644 --- a/libraries/MTConnect.NET-SysML/Extensions/StringFunctions.cs +++ b/libraries/MTConnect.NET-SysML/Extensions/StringFunctions.cs @@ -10,6 +10,11 @@ namespace MTConnect.SysML { + /// + /// String, hashing, and casing helpers used by the SysML importer to turn + /// raw XMI names and documentation into the identifiers and content the + /// Scriban templates emit. + /// public static class StringFunctions { private static readonly Encoding _utf8 = Encoding.UTF8; @@ -17,10 +22,10 @@ public static class StringFunctions [ThreadStatic] private static MD5 _md5; - [ThreadStatic] - private static SHA1 _sha1; + [ThreadStatic] + private static SHA1 _sha1; - [ThreadStatic] + [ThreadStatic] private static Random _random; private static MD5 MD5Algorithm @@ -35,19 +40,19 @@ private static MD5 MD5Algorithm } } - private static SHA1 SHA1Algorithm - { - get - { - if (_sha1 == null) - { - _sha1 = SHA1.Create(); - } - return _sha1; - } - } + private static SHA1 SHA1Algorithm + { + get + { + if (_sha1 == null) + { + _sha1 = SHA1.Create(); + } + return _sha1; + } + } - private static Random Random + private static Random Random { get { @@ -60,6 +65,11 @@ private static Random Random } } + /// + /// Converts the value to PascalCase by splitting it into words and + /// capitalizing the first character of each word. Returns + /// null when the input is null or empty. + /// public static string ToPascalCase(this string s) { if (!string.IsNullOrEmpty(s)) @@ -79,6 +89,11 @@ public static string ToPascalCase(this string s) return null; } + /// + /// Converts the value to title case by splitting it into words and + /// capitalizing the first character of each word. Returns + /// null when the input is null or empty. + /// public static string ToTitleCase(this string s) { if (!string.IsNullOrEmpty(s)) @@ -98,6 +113,11 @@ public static string ToTitleCase(this string s) return null; } + /// + /// Converts the value to camelCase: the first word is lowercased and + /// every subsequent word has its first character capitalized. Returns + /// null when the input is null or empty. + /// public static string ToCamelCase(this string s) { if (!string.IsNullOrEmpty(s)) @@ -118,6 +138,12 @@ public static string ToCamelCase(this string s) return null; } + /// + /// Splits the value into its constituent words. Spaces take priority, + /// then underscores, then a fall-back split on uppercase boundaries. + /// Returns a single-element array containing the input when it cannot + /// be split. + /// public static string[] SplitOnWord(this string s) { if (!string.IsNullOrEmpty(s)) @@ -146,6 +172,12 @@ public static string[] SplitOnWord(this string s) return new string[] { s }; } + /// + /// Splits the value on uppercase-character boundaries (so + /// "DataItem" becomes ["Data", "Item"]). An all-uppercase + /// value is returned as a single element; null is returned for a + /// null or empty input. + /// public static string[] SplitOnUppercase(this string s) { if (!string.IsNullOrEmpty(s)) @@ -175,6 +207,11 @@ public static string[] SplitOnUppercase(this string s) return null; } + /// + /// Returns the value with its first character uppercased and the + /// remainder lowercased. A single-character value is uppercased; + /// null is passed through. + /// public static string UppercaseFirstCharacter(this string s) { if (s == null) return null; @@ -193,6 +230,11 @@ public static string UppercaseFirstCharacter(this string s) return s.ToUpper(); } + /// + /// Returns the value with only its first character lowercased; the + /// remainder is left unchanged. A single-character value is + /// lowercased; null is passed through. + /// public static string LowercaseFirstCharacter(this string s) { if (s == null) return null; @@ -212,6 +254,13 @@ public static string LowercaseFirstCharacter(this string s) } + /// + /// Converts the value to a lowercase underscore-delimited form. Words + /// are taken from spaces or, when + /// is set, uppercase boundaries. An all-uppercase value is lowercased + /// as-is; null is returned when nothing could be produced. + /// + /// When true, splits on uppercase boundaries if the value contains no spaces. public static string ToUnderscore(this string s, bool splitOnUppercase = true) { if (!string.IsNullOrEmpty(s)) @@ -244,6 +293,13 @@ public static string ToUnderscore(this string s, bool splitOnUppercase = true) return null; } + /// + /// Converts the value to an uppercase underscore-delimited form. Words + /// are taken from spaces or, when + /// is set, uppercase boundaries. An all-uppercase value is uppercased + /// as-is; null is returned when nothing could be produced. + /// + /// When true, splits on uppercase boundaries if the value contains no spaces. public static string ToUnderscoreUpper(this string s, bool splitOnUppercase = true) { if (!string.IsNullOrEmpty(s)) @@ -276,6 +332,11 @@ public static string ToUnderscoreUpper(this string s, bool splitOnUppercase = tr return null; } + /// + /// Builds a random string of the requested length drawn from the + /// uppercase letters and digits A-Z and 0-9. + /// + /// Number of characters to generate. public static string RandomString(int length) { const string chars = "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"; @@ -283,6 +344,10 @@ public static string RandomString(int length) .Select(s => s[Random.Next(s.Length)]).ToArray()); } + /// + /// Parses the value as a , returning + /// when the value cannot be parsed. + /// public static DateTime ToDateTime(this string s) { if (DateTime.TryParse(s, out var dateTime)) @@ -293,6 +358,10 @@ public static DateTime ToDateTime(this string s) return DateTime.MinValue; } + /// + /// Computes the MD5 hash of the UTF-8 encoded value and returns it as + /// a lowercase hexadecimal string, or null on failure. + /// public static string ToMD5Hash(this string s) { try @@ -305,6 +374,11 @@ public static string ToMD5Hash(this string s) return null; } + /// + /// Computes the MD5 hash of the byte buffer and returns it as a + /// lowercase hexadecimal string, or null when the input is null + /// or hashing fails. + /// public static string ToMD5Hash(this byte[] bytes) { if (bytes != null) @@ -320,6 +394,10 @@ public static string ToMD5Hash(this byte[] bytes) return null; } + /// + /// Formats already-computed hash bytes as a lowercase hexadecimal + /// string, or null when the input is null. + /// public static string ToMD5HashString(this byte[] hashBytes) { if (hashBytes != null) @@ -334,6 +412,10 @@ public static string ToMD5HashString(this byte[] hashBytes) return null; } + /// + /// Computes the raw MD5 hash bytes of the UTF-8 encoded value, or + /// null on failure. + /// public static byte[] ToMD5HashBytes(this string s) { try @@ -345,6 +427,10 @@ public static byte[] ToMD5HashBytes(this string s) return null; } + /// + /// Computes the raw MD5 hash bytes of the byte buffer, or null + /// when the input is null or hashing fails. + /// public static byte[] ToMD5HashBytes(this byte[] bytes) { if (bytes != null) @@ -358,6 +444,11 @@ public static byte[] ToMD5HashBytes(this byte[] bytes) return null; } + /// + /// Computes a single MD5 digest over a sequence of lines by hashing + /// each line and folding it into the running hash. Returns null + /// for a null or empty array. + /// public static string ToMD5Hash(string[] lines) { if (lines != null && lines.Length > 0) @@ -378,6 +469,11 @@ public static string ToMD5Hash(string[] lines) return null; } + /// + /// Folds a sequence of byte buffers into a single MD5 hash by + /// concatenating and re-hashing pairwise. Returns null for a + /// null or empty array. + /// public static byte[] ToMD5HashBytes(byte[][] hashBytes) { if (hashBytes != null && hashBytes.Length > 0) @@ -406,120 +502,155 @@ public static byte[] ToMD5HashBytes(byte[][] hashBytes) } - public static string ToSHA1Hash(this string s) - { - try - { - var hash = SHA1Algorithm.ComputeHash(_utf8.GetBytes(s)); - return string.Concat(hash.Select(b => b.ToString("x2"))); - } - catch { } - - return null; - } - - public static string ToSHA1Hash(this byte[] bytes) - { - if (bytes != null) - { - try - { - var hash = SHA1Algorithm.ComputeHash(bytes); - return string.Concat(hash.Select(b => b.ToString("x2"))); - } - catch { } - } - - return null; - } - - public static string ToSHA1HashString(this byte[] hashBytes) - { - if (hashBytes != null) - { - try - { - return string.Concat(hashBytes.Select(b => b.ToString("x2"))); - } - catch { } - } - - return null; - } - - public static byte[] ToSHA1HashBytes(this string s) - { - try - { - return SHA1Algorithm.ComputeHash(_utf8.GetBytes(s)); - } - catch { } - - return null; - } - - public static byte[] ToSHA1HashBytes(this byte[] bytes) - { - if (bytes != null) - { - try - { - return SHA1Algorithm.ComputeHash(bytes); - } - catch { } - } - return null; - } - - public static string ToSHA1Hash(string[] lines) - { - if (lines != null && lines.Length > 0) - { - var x1 = lines[0]; - var h = x1.ToSHA1Hash(); - - for (int i = 1; i < lines.Length; i++) - { - x1 = lines[i].ToSHA1Hash(); - x1 = h + x1; - h = x1.ToSHA1Hash(); - } - - return h; - } - - return null; - } - - public static byte[] ToSHA1HashBytes(byte[][] hashBytes) - { - if (hashBytes != null && hashBytes.Length > 0) - { - var x1 = hashBytes[0]; - var x2 = x1; - byte[] a1; - - for (int i = 1; i < hashBytes.Length; i++) - { - x2 = hashBytes[i]; - if (x2 != null) - { - a1 = new byte[x1.Length + x2.Length]; - Array.Copy(x1, 0, a1, 0, x1.Length); - Array.Copy(x2, 0, a1, x1.Length, x2.Length); - - x1 = a1.ToSHA1HashBytes(); - } - } - - return x2; - } - - return null; - } - - - public static string ToFileSize(this long byteCount) + /// + /// Computes the SHA-1 hash of the UTF-8 encoded value and returns it as + /// a lowercase hexadecimal string, or null on failure. + /// + public static string ToSHA1Hash(this string s) + { + try + { + var hash = SHA1Algorithm.ComputeHash(_utf8.GetBytes(s)); + return string.Concat(hash.Select(b => b.ToString("x2"))); + } + catch { } + + return null; + } + + /// + /// Computes the SHA-1 hash of the byte buffer and returns it as a + /// lowercase hexadecimal string, or null when the input is null + /// or hashing fails. + /// + public static string ToSHA1Hash(this byte[] bytes) + { + if (bytes != null) + { + try + { + var hash = SHA1Algorithm.ComputeHash(bytes); + return string.Concat(hash.Select(b => b.ToString("x2"))); + } + catch { } + } + + return null; + } + + /// + /// Formats already-computed SHA-1 hash bytes as a lowercase + /// hexadecimal string, or null when the input is null. + /// + public static string ToSHA1HashString(this byte[] hashBytes) + { + if (hashBytes != null) + { + try + { + return string.Concat(hashBytes.Select(b => b.ToString("x2"))); + } + catch { } + } + + return null; + } + + /// + /// Computes the raw SHA-1 hash bytes of the UTF-8 encoded value, or + /// null on failure. + /// + public static byte[] ToSHA1HashBytes(this string s) + { + try + { + return SHA1Algorithm.ComputeHash(_utf8.GetBytes(s)); + } + catch { } + + return null; + } + + /// + /// Computes the raw SHA-1 hash bytes of the byte buffer, or null + /// when the input is null or hashing fails. + /// + public static byte[] ToSHA1HashBytes(this byte[] bytes) + { + if (bytes != null) + { + try + { + return SHA1Algorithm.ComputeHash(bytes); + } + catch { } + } + return null; + } + + /// + /// Computes a single SHA-1 digest over a sequence of lines by hashing + /// each line and folding it into the running hash. Returns null + /// for a null or empty array. + /// + public static string ToSHA1Hash(string[] lines) + { + if (lines != null && lines.Length > 0) + { + var x1 = lines[0]; + var h = x1.ToSHA1Hash(); + + for (int i = 1; i < lines.Length; i++) + { + x1 = lines[i].ToSHA1Hash(); + x1 = h + x1; + h = x1.ToSHA1Hash(); + } + + return h; + } + + return null; + } + + /// + /// Folds a sequence of byte buffers into a single SHA-1 hash by + /// concatenating and re-hashing pairwise. Returns null for a + /// null or empty array. + /// + public static byte[] ToSHA1HashBytes(byte[][] hashBytes) + { + if (hashBytes != null && hashBytes.Length > 0) + { + var x1 = hashBytes[0]; + var x2 = x1; + byte[] a1; + + for (int i = 1; i < hashBytes.Length; i++) + { + x2 = hashBytes[i]; + if (x2 != null) + { + a1 = new byte[x1.Length + x2.Length]; + Array.Copy(x1, 0, a1, 0, x1.Length); + Array.Copy(x2, 0, a1, x1.Length, x2.Length); + + x1 = a1.ToSHA1HashBytes(); + } + } + + return x2; + } + + return null; + } + + + /// + /// Formats a byte count as a human-readable size string using binary + /// (1024-based) units from B up to EB. + /// + public static string ToFileSize(this long byteCount) { string[] suf = { "B", "KB", "MB", "GB", "TB", "PB", "EB" }; //Longs run out around EB if (byteCount == 0) @@ -530,6 +661,11 @@ public static string ToFileSize(this long byteCount) return (Math.Sign(byteCount) * num).ToString() + suf[place]; } + /// + /// Formats a decimal byte count as a human-readable size string by + /// truncating to a whole number of bytes and delegating to the + /// overload. + /// public static string ToFileSize(this decimal byteCount) { var x = (long)byteCount; @@ -537,6 +673,10 @@ public static string ToFileSize(this decimal byteCount) } + /// + /// Returns true when the value contains at least one matched + /// open/close HTML-style tag pair. + /// public static bool IsHtml(this string s) { if (!string.IsNullOrEmpty(s)) @@ -548,6 +688,13 @@ public static bool IsHtml(this string s) return false; } + /// + /// Parses the value into the enum type + /// case-insensitively, returning default(T) when the value is + /// null, is not an enum, or no member + /// matches. + /// + /// Enum type to parse into. public static T ConvertEnum(this string value) where T : struct { if (value != null && typeof(T).IsEnum) @@ -561,6 +708,10 @@ public static T ConvertEnum(this string value) where T : struct return default; } + /// + /// Derives a stable 64-bit hash of the text by MD5-hashing it and + /// XOR-folding the digest down to a single . + /// public static ulong GetUInt64Hash(this string text) { using (var md5 = MD5.Create()) @@ -574,6 +725,12 @@ public static ulong GetUInt64Hash(this string text) } + /// + /// Replaces standalone integers 0 through 10 in the text with their + /// English word form. Numbers outside that range and the surrounding + /// text are left unchanged; returns null for a null or empty + /// input. + /// public static string ReplaceNumbersWithWords(string text) { if (!string.IsNullOrEmpty(text)) diff --git a/libraries/MTConnect.NET-SysML/IMTConnectExportModel.cs b/libraries/MTConnect.NET-SysML/IMTConnectExportModel.cs index 397d8bebd..af2558928 100644 --- a/libraries/MTConnect.NET-SysML/IMTConnectExportModel.cs +++ b/libraries/MTConnect.NET-SysML/IMTConnectExportModel.cs @@ -1,9 +1,21 @@ namespace MTConnect.SysML { + /// + /// A parsed MTConnect model element that can be rendered into generated + /// C# by the Scriban templates. + /// public interface IMTConnectExportModel { + /// + /// The xmi:id of the source XMI element this model was parsed + /// from. + /// string UmlId { get; } + /// + /// The dotted MTConnect model identifier (for example + /// Devices.Component) used to key and resolve the element. + /// string Id { get; } } } diff --git a/libraries/MTConnect.NET-SysML/MTConnectClassModel.cs b/libraries/MTConnect.NET-SysML/MTConnectClassModel.cs index 88475c3a9..20bf905cf 100644 --- a/libraries/MTConnect.NET-SysML/MTConnectClassModel.cs +++ b/libraries/MTConnect.NET-SysML/MTConnectClassModel.cs @@ -6,16 +6,35 @@ namespace MTConnect.SysML { + /// + /// A parsed MTConnect class: its identity, inheritance (primary base plus + /// any additional generalizations rendered as marker interfaces), + /// properties, description, and valid version range. The cross-package + /// parent resolver () operates on + /// instances of this type. + /// public class MTConnectClassModel : IMTConnectExportModel { + /// public string UmlId { get; set; } + /// public string Id { get; set; } + /// + /// True when the class is emitted as abstract. + /// public bool IsAbstract { get; set; } + /// + /// The class name as emitted in the generated C#. + /// public string Name { get; set; } + /// + /// The name of the primary base class (the single C# class base), or + /// null when the class is root-level. + /// public string ParentName { get; set; } /// @@ -44,17 +63,41 @@ public class MTConnectClassModel : IMTConnectExportModel /// public List AdditionalParentUmlIds { get; set; } = new(); + /// + /// The cleaned description text emitted into the doc comment. + /// public string Description { get; set; } + /// + /// The class's properties, ordered by name. + /// public List Properties { get; set; } = new(); + /// + /// The MTConnect version this class was deprecated at, or + /// null when it is not deprecated. + /// public Version MaximumVersion { get; set; } + /// + /// The MTConnect version this class was introduced in, or + /// null when no introduction is recorded. + /// public Version MinimumVersion { get; set; } + /// + /// Creates an empty model for manual population. + /// public MTConnectClassModel() { } + /// + /// Parses a class from under model id + /// : resolves its generalizations, cleans its + /// description, and parses its properties (excluding the derived + /// made*/is*/observes* navigations), ordered by + /// name. + /// public MTConnectClassModel(XmiDocument xmiDocument, string id, UmlClass umlClass) { if (umlClass != null) @@ -164,6 +207,10 @@ private void SelectGeneralizations(XmiDocument xmiDocument, UmlClass umlClass) } } + /// + /// Adds the given properties to this class, skipping any whose name + /// already exists so an inherited property is not duplicated. + /// public void AddProperties(IEnumerable properties) { if (properties != null) @@ -178,6 +225,12 @@ public void AddProperties(IEnumerable properties) } } + /// + /// Parses every class in under + /// , skipping single-valued wrapper + /// classes (see ) which are + /// collapsed into scalar value types elsewhere. + /// public static IEnumerable Parse(XmiDocument xmiDocument, string idPrefix, IEnumerable umlClasses) { var models = new List(); diff --git a/libraries/MTConnect.NET-SysML/MTConnectEnumModel.cs b/libraries/MTConnect.NET-SysML/MTConnectEnumModel.cs index 9cfb436cf..b06a8a27e 100644 --- a/libraries/MTConnect.NET-SysML/MTConnectEnumModel.cs +++ b/libraries/MTConnect.NET-SysML/MTConnectEnumModel.cs @@ -7,21 +7,46 @@ namespace MTConnect.SysML { + /// + /// A parsed enumeration: its disambiguated C# name, cleaned description, + /// and its ordered set of literal values. + /// public class MTConnectEnumModel : IMTConnectExportModel { + /// public string UmlId { get; set; } + /// public string Id { get; set; } + /// + /// The C# enum name as emitted, after + /// disambiguation. + /// public string Name { get; set; } + /// + /// The cleaned description text emitted into the doc comment. + /// public string Description { get; set; } + /// + /// The enumeration's literal members, ordered by name. + /// public List Values { get; set; } = new(); + /// + /// Creates an empty model for manual population. + /// public MTConnectEnumModel() { } + /// + /// Parses an enumeration under , applying + /// the title-case and disambiguation rules to its name and parsing + /// each literal (optionally rewritten by + /// ) in name order. + /// public MTConnectEnumModel(XmiDocument xmiDocument, string idPrefix, UmlEnumeration umlEnumeration, Func convertFunction = null) { if (umlEnumeration != null) @@ -55,6 +80,10 @@ public MTConnectEnumModel(XmiDocument xmiDocument, string idPrefix, UmlEnumerati } } + /// + /// Parses every enumeration in + /// under , returning them ordered by name. + /// public static IEnumerable Parse(XmiDocument xmiDocument, string idPrefix, IEnumerable umlEnumerations, Func convertFunction = null) { var models = new List(); diff --git a/libraries/MTConnect.NET-SysML/MTConnectEnumValueModel.cs b/libraries/MTConnect.NET-SysML/MTConnectEnumValueModel.cs index db0f91f2a..00ecbdd65 100644 --- a/libraries/MTConnect.NET-SysML/MTConnectEnumValueModel.cs +++ b/libraries/MTConnect.NET-SysML/MTConnectEnumValueModel.cs @@ -4,21 +4,46 @@ namespace MTConnect.SysML { + /// + /// A single parsed enumeration literal: its C# member name, the original + /// XMI literal value, and the cleaned description emitted as its doc + /// comment. + /// public class MTConnectEnumValueModel : IMTConnectExportModel { + /// public string UmlId { get; set; } + /// public string Id { get; set; } + /// + /// The enumeration member name as emitted in the generated C# enum. + /// public string Name { get; set; } + /// + /// The original XMI literal value the member maps to. + /// public string Value { get; set; } + /// + /// The cleaned description text emitted into the doc comment. + /// public string Description { get; set; } + /// + /// Creates an empty model for manual population. + /// public MTConnectEnumValueModel() { } + /// + /// Parses an enumeration literal under , + /// optionally rewriting its name through + /// while preserving the original + /// literal as . + /// public MTConnectEnumValueModel(string idPrefix, UmlEnumerationLiteral enumerationLiteral, Func convertFunction = null) { if (enumerationLiteral != null) diff --git a/libraries/MTConnect.NET-SysML/MTConnectModel.cs b/libraries/MTConnect.NET-SysML/MTConnectModel.cs index 9f8d95b13..d66558266 100644 --- a/libraries/MTConnect.NET-SysML/MTConnectModel.cs +++ b/libraries/MTConnect.NET-SysML/MTConnectModel.cs @@ -15,12 +15,28 @@ namespace MTConnect.SysML /// public class MTConnectModel { + /// + /// The parsed Device Information Model (devices, components, + /// compositions, data items, configurations, references). + /// public MTConnectDeviceInformationModel DeviceInformationModel { get; set; } + /// + /// The parsed Observation Information Model (condition, event, and + /// sample observation types and their result classes). + /// public MTConnectObservationInformationModel ObservationInformationModel { get; set; } + /// + /// The parsed Asset Information Model (the asset hierarchy and its + /// supporting types). + /// public MTConnectAssetInformationModel AssetInformationModel { get; set; } + /// + /// The parsed Interface Interaction Model (interface-specific + /// DataItem types). + /// public MTConnectInterfaceInformationModel IntefaceInformationModel { get; set; } diff --git a/libraries/MTConnect.NET-SysML/MTConnectPackageModel.cs b/libraries/MTConnect.NET-SysML/MTConnectPackageModel.cs index 950294ae4..17ca4ffa2 100644 --- a/libraries/MTConnect.NET-SysML/MTConnectPackageModel.cs +++ b/libraries/MTConnect.NET-SysML/MTConnectPackageModel.cs @@ -2,10 +2,20 @@ namespace MTConnect.SysML { + /// + /// A parsed MTConnect package: the classes and enumerations it + /// contributes to the generated output. + /// public class MTConnectPackageModel { + /// + /// The classes declared in this package. + /// public List Classes { get; set; } = new(); + /// + /// The enumerations declared in this package. + /// public List Enums { get; set; } = new(); } } diff --git a/libraries/MTConnect.NET-SysML/MTConnectPropertyModel.cs b/libraries/MTConnect.NET-SysML/MTConnectPropertyModel.cs index 2c496e785..f4298bd99 100644 --- a/libraries/MTConnect.NET-SysML/MTConnectPropertyModel.cs +++ b/libraries/MTConnect.NET-SysML/MTConnectPropertyModel.cs @@ -4,28 +4,67 @@ namespace MTConnect.SysML { + /// + /// A parsed class property: its emitted name and C# data type, whether + /// it is optional (nullable) or a collection, and its cleaned + /// description. + /// public class MTConnectPropertyModel : IMTConnectExportModel { + /// public string UmlId { get; set; } + /// public string Id { get; set; } + /// + /// The property name as emitted in the generated C#. + /// public string Name { get; set; } + /// + /// The cleaned description text emitted into the doc comment, + /// falling back to the description of the property's type when the + /// property itself has none. + /// public string Description { get; set; } + /// + /// The resolved C# data type of the property. + /// public string DataType { get; set; } + /// + /// The xmi:id of the property's declared type. + /// public string DataTypeUmlId { get; set; } + /// + /// True when the property is optional and must be emitted as a + /// nullable member. + /// public bool IsOptional { get; set; } + /// + /// True when the property is a collection and must be emitted as an + /// enumerable member. + /// public bool IsArray { get; set; } + /// + /// Creates an empty model for manual population. + /// public MTConnectPropertyModel() { } - public MTConnectPropertyModel(XmiDocument xmiDocument, string idPrefix, UmlProperty umlProperty) + /// + /// Parses a property from under + /// : normalizes the name (strips a + /// leading has, maps xlink:type, pluralizes + /// collections), resolves the C# data type, and cleans the + /// description. + /// + public MTConnectPropertyModel(XmiDocument xmiDocument, string idPrefix, UmlProperty umlProperty) { UmlId = umlProperty.Id; @@ -53,6 +92,12 @@ public MTConnectPropertyModel(XmiDocument xmiDocument, string idPrefix, UmlPrope } } + /// + /// Resolves the C# data type for a property: applies the + /// per-property and per-type xmi:id overrides for the cases + /// the XMI types incorrectly, then maps primitive types, value + /// classes, and enumerations, defaulting to string. + /// internal static string ParseType(XmiDocument xmiDocument, string propertyId, string typeId) { if (xmiDocument != null && propertyId != null && typeId != null) diff --git a/libraries/MTConnect.NET-SysML/MTConnectSubclassModel.cs b/libraries/MTConnect.NET-SysML/MTConnectSubclassModel.cs index d70f0832b..2c8d03eb9 100644 --- a/libraries/MTConnect.NET-SysML/MTConnectSubclassModel.cs +++ b/libraries/MTConnect.NET-SysML/MTConnectSubclassModel.cs @@ -4,21 +4,46 @@ namespace MTConnect.SysML { + /// + /// Base parsed model for a subtype/enumeration-derived element: carries + /// its identity, display name, cleaned description, and the version range + /// over which it is valid. + /// public class MTConnectSubclassModel : IMTConnectExportModel { + /// public string UmlId { get; set; } + /// public string Id { get; set; } + /// + /// The subtype's name as it appears in the generated C#. + /// public string Name { get; set; } + /// + /// The cleaned description text emitted into the doc comment. + /// public string Description { get; set; } + /// + /// The MTConnect version this subtype was deprecated at, or + /// null when it is not deprecated. + /// public Version MaximumVersion { get; set; } + /// + /// The MTConnect version this subtype was introduced in, or + /// null when no introduction is recorded. + /// public Version MinimumVersion { get; set; } + /// + /// Initializes the model from a UML class, taking its name and + /// cleaned description; a null class leaves the members unset. + /// public MTConnectSubclassModel(UmlClass umlClass) { if (umlClass != null) diff --git a/libraries/MTConnect.NET-SysML/MTConnectVersion.cs b/libraries/MTConnect.NET-SysML/MTConnectVersion.cs index 4cf994eca..0830ec0c4 100644 --- a/libraries/MTConnect.NET-SysML/MTConnectVersion.cs +++ b/libraries/MTConnect.NET-SysML/MTConnectVersion.cs @@ -4,8 +4,19 @@ namespace MTConnect.SysML { + /// + /// Maps MTConnect Standard version numbers to their generated + /// MTConnectVersions constant names and resolves the version a + /// model element was introduced in or deprecated at from the XMI profile + /// stereotypes. + /// public class MTConnectVersion { + /// + /// Returns the fully qualified MTConnectVersions.VersionXY + /// constant name for the given version, or null when the + /// version is null or outside the known v1.0-v2.7 range. + /// public static string GetVersionEnum(Version version) { if (version != null) @@ -46,6 +57,11 @@ public static string GetVersionEnum(Version version) return null; } + /// + /// Resolves the MTConnect version an element became normative in by + /// matching the element id against the XMI's normative-introduction + /// stereotypes. Returns null when no introduction is recorded. + /// public static Version LookupNormative(XmiDocument xmiDocument, string id) { if (xmiDocument != null && !string.IsNullOrEmpty(id)) @@ -68,6 +84,11 @@ public static Version LookupNormative(XmiDocument xmiDocument, string id) return null; } + /// + /// Resolves the MTConnect version an element was deprecated at by + /// matching the element id against the XMI's deprecation stereotypes. + /// Returns null when the element is not deprecated. + /// public static Version LookupDeprecated(XmiDocument xmiDocument, string id) { if (xmiDocument != null && !string.IsNullOrEmpty(id)) diff --git a/libraries/MTConnect.NET-SysML/ModelHelper.cs b/libraries/MTConnect.NET-SysML/ModelHelper.cs index 06211dedc..aba16f1a3 100644 --- a/libraries/MTConnect.NET-SysML/ModelHelper.cs +++ b/libraries/MTConnect.NET-SysML/ModelHelper.cs @@ -7,6 +7,12 @@ namespace MTConnect.SysML { + /// + /// Lookup and normalization helpers over a parsed XMI document: resolves + /// classes, enumerations, and their descriptions by id, cleans raw XMI + /// documentation into C# doc-comment text, and applies the + /// model-specific name/array/optional rules the renderers depend on. + /// public static class ModelHelper { private static Dictionary _packages; @@ -14,6 +20,12 @@ public static class ModelHelper private static Dictionary _enumerations; + /// + /// Returns the UML class with the given xmi:id, lazily + /// indexing the document's packages and classes on first use. + /// Returns null when the document or id is missing or no class + /// matches. + /// public static UmlClass GetClass(XmiDocument xmiDocument, string id) { if (xmiDocument != null && !string.IsNullOrEmpty(id)) @@ -27,6 +39,10 @@ public static UmlClass GetClass(XmiDocument xmiDocument, string id) return null; } + /// + /// Returns the name of the UML class with the given xmi:id, or + /// null when no class matches. + /// public static string GetClassName(XmiDocument xmiDocument, string id) { if (xmiDocument != null && !string.IsNullOrEmpty(id)) @@ -41,6 +57,12 @@ public static string GetClassName(XmiDocument xmiDocument, string id) return null; } + /// + /// Returns the cleaned documentation text of the UML class with the + /// given xmi:id (its first comment run through + /// ), or null when no class or + /// comment is present. + /// public static string GetClassDescription(XmiDocument xmiDocument, string id) { if (xmiDocument != null && !string.IsNullOrEmpty(id)) @@ -59,6 +81,11 @@ public static string GetClassDescription(XmiDocument xmiDocument, string id) return null; } + /// + /// Returns the UML enumeration with the given xmi:id, lazily + /// indexing the document's enumerations on first use. Returns + /// null when none matches. + /// public static UmlEnumeration GetEnum(XmiDocument xmiDocument, string typeId) { if (xmiDocument != null && !string.IsNullOrEmpty(typeId)) @@ -72,6 +99,11 @@ public static UmlEnumeration GetEnum(XmiDocument xmiDocument, string typeId) return null; } + /// + /// Returns the C# enum name for the enumeration with the given + /// xmi:id, applying the + /// disambiguation rules. Returns null when none matches. + /// public static string GetEnumName(XmiDocument xmiDocument, string typeId) { if (xmiDocument != null && !string.IsNullOrEmpty(typeId)) @@ -89,6 +121,11 @@ public static string GetEnumName(XmiDocument xmiDocument, string typeId) return null; } + /// + /// Returns the literal name of the value + /// within the enumeration , or null + /// when the enumeration or value is not found. + /// public static string GetEnumValue(XmiDocument xmiDocument, string typeId, string valueId) { if (xmiDocument != null && !string.IsNullOrEmpty(typeId) && !string.IsNullOrEmpty(valueId)) @@ -110,6 +147,12 @@ public static string GetEnumValue(XmiDocument xmiDocument, string typeId, string return null; } + /// + /// Disambiguates a raw XMI enumeration name into the project's C# + /// enum name (for example CategoryEnum becomes + /// DataItemCategoryEnum); names without a mapping are returned + /// unchanged. + /// public static string ConvertEnumName(string name) { if (name != null) @@ -132,6 +175,10 @@ public static string ConvertEnumName(string name) return name; } + /// + /// Strips a trailing Enum suffix from the name when present; + /// returns the name unchanged otherwise. + /// public static string RemoveEnumSuffix(string name) { if (name != null) @@ -160,6 +207,10 @@ private static IEnumerable GetAllPackages(UmlModel umlModel) return packages; } + /// + /// Returns the package and all of its descendant packages, flattened + /// depth-first. + /// public static IEnumerable GetPackages(UmlPackage package) { var packages = new List(); @@ -191,6 +242,9 @@ private static IEnumerable GetPackages(UmlProfile profile) return packages; } + /// + /// Returns every UML class declared directly in the given packages. + /// public static IEnumerable GetClasses(IEnumerable packages) { var classes = new List(); @@ -279,6 +333,13 @@ private static void InitializeEnumerations() } + /// + /// Cleans raw XMI documentation into doc-comment-ready text: + /// unwraps {{macro(label)}} and scope::name references + /// to their readable form, strips newlines, normalizes quotes, + /// capitalizes the first word, and restores MTConnect casing. + /// Returns null for null or empty input. + /// public static string ProcessDescription(string text) { if (!string.IsNullOrEmpty(text)) @@ -363,6 +424,13 @@ private static string UppercaseFirstCharacter(string s) } + /// + /// Returns true when the property identified by + /// is a collection in the MTConnect model. The set is keyed by + /// xmi:id because the XMI multiplicity alone does not reliably + /// distinguish the collection-valued associations the generated + /// classes must expose as enumerables. + /// public static bool IsArray(XmiDocument xmiDocument, string id) { switch (id) @@ -419,6 +487,12 @@ public static bool IsArray(XmiDocument xmiDocument, string id) return false; } + /// + /// Pluralizes a collection property's element name for its C# + /// accessor, honoring the irregular cases (ToolLife, + /// ItemLife, FileProperty) and otherwise appending an + /// s when not already present. + /// public static string ConvertArrayName(string name) { if (name != null) @@ -431,13 +505,19 @@ public static string ConvertArrayName(string name) default: if (!name.EndsWith("s")) return name += "s"; break; - + } } return name; } + /// + /// Returns true when the property identified by + /// is optional in the MTConnect model and must therefore be emitted + /// as a nullable C# member. Keyed by xmi:id for the same + /// reason as . + /// public static bool IsOptional(XmiDocument xmiDocument, string id) { switch (id) @@ -536,6 +616,12 @@ public static bool IsOptional(XmiDocument xmiDocument, string id) } + /// + /// Returns true when the class is a single-valued wrapper (no + /// generalization and exactly one non-derived property), which the + /// renderer collapses into a scalar value type rather than a full + /// class. Destination is explicitly excluded. + /// public static bool IsValueClass(UmlClass umlClass) { if (umlClass != null && (umlClass.Generalizations == null || umlClass.Generalizations.Length == 0)) @@ -563,6 +649,11 @@ public static bool IsValueClass(UmlClass umlClass) return false; } + /// + /// Returns the C# type of a value class's single property (see + /// ), defaulting to string when the + /// class is not a value class or no single property is found. + /// public static string GetValueType(XmiDocument xmiDocument, UmlClass umlClass) { if (umlClass != null) diff --git a/libraries/MTConnect.NET-SysML/Models/Assets/MTConnectAssetInformationModel.cs b/libraries/MTConnect.NET-SysML/Models/Assets/MTConnectAssetInformationModel.cs index 6c3469afe..cb2b5e657 100644 --- a/libraries/MTConnect.NET-SysML/Models/Assets/MTConnectAssetInformationModel.cs +++ b/libraries/MTConnect.NET-SysML/Models/Assets/MTConnectAssetInformationModel.cs @@ -5,35 +5,80 @@ namespace MTConnect.SysML.Models.Assets { + /// + /// Parses the Asset Information Model from the XMI: the Asset and + /// PhysicalAsset base classes plus the per-asset-family packages + /// (cutting tools, files, fixtures, pallets, QIF, raw materials, + /// component configuration parameters). + /// public class MTConnectAssetInformationModel { + /// + /// The parsed Asset base class. + /// public MTConnectAssetModel Asset { get; set; } + /// + /// The parsed PhysicalAsset base class. + /// public MTConnectPhysicalAssetModel PhysicalAsset { get; set; } + /// + /// The parsed Component Configuration Parameters asset classes. + /// public MTConnectPackageModel ComponentConfigurationParameters { get; set; } = new(); + /// + /// The parsed Cutting Tool asset classes, measurement classes, and + /// enumerations. + /// public MTConnectPackageModel CuttingTools { get; set; } = new(); + /// + /// The parsed File asset classes and enumerations. + /// public MTConnectPackageModel Files { get; set; } = new(); + /// + /// The parsed Fixture asset classes. + /// public MTConnectPackageModel Fixtures { get; set; } = new(); + /// + /// The parsed Pallet asset classes and measurement classes. + /// public MTConnectPackageModel Pallets { get; set; } = new(); + /// + /// The parsed QIF asset classes and enumerations. + /// public MTConnectPackageModel QIF { get; set; } = new(); + /// + /// The parsed Raw Material asset classes and enumerations. + /// public MTConnectPackageModel RawMaterials { get; set; } = new(); + /// + /// Creates an empty model for manual population. + /// public MTConnectAssetInformationModel() { } + /// + /// Parses the full asset information model from the given XMI + /// document. + /// public MTConnectAssetInformationModel(XmiDocument xmiDocument) { Parse(xmiDocument); } + /// + /// Locates the Asset Information Model package and parses the asset + /// base classes and every per-family package from it. + /// private void Parse(XmiDocument xmiDocument) { if (xmiDocument != null) @@ -62,6 +107,10 @@ private void Parse(XmiDocument xmiDocument) } + /// + /// Parses the Component Configuration Parameters package into + /// . + /// private void ParseComponentConfigurationParameters(XmiDocument xmiDocument, UmlPackage umlPackage) { var targetPackage = umlPackage.Packages.FirstOrDefault(o => o.Name == "Component Configuration Parameters"); @@ -78,6 +127,11 @@ private void ParseComponentConfigurationParameters(XmiDocument xmiDocument, UmlP } } + /// + /// Parses the Cutting Tool package into : + /// its primary classes, the rich measurement subtypes, and the + /// cutting-tool enumerations. + /// private void ParseCuttingTools(XmiDocument xmiDocument, UmlPackage umlPackage) { var cuttingTool = umlPackage.Packages.FirstOrDefault(o => o.Name == "Cutting Tool"); @@ -133,9 +187,41 @@ private void ParseCuttingTools(XmiDocument xmiDocument, UmlPackage umlPackage) CuttingTools.Enums.Add(new MTConnectEnumModel(xmiDocument, "Assets.CuttingTools", dataTypes?.Enumerations.FirstOrDefault(o => o.Name == "LocationTypeEnum"))); CuttingTools.Enums.Add(new MTConnectEnumModel(xmiDocument, "Assets.CuttingTools", dataTypes?.Enumerations.FirstOrDefault(o => o.Name == "FormatTypeEnum"))); CuttingTools.Enums.Add(new MTConnectEnumModel(xmiDocument, "Assets.CuttingTools.Measurements", dataTypes?.Enumerations.FirstOrDefault(o => o.Name == "CodeEnum"), ConvertMeasurementCode)); + + + // Emit the shared abstract `Measurement` base under + // Assets.CuttingTools as well. The SysML model declares a + // single `Measurement` class (carried under the Pallet + // Measurements package); the CuttingTool measurement + // hierarchy reuses it as the concrete base of + // `ToolingMeasurement` and the per-subtype rich measurement + // classes. Without this second emission the generated + // `ToolingMeasurement.g.cs` (`: Measurement`) has no + // `MTConnect.Assets.CuttingTools.Measurement` base to compile + // against, and the hand-authored + // `Assets/CuttingTools/Measurement.cs` partial has no + // generated partner supplying the `IMeasurement` members. + // Mirrors the abstract-`Measurement` handling in + // ParsePallets; the renderer's `Assets.CuttingTools.Measurement` + // case re-emits it as a concrete partial. + var palletPackage = umlPackage.Packages.FirstOrDefault(o => o.Name == "Pallet"); + var palletMeasurements = palletPackage?.Packages.FirstOrDefault(o => o.Name == "Measurements"); + var sharedMeasurement = palletMeasurements?.Classes.Where(o => o.Name == "Measurement"); + if (sharedMeasurement != null) + { + var baseMeasurementClasses = MTConnectClassModel.Parse(xmiDocument, "Assets.CuttingTools", sharedMeasurement); + if (baseMeasurementClasses != null) + { + CuttingTools.Classes.AddRange(baseMeasurementClasses); + } + } } } + /// + /// Parses the Files package into along with its + /// application/file-state enumerations. + /// private void ParseFiles(XmiDocument xmiDocument, UmlPackage umlPackage) { var targetPackage = umlPackage.Packages.FirstOrDefault(o => o.Name == "Files"); @@ -159,6 +245,9 @@ private void ParseFiles(XmiDocument xmiDocument, UmlPackage umlPackage) } } + /// + /// Parses the Fixture package into . + /// private void ParseFixtures(XmiDocument xmiDocument, UmlPackage umlPackage) { var targetPackage = umlPackage.Packages.FirstOrDefault(o => o.Name == "Fixture"); @@ -174,6 +263,12 @@ private void ParseFixtures(XmiDocument xmiDocument, UmlPackage umlPackage) } } + /// + /// Parses the Pallet package into : its + /// primary classes, the concrete measurement subclasses through the + /// rich measurement pipeline, and the abstract Measurement + /// base as a partial class. + /// private void ParsePallets(XmiDocument xmiDocument, UmlPackage umlPackage) { var targetPackage = umlPackage.Packages.FirstOrDefault(o => o.Name == "Pallet"); @@ -243,6 +338,10 @@ private void ParsePallets(XmiDocument xmiDocument, UmlPackage umlPackage) } } + /// + /// Parses the QIF package into along with its + /// document-type enumeration. + /// private void ParseQIF(XmiDocument xmiDocument, UmlPackage umlPackage) { var targetPackage = umlPackage.Packages.FirstOrDefault(o => o.Name == "QIF"); @@ -264,6 +363,10 @@ private void ParseQIF(XmiDocument xmiDocument, UmlPackage umlPackage) } } + /// + /// Parses the Raw Material package into + /// along with its form enumeration. + /// private void ParseRawMaterials(XmiDocument xmiDocument, UmlPackage umlPackage) { var targetPackage = umlPackage.Packages.FirstOrDefault(o => o.Name == "Raw Material"); @@ -286,6 +389,10 @@ private void ParseRawMaterials(XmiDocument xmiDocument, UmlPackage umlPackage) } + /// + /// Maps the cutting-tool measurement code N/A to the + /// C#-identifier-safe N_A; all other codes pass through. + /// private static string ConvertMeasurementCode(string name) { if (name == "N/A") return "N_A"; diff --git a/libraries/MTConnect.NET-SysML/Models/Assets/MTConnectAssetModel.cs b/libraries/MTConnect.NET-SysML/Models/Assets/MTConnectAssetModel.cs index 752862450..fe8d35bec 100644 --- a/libraries/MTConnect.NET-SysML/Models/Assets/MTConnectAssetModel.cs +++ b/libraries/MTConnect.NET-SysML/Models/Assets/MTConnectAssetModel.cs @@ -3,10 +3,21 @@ namespace MTConnect.SysML.Models.Assets { + /// + /// Parsed model for the MTConnect Assets.Asset element, emitted as + /// a concrete root type. + /// public class MTConnectAssetModel : MTConnectClassModel { + /// + /// Creates an empty model for manual population. + /// public MTConnectAssetModel() { } + /// + /// Parses the Asset class as a concrete, root-level type + /// (parent and abstract flag cleared). + /// public MTConnectAssetModel(XmiDocument xmiDocument, UmlClass umlClass) : base(xmiDocument, "Assets.Asset", umlClass) { ParentName = null; diff --git a/libraries/MTConnect.NET-SysML/Models/Assets/MTConnectMeasurementModel.cs b/libraries/MTConnect.NET-SysML/Models/Assets/MTConnectMeasurementModel.cs index 5ae3d622f..18c77ef09 100644 --- a/libraries/MTConnect.NET-SysML/Models/Assets/MTConnectMeasurementModel.cs +++ b/libraries/MTConnect.NET-SysML/Models/Assets/MTConnectMeasurementModel.cs @@ -5,19 +5,48 @@ namespace MTConnect.SysML.Models.Assets { + /// + /// A parsed cutting-tool measurement type, carrying its measurement + /// category, MTConnect type id, and the default code and units pulled + /// from the XMI default-value instances. + /// public class MTConnectMeasurementModel : MTConnectClassModel { + /// + /// The measurement category (for example the asset measurement + /// group this type belongs to). + /// public string MeasurementType { get; set; } + /// + /// The MTConnect type id of the measurement. + /// public string TypeId { get; set; } + /// + /// The default measurement code, resolved from the XMI + /// code default-value instance, or null when none is + /// declared. + /// public string CodeId { get; set; } + /// + /// The default units, resolved from the XMI units + /// default-value instance, or null when none is declared. + /// public string Units { get; set; } + /// + /// Creates an empty model for manual population. + /// public MTConnectMeasurementModel() { } + /// + /// Parses a measurement type from under + /// , resolving its default code and units + /// from the XMI default-value instances. + /// public MTConnectMeasurementModel(XmiDocument xmiDocument, string measurementType, string idPrefix, UmlClass umlClass) : base(null, null, null) { if (umlClass != null) @@ -65,6 +94,11 @@ public MTConnectMeasurementModel(XmiDocument xmiDocument, string measurementType } } + /// + /// Parses every measurement type in + /// under , de-duplicating by id and + /// ordering by name. + /// public static IEnumerable Parse(XmiDocument xmiDocument, string measurementType, string idPrefix, IEnumerable umlClasses) { var models = new List(); diff --git a/libraries/MTConnect.NET-SysML/Models/Assets/MTConnectPhysicalAssetModel.cs b/libraries/MTConnect.NET-SysML/Models/Assets/MTConnectPhysicalAssetModel.cs index 7e9cb98f3..426f2fc08 100644 --- a/libraries/MTConnect.NET-SysML/Models/Assets/MTConnectPhysicalAssetModel.cs +++ b/libraries/MTConnect.NET-SysML/Models/Assets/MTConnectPhysicalAssetModel.cs @@ -3,10 +3,21 @@ namespace MTConnect.SysML.Models.Assets { + /// + /// Parsed model for the MTConnect Assets.PhysicalAsset element, + /// emitted as a concrete root type. + /// public class MTConnectPhysicalAssetModel : MTConnectClassModel { + /// + /// Creates an empty model for manual population. + /// public MTConnectPhysicalAssetModel() { } + /// + /// Parses the PhysicalAsset class as a concrete, root-level + /// type (parent and abstract flag cleared). + /// public MTConnectPhysicalAssetModel(XmiDocument xmiDocument, UmlClass umlClass) : base(xmiDocument, "Assets.PhysicalAsset", umlClass) { ParentName = null; diff --git a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectComponentModel.cs b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectComponentModel.cs index d8e9c9091..3803c4574 100644 --- a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectComponentModel.cs +++ b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectComponentModel.cs @@ -3,8 +3,18 @@ namespace MTConnect.SysML.Models.Devices { + /// + /// Parsed model for the MTConnect Devices.Component element, with + /// the streaming navigations stripped so the generated base class only + /// carries the static device-model shape. + /// public class MTConnectComponentModel : MTConnectClassModel { + /// + /// Parses the Component class as a concrete, root-level type + /// and removes the ComponentStream, CompositionStream, and + /// DataItemStream navigations that belong to the streaming model. + /// public MTConnectComponentModel(XmiDocument xmiDocument, UmlClass umlClass) : base(xmiDocument, "Devices.Component", umlClass) { IsAbstract = false; diff --git a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectComponentType.cs b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectComponentType.cs index 48714b4cc..50f9b2cef 100644 --- a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectComponentType.cs +++ b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectComponentType.cs @@ -6,33 +6,80 @@ namespace MTConnect.SysML.Models.Devices { + /// + /// A parsed concrete Component subtype: its emitted class name, the + /// MTConnect type value, default component name, organizer flag, + /// and valid version range. + /// public class MTConnectComponentType : IMTConnectExportModel { + /// public string UmlId { get; set; } + /// public string Id { get; set; } + /// + /// The emitted C# class name (the MTConnect type with a + /// Component suffix). + /// public string Name { get; set; } + /// + /// The MTConnect type attribute value for this component. + /// public string Type { get; set; } + /// + /// The name of the base component class, or null when the + /// base is Component. + /// public string ParentName { get; set; } + /// + /// The cleaned description text emitted into the doc comment. + /// public string Description { get; set; } + /// + /// The default instance name for this component type. + /// public string DefaultName { get; set; } + /// + /// True when the component is emitted as abstract. + /// public bool IsAbstract { get; set; } + /// + /// True when the component is an organizer (a container for other + /// components). + /// public bool IsOrganizer { get; set; } + /// + /// The MTConnect version this component was deprecated at, or + /// null. + /// public Version MaximumVersion { get; set; } + /// + /// The MTConnect version this component was introduced in, or + /// null. + /// public Version MinimumVersion { get; set; } + /// + /// Creates an empty model for manual population. + /// public MTConnectComponentType() { } + /// + /// Parses a Component subtype from under + /// , resolving its default name, version + /// range, and single base class. + /// public MTConnectComponentType(XmiDocument xmiDocument, string idPrefix, UmlClass umlClass, bool isOrganizer = false) { if (umlClass != null) @@ -69,6 +116,10 @@ public MTConnectComponentType(XmiDocument xmiDocument, string idPrefix, UmlClass } + /// + /// Parses every Component subtype in + /// under . + /// public static IEnumerable Parse(XmiDocument xmiDocument, string idPrefix, IEnumerable umlClasses, bool isOrganizer = false) { var subClasses = new List(); @@ -88,11 +139,11 @@ private static string GetName(string type) { switch (type) { - case "Controller": return "cont"; - case "Environment": return "env"; + case "Controller": return "cont"; + case "Environment": return "env"; } return type.ToCamelCase(); - } + } } } diff --git a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectComponentsModel.cs b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectComponentsModel.cs index 45d905b37..0c8ec4e3d 100644 --- a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectComponentsModel.cs +++ b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectComponentsModel.cs @@ -2,10 +2,21 @@ namespace MTConnect.SysML.Models.Devices { + /// + /// The parsed Component model: the Component base class plus its + /// concrete component subtypes. + /// public class MTConnectComponentsModel { + /// + /// The parsed Component base class. + /// public MTConnectComponentModel Component { get; set; } + /// + /// The concrete Component subtypes derived from the + /// ComponentTypeEnum. + /// public List Types { get; set; } = new(); } } diff --git a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectCompositionModel.cs b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectCompositionModel.cs index 878303cd0..eedd37d79 100644 --- a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectCompositionModel.cs +++ b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectCompositionModel.cs @@ -5,11 +5,24 @@ namespace MTConnect.SysML.Models.Devices { + /// + /// Parsed model for the MTConnect Devices.Composition element and + /// its concrete composition subtypes. + /// public class MTConnectCompositionModel : MTConnectClassModel { + /// + /// The concrete Composition subtypes derived from the + /// CompositionTypeEnum. + /// public List Types { get; set; } = new(); + /// + /// Parses the Composition class as a concrete root type, + /// coerces its Type property to string, and removes the nested + /// Components/Compositions navigations. + /// public MTConnectCompositionModel(XmiDocument xmiDocument, UmlClass umlClass) : base(xmiDocument, "Devices.Composition", umlClass) { IsAbstract = false; diff --git a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectCompositionType.cs b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectCompositionType.cs index c5f2d666b..50c476fba 100644 --- a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectCompositionType.cs +++ b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectCompositionType.cs @@ -6,27 +6,63 @@ namespace MTConnect.SysML.Models.Devices { + /// + /// A parsed concrete Composition subtype, derived from a member of the + /// CompositionTypeEnum: its emitted class name, MTConnect + /// type value, default name, and valid version range. + /// public class MTConnectCompositionType : IMTConnectExportModel { + /// public string UmlId { get; set; } + /// public string Id { get; set; } + /// + /// The emitted C# class name (the MTConnect type with a + /// Composition suffix). + /// public string Name { get; set; } + /// + /// The MTConnect type attribute value for this composition. + /// public string Type { get; set; } + /// + /// The cleaned description text emitted into the doc comment. + /// public string Description { get; set; } + /// + /// The default instance name for this composition type. + /// public string DefaultName { get; set; } + /// + /// The MTConnect version this composition was deprecated at, or + /// null. + /// public Version MaximumVersion { get; set; } + /// + /// The MTConnect version this composition was introduced in, or + /// null. + /// public Version MinimumVersion { get; set; } + /// + /// Creates an empty model for manual population. + /// public MTConnectCompositionType() { } + /// + /// Parses a Composition subtype from an enumeration literal under + /// , resolving its default name and + /// version range. + /// public MTConnectCompositionType(XmiDocument xmiDocument, string idPrefix, UmlEnumerationLiteral umlEnumerationLiteral) { if (umlEnumerationLiteral != null) @@ -49,6 +85,10 @@ public MTConnectCompositionType(XmiDocument xmiDocument, string idPrefix, UmlEnu } + /// + /// Parses every member of into a + /// Composition subtype under . + /// public static IEnumerable Parse(XmiDocument xmiDocument, string idPrefix, UmlEnumeration umlEnumeration) { var subClasses = new List(); diff --git a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectCompositionsModel.cs b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectCompositionsModel.cs index 9784dd0fe..cc8322e61 100644 --- a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectCompositionsModel.cs +++ b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectCompositionsModel.cs @@ -2,10 +2,21 @@ namespace MTConnect.SysML.Models.Devices { + /// + /// The parsed Composition model: the Composition base class plus + /// its concrete composition subtypes. + /// public class MTConnectCompositionsModel { + /// + /// The parsed Composition base class. + /// public MTConnectCompositionModel Composition { get; set; } + /// + /// The concrete Composition subtypes derived from the + /// CompositionTypeEnum. + /// public List Types { get; set; } = new(); } } diff --git a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectConfigurationModel.cs b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectConfigurationModel.cs index 1a1d7ac0c..ae86b4bdb 100644 --- a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectConfigurationModel.cs +++ b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectConfigurationModel.cs @@ -4,12 +4,28 @@ namespace MTConnect.SysML.Models.Devices { + /// + /// Parsed model for the MTConnect Devices.Configurations.Configuration + /// element together with the configuration sub-element classes and + /// enumerations it carries. + /// public class MTConnectConfigurationModel : MTConnectClassModel { + /// + /// The configuration sub-element classes (coordinate systems, + /// specifications, sensor configuration, etc.). + /// public List Classes { get; set; } = new(); + /// + /// The enumerations referenced by the configuration classes. + /// public List Enums { get; set; } = new(); + /// + /// Parses the Configuration class as a concrete, root-level + /// type (parent cleared). + /// public MTConnectConfigurationModel(XmiDocument xmiDocument, UmlClass umlClass) : base(xmiDocument, "Devices.Configurations.Configuration", umlClass) { ParentName = null; diff --git a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDataItemModel.cs b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDataItemModel.cs index 3ec1f6446..d29ad9bd1 100644 --- a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDataItemModel.cs +++ b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDataItemModel.cs @@ -4,8 +4,19 @@ namespace MTConnect.SysML.Models.Devices { + /// + /// Parsed model for the MTConnect Devices.DataItem element, with + /// the type/subtype/units overrides and property renames the generated + /// DataItem base class requires. + /// public class MTConnectDataItemModel : MTConnectClassModel { + /// + /// Parses the DataItem class and applies its overrides: the + /// Type, SubType, Units, and NativeUnits properties are coerced to + /// string; Constraint/Relationship are pluralized; and the + /// inverse Observation navigation is dropped. + /// public MTConnectDataItemModel(XmiDocument xmiDocument, UmlClass umlClass) : base(xmiDocument, "Devices.DataItem", umlClass) { IsAbstract = false; diff --git a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDataItemSubType.cs b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDataItemSubType.cs index 5a8290a14..daa35ff7e 100644 --- a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDataItemSubType.cs +++ b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDataItemSubType.cs @@ -5,8 +5,18 @@ namespace MTConnect.SysML.Models.Devices { + /// + /// A parsed DataItem subtype: the trailing segment of the XMI class name + /// becomes the uppercase-underscore subtype constant, carried with its + /// introduced/deprecated versions and cleaned description. + /// public class MTConnectDataItemSubType : MTConnectSubclassModel { + /// + /// Parses a DataItem subtype from , keying + /// it under and resolving its version + /// metadata and description from . + /// public MTConnectDataItemSubType(XmiDocument xmiDocument, string idPrefix, UmlClass umlClass) : base(null) { UmlId = umlClass.Id; diff --git a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDataItemType.cs b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDataItemType.cs index c68704859..40f766d8c 100644 --- a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDataItemType.cs +++ b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDataItemType.cs @@ -6,39 +6,98 @@ namespace MTConnect.SysML.Models.Devices { + /// + /// A parsed concrete DataItem type: its emitted class name, MTConnect + /// category and type, default representation/units/subtype, structured + /// result type, valid version range, and its subtypes. + /// public class MTConnectDataItemType : IMTConnectExportModel { + /// public string UmlId { get; set; } + /// public string Id { get; set; } + /// + /// The emitted C# class name for this DataItem type. + /// public string Name { get; set; } + /// + /// The cleaned description text emitted into the doc comment. + /// public string Description { get; set; } + /// + /// The MTConnect category (SAMPLE, EVENT, or + /// CONDITION). + /// public string Category { get; set; } + /// + /// The MTConnect type attribute value for this DataItem. + /// public string Type { get; set; } + /// + /// The name of the base DataItem class. + /// public string ParentName { get; set; } + /// + /// The default representation (for example VALUE, + /// DATA_SET, TABLE, TIME_SERIES), or + /// null when the default applies. + /// public string Representation { get; set; } + /// + /// The default units for this DataItem, or null when none. + /// public string Units { get; set; } + /// + /// The default subtype, or null when none is declared. + /// public string DefaultSubType { get; set; } + /// + /// The structured result type name backing this DataItem, or + /// null for a plain value. + /// public string Result { get; set; } + /// + /// The MTConnect version this DataItem was deprecated at, or + /// null. + /// public Version MaximumVersion { get; set; } + /// + /// The MTConnect version this DataItem was introduced in, or + /// null. + /// public Version MinimumVersion { get; set; } + /// + /// The subtypes declared for this DataItem type. + /// public List SubTypes { get; set; } + /// + /// Creates an empty model for manual population. + /// public MTConnectDataItemType() { } + /// + /// Parses a DataItem type from and its + /// matching : resolves the + /// emitted name, category, default subtype, structured representation + /// (read from both the result property's parent chain and the enum + /// literal's prose marker), version range, base class, and subtypes. + /// public MTConnectDataItemType(XmiDocument xmiDocument, string category, string idPrefix, UmlClass umlClass, UmlEnumerationLiteral umlEnumerationLiteral, IEnumerable subClasses = null) { if (umlClass != null && umlEnumerationLiteral != null) @@ -174,6 +233,12 @@ public MTConnectDataItemType(XmiDocument xmiDocument, string category, string id } + /// + /// Parses every top-level DataItem type in + /// (excluding Type.SubType + /// entries), matching each against , + /// ordered by name. + /// public static IEnumerable Parse(XmiDocument xmiDocument, string category, string idPrefix, IEnumerable umlClasses, UmlEnumeration umlEnumeration) { var types = new List(); @@ -198,14 +263,20 @@ public static IEnumerable Parse(XmiDocument xmiDocument, } + /// + /// Maps an XMI DataItem class name to its emitted C# class name, + /// preserving the acronym casing the spec uses (AdapterUri, the + /// AC/DC pairs, MTConnectVersion, PH) and title-casing everything + /// else. + /// private static string ConvertClassName(string name) { if (name != null) { switch (name) { - case "AdapterURI": return "AdapterUri"; - case "AmperageAC": return "AmperageAC"; + case "AdapterURI": return "AdapterUri"; + case "AmperageAC": return "AmperageAC"; case "AmperageDC": return "AmperageDC"; case "VoltageAC": return "VoltageAC"; case "VoltageDC": return "VoltageDC"; @@ -232,6 +303,12 @@ private static string ConvertClassName(string name) // because a malformed XMI cycle would otherwise loop forever; // the visited-set both detects cycles and short-circuits a // diamond-inheritance graph that visits the same parent twice. + /// + /// Walks the generalization chain of a result class to determine its + /// structured representation (DATA_SET, TABLE, or + /// TIME_SERIES), defaulting to TABLE. The walk is + /// cycle-safe via a visited-set. + /// private static string ResolveStructuredRepresentation(XmiDocument xmiDocument, string resultClassId) { var visited = new HashSet(); @@ -261,6 +338,12 @@ private static string ResolveStructuredRepresentation(XmiDocument xmiDocument, s // typing fallback so DataItems whose `result` references a // primitive DataType (e.g. ASSET_COUNT pointing at `integer`) // still inherit the structured representation the spec mandates. + /// + /// Reads the canonical representation marker + /// ({{term(data set)}}, {{term(table)}}, or + /// {{term(time series)}}) from the start of the enum literal's + /// description, or null when no marker is present. + /// private static string GetRepresentationFromEnumLiteral(UmlEnumerationLiteral umlEnumerationLiteral) { var body = umlEnumerationLiteral?.Comments?.FirstOrDefault()?.Body; @@ -274,6 +357,10 @@ private static string GetRepresentationFromEnumLiteral(UmlEnumerationLiteral uml return null; } + /// + /// Maps an XMI DataItem enum literal name to its emitted C# name, + /// preserving the spec's acronym casing and title-casing the rest. + /// private static string ConvertEnumName(string name) { if (name != null) diff --git a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDataItemsModel.cs b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDataItemsModel.cs index 9458bb98c..dfa91c3e9 100644 --- a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDataItemsModel.cs +++ b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDataItemsModel.cs @@ -2,14 +2,32 @@ namespace MTConnect.SysML.Models.Devices { + /// + /// The parsed DataItem model: the DataItem base class, its + /// concrete type subclasses, and the supporting classes and enumerations + /// the DataItem types depend on. + /// public class MTConnectDataItemsModel { + /// + /// The parsed DataItem base class. + /// public MTConnectDataItemModel DataItem { get; set; } + /// + /// The concrete DataItem type subclasses derived from the DataItem + /// type enumerations. + /// public List Types { get; set; } = new(); + /// + /// Supporting classes referenced by the DataItem types. + /// public List Classes { get; set; } = new(); + /// + /// Enumerations referenced by the DataItem types. + /// public List Enums { get; set; } = new(); } } diff --git a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDescriptionModel.cs b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDescriptionModel.cs index b40c68284..e3ae3c793 100644 --- a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDescriptionModel.cs +++ b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDescriptionModel.cs @@ -3,8 +3,16 @@ namespace MTConnect.SysML.Models.Devices { + /// + /// Parsed model for the MTConnect Devices.Description element. + /// public class MTConnectDescriptionModel : MTConnectClassModel { + /// + /// Parses the Description class from + /// under the Devices.Description + /// model id. + /// public MTConnectDescriptionModel(XmiDocument xmiDocument, UmlClass umlClass) : base(xmiDocument, "Devices.Description", umlClass) { } } } diff --git a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDeviceInformationModel.cs b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDeviceInformationModel.cs index fed2bf703..58f86edab 100644 --- a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDeviceInformationModel.cs +++ b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDeviceInformationModel.cs @@ -3,25 +3,63 @@ namespace MTConnect.SysML.Models.Devices { + /// + /// Parses the Device Information Model from the XMI: the Device + /// class plus its component, composition, data item, description, + /// configuration, and reference models, with the project's name and + /// type overrides applied. + /// public class MTConnectDeviceInformationModel { + /// + /// The parsed Device class (with the component properties + /// folded in). + /// public MTConnectDeviceModel Device { get; private set; } + /// + /// The parsed Component base class and its concrete subtypes. + /// public MTConnectComponentsModel Components { get; private set; } + /// + /// The parsed Composition base class and its concrete subtypes. + /// public MTConnectCompositionsModel Compositions { get; private set; } + /// + /// The parsed DataItem base class, its type subclasses, and the + /// supporting classes and enumerations. + /// public MTConnectDataItemsModel DataItems { get; private set; } + /// + /// The parsed Description class. + /// public MTConnectDescriptionModel Description { get; private set; } + /// + /// The parsed Configuration class and its sub-element classes + /// and enumerations. + /// public MTConnectConfigurationModel Configurations { get; private set; } + /// + /// The parsed reference classes (ComponentReference, + /// DataItemReference). + /// public MTConnectPackageModel References { get; private set; } = new(); + /// + /// Creates an empty model for manual population. + /// public MTConnectDeviceInformationModel() { } + /// + /// Parses the full device information model from the given XMI + /// document. + /// public MTConnectDeviceInformationModel(XmiDocument xmiDocument) { Parse(xmiDocument); diff --git a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDeviceModel.cs b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDeviceModel.cs index fe6467e39..355910689 100644 --- a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDeviceModel.cs +++ b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectDeviceModel.cs @@ -4,8 +4,19 @@ namespace MTConnect.SysML.Models.Devices { + /// + /// Parsed model for the MTConnect Devices.Device element, with the + /// MTConnectVersion casing fixed and the streaming/organizer navigations + /// stripped so the generated class carries only the static device shape. + /// public class MTConnectDeviceModel : MTConnectClassModel { + /// + /// Parses the Device class as a concrete type, renames the + /// version property to MTConnectVersion of type + /// , and removes the organizer and + /// streaming navigations (Adapter, Axis, Controller, System, etc.). + /// public MTConnectDeviceModel(XmiDocument xmiDocument, UmlClass umlClass) : base(xmiDocument, "Devices.Device", umlClass) { IsAbstract = false; diff --git a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectInterfaceDataItemType.cs b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectInterfaceDataItemType.cs index d77ea6aa7..6433f36cc 100644 --- a/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectInterfaceDataItemType.cs +++ b/libraries/MTConnect.NET-SysML/Models/Devices/MTConnectInterfaceDataItemType.cs @@ -5,14 +5,32 @@ namespace MTConnect.SysML.Models.Devices { + /// + /// A parsed interface-specific DataItem type. Identical in shape to + /// but parsed from the Interface + /// Interaction Model's DataItem package. + /// public class MTConnectInterfaceDataItemType : MTConnectDataItemType { + /// + /// Creates an empty model for manual population. + /// public MTConnectInterfaceDataItemType() { } + /// + /// Parses an interface DataItem type, delegating to the + /// base parser. + /// public MTConnectInterfaceDataItemType(XmiDocument xmiDocument, string category, string idPrefix, UmlClass umlClass, UmlEnumerationLiteral umlEnumerationLiteral, IEnumerable subClasses = null) : base(xmiDocument, category, idPrefix, umlClass, umlEnumerationLiteral, subClasses) { } + /// + /// Parses every top-level interface DataItem type in + /// (excluding Type.SubType + /// entries), matching each against + /// , ordered by name. + /// public static IEnumerable Parse(XmiDocument xmiDocument, string category, string idPrefix, IEnumerable umlClasses, UmlEnumeration umlEnumeration) { var types = new List(); diff --git a/libraries/MTConnect.NET-SysML/Models/Interfaces/MTConnectDeviceInformationModel.cs b/libraries/MTConnect.NET-SysML/Models/Interfaces/MTConnectDeviceInformationModel.cs index c6eb91e56..d2de86f5e 100644 --- a/libraries/MTConnect.NET-SysML/Models/Interfaces/MTConnectDeviceInformationModel.cs +++ b/libraries/MTConnect.NET-SysML/Models/Interfaces/MTConnectDeviceInformationModel.cs @@ -4,13 +4,28 @@ namespace MTConnect.SysML.Models.Devices { + /// + /// Parses the Interface Interaction Model from the XMI, collecting the + /// interface-specific DataItem types keyed off the + /// InterfaceEventEnum. + /// public class MTConnectInterfaceInformationModel { + /// + /// The DataItem types declared for the interface model, or + /// null when the XMI carries no interface DataItem package. + /// public MTConnectDataItemsModel DataItems { get; private set; } + /// + /// Creates an empty model for manual population. + /// public MTConnectInterfaceInformationModel() { } + /// + /// Parses the interface DataItem types from the given XMI document. + /// public MTConnectInterfaceInformationModel(XmiDocument xmiDocument) { Parse(xmiDocument); diff --git a/libraries/MTConnect.NET-SysML/Models/Observations/MTConnectObservationInformationModel.cs b/libraries/MTConnect.NET-SysML/Models/Observations/MTConnectObservationInformationModel.cs index 8af90f7d3..59ed91851 100644 --- a/libraries/MTConnect.NET-SysML/Models/Observations/MTConnectObservationInformationModel.cs +++ b/libraries/MTConnect.NET-SysML/Models/Observations/MTConnectObservationInformationModel.cs @@ -4,15 +4,46 @@ namespace MTConnect.SysML.Models.Observations { + /// + /// Parses the Observation Information Model from the XMI, collecting the + /// Condition, Event, and Sample observation types (including the + /// interface event observations) plus the *Result value classes. + /// public class MTConnectObservationInformationModel { + /// + /// The parsed Condition, Event, and Sample observation types. + /// public List Types { get; set; } = new(); + /// + /// The parsed *Result value classes referenced by the + /// observation types. + /// public List Results { get; set; } = new(); + /// + /// The per-subtype value vocabularies for the CompositionState + /// and Direction event types. These DataItems carry a + /// subType that selects which value enumeration applies, so the + /// SysML model declares one enumeration per subtype (for example + /// CompositionStateActionEnum for the ACTION subtype). + /// Each is emitted under Observations.Events as a strongly + /// typed enum plus its paired *Descriptions lookup, which the + /// hand-authored EventValue.cs subtype switch consumes. + /// + public List Enums { get; set; } = new(); + + /// + /// Creates an empty model for manual population. + /// public MTConnectObservationInformationModel() { } + /// + /// Parses the observation types and result classes from the given + /// XMI document. + /// public MTConnectObservationInformationModel(XmiDocument xmiDocument) { Parse(xmiDocument); @@ -63,7 +94,7 @@ private void Parse(XmiDocument xmiDocument) } } - // Find Observatoin Result Model in the UML + // Find Observation Result Model in the UML var dataTypes = umlModel.Profiles.FirstOrDefault().Packages.FirstOrDefault(o => o.Name == "DataTypes"); if (dataTypes != null) { @@ -72,6 +103,31 @@ private void Parse(XmiDocument xmiDocument) { Results.AddRange(MTConnectClassModel.Parse(xmiDocument, "Observations.Events", resultDataTypes)); } + + // The CompositionState and Direction event DataItems + // resolve their value vocabulary from their subType. The + // SysML model carries one enumeration per subtype; emit + // each under Observations.Events so the generated enum and + // its paired *Descriptions lookup land beside + // EventValue.cs, which dispatches on the subType to the + // matching *Descriptions.Get(...) call. + foreach (var subtypeEnumName in new[] + { + "CompositionStateActionEnum", + "CompositionStateLateralEnum", + "CompositionStateMotionEnum", + "CompositionStateSwitchedEnum", + "CompositionStateVerticalEnum", + "DirectionLinearEnum", + "DirectionRotaryEnum", + }) + { + var subtypeEnum = dataTypes.Enumerations.FirstOrDefault(o => o.Name == subtypeEnumName); + if (subtypeEnum != null) + { + Enums.Add(new MTConnectEnumModel(xmiDocument, "Observations.Events", subtypeEnum)); + } + } } } } diff --git a/libraries/MTConnect.NET-SysML/Models/Observations/MTConnectObservationModel.cs b/libraries/MTConnect.NET-SysML/Models/Observations/MTConnectObservationModel.cs index 84b5a5c20..2095b7260 100644 --- a/libraries/MTConnect.NET-SysML/Models/Observations/MTConnectObservationModel.cs +++ b/libraries/MTConnect.NET-SysML/Models/Observations/MTConnectObservationModel.cs @@ -5,21 +5,46 @@ namespace MTConnect.SysML.Models.Observations { + /// + /// A parsed observation type (a Condition, Event, or Sample) whose + /// controlled result vocabulary is emitted as an enum of + /// members. + /// public class MTConnectObservationModel : IMTConnectExportModel { + /// public string UmlId { get; set; } + /// public string Id { get; set; } + /// + /// The emitted C# name for this observation type. + /// public string Name { get; set; } + /// + /// The cleaned description text emitted into the doc comment. + /// public string Description { get; set; } + /// + /// The observation's controlled result values. + /// public List Values { get; set; } = new(); + /// + /// Creates an empty model for manual population. + /// public MTConnectObservationModel() { } + /// + /// Parses an observation type from under + /// , taking its cleaned description from + /// the matching enum literal and its result values from + /// . + /// public MTConnectObservationModel(XmiDocument xmiDocument, string category, string idPrefix, UmlClass umlClass, UmlEnumerationLiteral umlEnumerationLiteral, UmlEnumeration resultEnumeration) { if (umlClass != null) @@ -43,6 +68,12 @@ public MTConnectObservationModel(XmiDocument xmiDocument, string category, strin } } + /// + /// Parses every observation type in + /// that has a result property whose type is an enumeration, + /// matching each against and + /// ordering by name. + /// public static IEnumerable Parse(XmiDocument xmiDocument, string category, string idPrefix, IEnumerable umlClasses, UmlEnumeration umlEnumeration) { var models = new List(); diff --git a/libraries/MTConnect.NET-SysML/Models/Observations/MTConnectObservationValueModel.cs b/libraries/MTConnect.NET-SysML/Models/Observations/MTConnectObservationValueModel.cs index 47019e4ad..11d202ce4 100644 --- a/libraries/MTConnect.NET-SysML/Models/Observations/MTConnectObservationValueModel.cs +++ b/libraries/MTConnect.NET-SysML/Models/Observations/MTConnectObservationValueModel.cs @@ -3,19 +3,39 @@ namespace MTConnect.SysML.Models.Observations { + /// + /// A single parsed observation enumeration value (a controlled-vocabulary + /// member of an observation type) with its cleaned description. + /// public class MTConnectObservationValueModel : IMTConnectExportModel { + /// public string UmlId { get; set; } + /// public string Id { get; set; } + /// + /// The value's member name as emitted in the generated C#. + /// public string Name { get; set; } + /// + /// The cleaned description text emitted into the doc comment. + /// public string Description { get; set; } + /// + /// Creates an empty model for manual population. + /// public MTConnectObservationValueModel() { } + /// + /// Parses an observation value literal under + /// , taking its name and cleaned + /// description. + /// public MTConnectObservationValueModel(string idPrefix, UmlEnumerationLiteral enumerationLiteral) { if (enumerationLiteral != null) diff --git a/libraries/MTConnect.NET-SysML/Xmi/UML/UmlProperty.cs b/libraries/MTConnect.NET-SysML/Xmi/UML/UmlProperty.cs index a481be9ba..3497c771d 100644 --- a/libraries/MTConnect.NET-SysML/Xmi/UML/UmlProperty.cs +++ b/libraries/MTConnect.NET-SysML/Xmi/UML/UmlProperty.cs @@ -58,6 +58,13 @@ public class UmlProperty : OwnedAttribute [XmlAnyElement(XmiHelper.XmiStructure.DEFAULT_VALUE, Namespace = "")] public XmlElement? DefaultValueElement { get; set; } private DefaultValue? _defaultValue; + /// + /// The deserialized default value of the property, materialized + /// lazily from as either a + /// or + /// depending on the element's xmi:type. Returns null + /// when no default value element is present. + /// public DefaultValue? DefaultValue { get diff --git a/libraries/MTConnect.NET-SysML/Xmi/XmiDeserializer.cs b/libraries/MTConnect.NET-SysML/Xmi/XmiDeserializer.cs index fc3fe6467..cff2bf9b8 100644 --- a/libraries/MTConnect.NET-SysML/Xmi/XmiDeserializer.cs +++ b/libraries/MTConnect.NET-SysML/Xmi/XmiDeserializer.cs @@ -18,7 +18,6 @@ public sealed class XmiDeserializer /// Constructs a new instance of the deserializer with a reference to the source document. /// /// A source of XMI to deserialize - /// public XmiDeserializer(XmlDocument xmlDocument) { xDoc = xmlDocument; @@ -78,7 +77,6 @@ public XmiDeserializer(XmlDocument xmlDocument) /// Creates a from a reference to the filepath of a XMI document. /// /// Filepath to a XMI-formatted XML document. - /// /// public static XmiDeserializer FromFile(string filename) { @@ -106,7 +104,6 @@ public static XmiDeserializer FromFile(string filename) /// Creates a from raw XML. /// /// Raw XML string - /// /// public static XmiDeserializer FromXml(string xml) { diff --git a/libraries/MTConnect.NET-TLS/CertificateLoadResult.cs b/libraries/MTConnect.NET-TLS/CertificateLoadResult.cs index 0958632f7..b38f10614 100644 --- a/libraries/MTConnect.NET-TLS/CertificateLoadResult.cs +++ b/libraries/MTConnect.NET-TLS/CertificateLoadResult.cs @@ -6,15 +6,32 @@ namespace MTConnect.Tls { + /// + /// The outcome of attempting to load a TLS certificate, carrying either the loaded certificate or the failure. + /// public struct CertificateLoadResult { + /// + /// Indicates whether the certificate was loaded successfully. + /// public bool Success { get; set; } + /// + /// The loaded certificate when is true; otherwise null. + /// public X509Certificate2 Certificate { get; set; } + /// + /// The exception that caused the load to fail when is false; otherwise null. + /// public Exception Exception { get; set; } + /// + /// Creates a successful result wrapping the loaded certificate. + /// + /// The certificate that was loaded. + /// A successful result, or an unsuccessful result when is null. public static CertificateLoadResult Ok(X509Certificate2 certificate) { var result = new CertificateLoadResult(); @@ -28,6 +45,11 @@ public static CertificateLoadResult Ok(X509Certificate2 certificate) return result; } + /// + /// Creates an unsuccessful result wrapping the exception that caused the failure. + /// + /// The exception describing the load failure. + /// An unsuccessful result. public static CertificateLoadResult Error(Exception exception) { var result = new CertificateLoadResult(); diff --git a/libraries/MTConnect.NET-TLS/PemCertificateConfiguration.cs b/libraries/MTConnect.NET-TLS/PemCertificateConfiguration.cs index c3c8793cf..ae4c7d138 100644 --- a/libraries/MTConnect.NET-TLS/PemCertificateConfiguration.cs +++ b/libraries/MTConnect.NET-TLS/PemCertificateConfiguration.cs @@ -5,17 +5,32 @@ namespace MTConnect.Tls { + /// + /// Configures a TLS certificate loaded from PEM-encoded files. + /// public class PemCertificateConfiguration { + /// + /// The path to the PEM file containing the trusted certificate authority chain. + /// [JsonPropertyName("certificateAuthority")] public string CertificateAuthority { get; set; } + /// + /// The path to the PEM file containing the server or client certificate. + /// [JsonPropertyName("certificatePath")] public string CertificatePath { get; set; } + /// + /// The path to the PEM file containing the certificate's private key. + /// [JsonPropertyName("privateKeyPath")] public string PrivateKeyPath { get; set; } + /// + /// The password protecting the private key, when it is encrypted. + /// [JsonPropertyName("privateKeyPassword")] public string PrivateKeyPassword { get; set; } } diff --git a/libraries/MTConnect.NET-TLS/PfxCertificateConfiguration.cs b/libraries/MTConnect.NET-TLS/PfxCertificateConfiguration.cs index 5bbb0d467..42117ff18 100644 --- a/libraries/MTConnect.NET-TLS/PfxCertificateConfiguration.cs +++ b/libraries/MTConnect.NET-TLS/PfxCertificateConfiguration.cs @@ -5,11 +5,20 @@ namespace MTConnect.Tls { + /// + /// Configures a TLS certificate loaded from a PKCS#12 (PFX) file. + /// public class PfxCertificateConfiguration { + /// + /// The path to the PFX file containing the certificate and its private key. + /// [JsonPropertyName("certificatePath")] public string CertificatePath { get; set; } + /// + /// The password protecting the PFX file, when it is encrypted. + /// [JsonPropertyName("certificatePassword")] public string CertificatePassword { get; set; } } diff --git a/libraries/MTConnect.NET-TLS/README.md b/libraries/MTConnect.NET-TLS/README.md new file mode 100644 index 000000000..eca8deb02 --- /dev/null +++ b/libraries/MTConnect.NET-TLS/README.md @@ -0,0 +1,82 @@ +![MTConnect.NET Logo](https://raw.githubusercontent.com/TrakHound/MTConnect.NET/master/img/mtconnect-net-03-md.png) + +# MTConnect.NET-TLS +MTConnect.NET-TLS is an extension library to MTConnect.NET that provides TLS certificate loading and configuration for use with the HTTP and MQTT transport layers. + +For TLS configuration within the HTTP server module or the MQTT relay module, see [docs/modules](../../docs/modules/). + +## Nuget +
+ + + + + + + + + + + + + + +
Package NameDownloadsLink
MTConnect.NET-TLShttps://www.nuget.org/packages/MTConnect.NET-TLS
+ +## Overview +This library defines the `TlsConfiguration` class and its companion types (`PfxCertificateConfiguration`, `PemCertificateConfiguration`, `CertificateLoadResult`) that are consumed by the HTTP server module and the MQTT relay/broker modules to set up TLS-secured connections. Both PFX (PKCS#12) and PEM certificate formats are supported. + +The `TlsConfiguration.GetCertificate()` method loads the certificate from the configured source and returns a `CertificateLoadResult` that carries either the loaded `X509Certificate2` or the exception that prevented loading. + +## Configuration + +### PFX Certificate +```yaml +tls: + pfx: + certificatePath: c:\certs\mtconnect-testing.pfx + certificatePassword: mtconnect +``` + +### PEM Certificate (with Certificate Authority) +```yaml +tls: + pem: + certificateAuthority: c:\certs\rootCA.crt + certificatePath: c:\certs\mtconnect-testing.crt + privateKeyPath: c:\certs\mtconnect-testing.key + privateKeyPassword: mtconnect +``` + +### Configuration Properties + +* `pfx` - PFX (PKCS#12) certificate settings. Takes precedence over `pem` when both are provided. + * `certificatePath` - Path to the `.pfx` file containing the certificate and its private key. + * `certificatePassword` - Password protecting the PFX file (omit if the file is not password-protected). + +* `pem` - PEM certificate settings, used when `pfx` is not configured. + * `certificateAuthority` - Path to the `.pem` or `.crt` file containing the trusted CA chain. + * `certificatePath` - Path to the `.pem` or `.crt` file containing the server or client certificate. + * `privateKeyPath` - Path to the `.key` file containing the private key. + * `privateKeyPassword` - Password protecting the private key (omit if the key is unencrypted). + +* `verifyClientCertificate` - When `true`, the endpoint requires and validates a client certificate. + +* `omitCAValidation` - When `true`, certificate-authority chain validation is skipped (useful for self-signed certificates in development). + +## Generating a Self-Signed Certificate (PowerShell) +```powershell +New-SelfSignedCertificate -DnsName "localhost" -CertStoreLocation "cert:\LocalMachine\My" -FriendlyName "MTConnect-Test" -Type "SSLServerAuthentication" -NotAfter (Get-Date).AddYears(1) +``` + +## Related Libraries +- [MTConnect.NET-HTTP](../MTConnect.NET-HTTP/) — HTTP client and server transport +- [MTConnect.NET-MQTT](../MTConnect.NET-MQTT/) — MQTT broker and client transport + +## Contribution / Feedback +- Please use the [Issues](https://github.com/TrakHound/MTConnect.NET/issues) tab to create issues for specific problems that you may encounter +- Please feel free to use the [Pull Requests](https://github.com/TrakHound/MTConnect.NET/pulls) tab for any suggested improvements to the source code +- For any other questions or feedback, please contact TrakHound directly at **info@trakhound.com**. + +## License +This library and its source code is licensed under the [MIT License](https://choosealicense.com/licenses/mit/) and is free to use and distribute. diff --git a/libraries/MTConnect.NET-TLS/TlsConfiguration.cs b/libraries/MTConnect.NET-TLS/TlsConfiguration.cs index 4a260a2cf..f6c3f3143 100644 --- a/libraries/MTConnect.NET-TLS/TlsConfiguration.cs +++ b/libraries/MTConnect.NET-TLS/TlsConfiguration.cs @@ -7,21 +7,40 @@ namespace MTConnect.Tls { + /// + /// Configures TLS for an MTConnect endpoint, selecting either a PFX or PEM certificate and its validation options. + /// public class TlsConfiguration { + /// + /// The PFX certificate configuration; takes precedence over when set. + /// [JsonPropertyName("pfx")] public PfxCertificateConfiguration Pfx { get; set; } + /// + /// The PEM certificate configuration, used when is not set. + /// [JsonPropertyName("pem")] public PemCertificateConfiguration Pem { get; set; } + /// + /// Whether the endpoint requires and verifies a client certificate. + /// [JsonPropertyName("verifyClientCertificate")] public bool VerifyClientCertificate { get; set; } + /// + /// Whether certificate-authority chain validation is skipped. + /// [JsonPropertyName("omitCAValidation")] public bool OmitCAValidation { get; set; } + /// + /// Loads the configured endpoint certificate from the PFX or PEM source. + /// + /// The load result, empty when no certificate source is configured. public CertificateLoadResult GetCertificate() { // Load PFX Certificate @@ -39,6 +58,10 @@ public CertificateLoadResult GetCertificate() return new CertificateLoadResult(); } + /// + /// Loads the configured certificate-authority chain from the PEM source. + /// + /// The load result, empty when no certificate authority is configured. public CertificateLoadResult GetCertificateAuthority() { // Load PEM Certificate @@ -60,7 +83,7 @@ private CertificateLoadResult GetPfxCertificate() if (!string.IsNullOrEmpty(Pfx.CertificatePassword)) certificate = new X509Certificate2(Pfx.CertificatePath, Pfx.CertificatePassword); else certificate = new X509Certificate2(Pfx.CertificatePath); - + return CertificateLoadResult.Ok(certificate); } catch (Exception ex) diff --git a/libraries/MTConnect.NET-XML/Assets/ComponentConfigurationParameters/XmlComponentConfigurationParametersAsset.cs b/libraries/MTConnect.NET-XML/Assets/ComponentConfigurationParameters/XmlComponentConfigurationParametersAsset.cs index ef65732a8..1e60f1582 100644 --- a/libraries/MTConnect.NET-XML/Assets/ComponentConfigurationParameters/XmlComponentConfigurationParametersAsset.cs +++ b/libraries/MTConnect.NET-XML/Assets/ComponentConfigurationParameters/XmlComponentConfigurationParametersAsset.cs @@ -8,14 +8,28 @@ namespace MTConnect.Assets.ComponentConfigurationParameters { + /// + /// XML serialization surrogate for a ComponentConfigurationParameters + /// asset, which captures the configurable parameters of a component grouped + /// into named parameter sets. + /// [XmlRoot("ComponentConfigurationParameters")] public class XmlComponentConfigurationParametersAsset : XmlAsset { + /// + /// The parameter sets carried by the asset, serialized as + /// ParameterSet elements within ParameterSets. + /// [XmlArray("ParameterSets")] [XmlArrayItem("ParameterSet")] public List ParameterSets { get; set; } + /// + /// Converts this surrogate to a strongly-typed + /// , copying the + /// shared asset fields and converting each parameter set. + /// public override IAsset ToAsset() { var asset = new ComponentConfigurationParametersAsset(); @@ -30,7 +44,7 @@ public override IAsset ToAsset() if (!ParameterSets.IsNullOrEmpty()) { var parameterSets = new List(); - foreach (var parameterSet in ParameterSets) + foreach (var parameterSet in ParameterSets) { parameterSets.Add(parameterSet.ToParameterSet()); } @@ -40,6 +54,11 @@ public override IAsset ToAsset() return asset; } + /// + /// Writes the ComponentConfigurationParameters element, emitting + /// the shared asset attributes followed by the parameter sets when + /// present. + /// public static void WriteXml(XmlWriter writer, IAsset asset) { if (asset != null) diff --git a/libraries/MTConnect.NET-XML/Assets/ComponentConfigurationParameters/XmlParameter.cs b/libraries/MTConnect.NET-XML/Assets/ComponentConfigurationParameters/XmlParameter.cs index b009e72cf..2a4a3dc6d 100644 --- a/libraries/MTConnect.NET-XML/Assets/ComponentConfigurationParameters/XmlParameter.cs +++ b/libraries/MTConnect.NET-XML/Assets/ComponentConfigurationParameters/XmlParameter.cs @@ -7,31 +7,62 @@ namespace MTConnect.Assets.ComponentConfigurationParameters { + /// + /// XML serialization surrogate for a component-configuration + /// Parameter. Mirrors the on-the-wire element, where the value is + /// carried as the element text and its metadata as attributes, and converts + /// to the strongly-typed model. + /// public class XmlParameter { + /// + /// The identifier that uniquely identifies the parameter. + /// [XmlAttribute("identifier")] public string Identifier { get; set; } + /// + /// The human-readable name of the parameter. + /// [XmlAttribute("name")] public string Name { get; set; } + /// + /// The minimum permitted value, as the raw attribute text. + /// [XmlAttribute("minimum")] public string Minimum { get; set; } + /// + /// The maximum permitted value, as the raw attribute text. + /// [XmlAttribute("maximum")] public string Maximum { get; set; } + /// + /// The nominal (target) value, as the raw attribute text. + /// [XmlAttribute("nominal")] public string Nominal { get; set; } + /// + /// The configured value, carried as the element text. + /// [XmlText] public string Value { get; set; } + /// + /// The engineering units the value is expressed in. + /// [XmlAttribute("units")] public string Units { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , parsing the numeric metadata values. + /// public IParameter ToParameter() { var parameter = new Parameter(); @@ -48,6 +79,11 @@ public IParameter ToParameter() return parameter; } + /// + /// Writes the given parameters to wrapped in + /// a Parameters element, one Parameter element per item, + /// omitting optional attributes that are not set. + /// public static void WriteXml(XmlWriter writer, IEnumerable parameters) { if (!parameters.IsNullOrEmpty()) diff --git a/libraries/MTConnect.NET-XML/Assets/ComponentConfigurationParameters/XmlParameterSet.cs b/libraries/MTConnect.NET-XML/Assets/ComponentConfigurationParameters/XmlParameterSet.cs index 0f9805061..a719ebcff 100644 --- a/libraries/MTConnect.NET-XML/Assets/ComponentConfigurationParameters/XmlParameterSet.cs +++ b/libraries/MTConnect.NET-XML/Assets/ComponentConfigurationParameters/XmlParameterSet.cs @@ -7,16 +7,33 @@ namespace MTConnect.Assets.ComponentConfigurationParameters { + /// + /// XML serialization surrogate for a ParameterSet, a named group of + /// configuration parameters within a ComponentConfigurationParameters + /// asset. + /// public class XmlParameterSet { + /// + /// The name identifying the parameter set, carried by the name + /// attribute. + /// [XmlAttribute("name")] public string Name { get; set; } + /// + /// The parameters in this set, serialized as Parameter elements + /// within Parameters. + /// [XmlArray("Parameters")] [XmlArrayItem("Parameter")] public List Parameters { get; set; } + /// + /// Converts this surrogate to a strongly-typed , + /// copying the optional name and converting each parameter. + /// public IParameterSet ToParameterSet() { var parameterSet = new ParameterSet(); @@ -38,6 +55,11 @@ public IParameterSet ToParameterSet() return parameterSet; } + /// + /// Writes the ParameterSets container with one + /// ParameterSet element per set; nothing is written when the + /// collection is empty. + /// public static void WriteXml(XmlWriter writer, IEnumerable parameterSets) { if (!parameterSets.IsNullOrEmpty()) diff --git a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCutterStatus.cs b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCutterStatus.cs index 442d31987..5b0d776df 100644 --- a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCutterStatus.cs +++ b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCutterStatus.cs @@ -5,8 +5,17 @@ namespace MTConnect.Assets.Xml.CuttingTools { + /// + /// XML serialization surrogate for a single Status entry within a + /// CuttingTool CutterStatus collection. Each entry records one + /// life-cycle state of the cutter (for example NEW, USED, + /// EXPIRED, or BROKEN). + /// public class XmlCutterStatus { + /// + /// The cutter status value carried by the Status element. + /// [XmlElement("Status")] public string Status { get; set; } } diff --git a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingItem.cs b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingItem.cs index 93ce7d264..77a7b3121 100644 --- a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingItem.cs +++ b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingItem.cs @@ -8,36 +8,76 @@ namespace MTConnect.Assets.Xml.CuttingTools { + /// + /// Hand-written part of the XML serialization surrogate for a cutting tool + /// CuttingItem (an individual edge of the tool). Carries the + /// properties that are not model-generated and converts to and from the + /// strongly-typed model. + /// public partial class XmlCuttingItem { + /// + /// The range of indices on the tool the cutting item occupies, as the + /// raw attribute text. + /// [XmlAttribute("indices")] public string Indices { get; set; } + /// + /// The identifier of the cutting item within the tool. + /// [XmlAttribute("itemId")] public string ItemId { get; set; } + /// + /// The manufacturers of the cutting item, as a comma-separated list. + /// [XmlAttribute("manufacturers")] public string Manufacturers { get; set; } + /// + /// The material grade of the cutting item. + /// [XmlAttribute("grade")] public string Grade { get; set; } + /// + /// The free-form description of the cutting item. + /// [XmlElement("Description")] public string Description { get; set; } + /// + /// The position of the cutting item on the tool. + /// [XmlElement("Locus")] public string Locus { get; set; } + /// + /// The identifier of the tool group the program refers to the item by. + /// [XmlElement("ProgramToolGroup")] public string ProgramToolGroup { get; set; } + /// + /// The status of the cutting item, such as NEW or USED. + /// [XmlElement("CutterStatus")] public List CutterStatus { get; set; } + /// + /// The accumulated and remaining life of the cutting item. + /// [XmlElement("ItemLife")] public List ItemLife { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , splitting the comma-separated + /// manufacturers and projecting each nested collection into its model + /// representation. + /// public ICuttingItem ToCuttingItem() { var cuttingItem = new CuttingItem(); @@ -90,6 +130,11 @@ public ICuttingItem ToCuttingItem() return cuttingItem; } + /// + /// Writes the given cutting items to wrapped + /// in a CuttingItems element, one CuttingItem element per + /// item, omitting optional values that are not set. + /// public static void WriteXml(XmlWriter writer, IEnumerable cuttingItems) { if (!cuttingItems.IsNullOrEmpty()) diff --git a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingItem.g.cs b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingItem.g.cs index a848024d2..a82720a10 100644 --- a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingItem.g.cs +++ b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingItem.g.cs @@ -9,6 +9,11 @@ namespace MTConnect.Assets.Xml.CuttingTools { public partial class XmlCuttingItem { + /// + /// The set of physical and geometric measurements that characterize this cutting item. + /// Each element is deserialized into the concrete subclass + /// registered for its MTConnect measurement type. + /// [XmlArray("Measurements")] [XmlArrayItem(BodyDiameterMaxMeasurement.TypeId, typeof(XmlBodyDiameterMaxMeasurement))] [XmlArrayItem(BodyLengthMaxMeasurement.TypeId, typeof(XmlBodyLengthMaxMeasurement))] diff --git a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingItems.cs b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingItems.cs index cc091f0ab..9a2d964bb 100644 --- a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingItems.cs +++ b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingItems.cs @@ -7,11 +7,24 @@ namespace MTConnect.Assets.Xml.CuttingTools { + /// + /// XML serialization surrogate for the CuttingItems container of a + /// CuttingTool life cycle. Holds the collection of individual cutting edges + /// and the declared count of items for round-trip validation. + /// public class XmlCuttingItems { + /// + /// The number of cutting items the tool declares, carried by the + /// count attribute. + /// [XmlAttribute("count")] public int Count { get; set; } + /// + /// The individual cutting edges, serialized as repeated + /// CuttingItem elements. + /// [XmlElement("CuttingItem")] public List CuttingItems { get; set; } } diff --git a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolArchetypeAsset.cs b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolArchetypeAsset.cs index 6e0bb7ade..791466bed 100644 --- a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolArchetypeAsset.cs +++ b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolArchetypeAsset.cs @@ -7,25 +7,51 @@ namespace MTConnect.Assets.Xml.CuttingTools { + /// + /// XML serialization surrogate for an MTConnect CuttingToolArchetype + /// asset, the template a physical cutting tool is instantiated from. + /// Mirrors the on-the-wire element and converts to and from the + /// strongly-typed model. + /// [XmlRoot("CuttingToolArchetype")] public class XmlCuttingToolArchetypeAsset : XmlAsset { + /// + /// The serial number of the archetype. + /// [XmlAttribute("serialNumber")] public string SerialNumber { get; set; } + /// + /// The identifier the tool is referenced by in programs. + /// [XmlAttribute("toolId")] public string ToolId { get; set; } + /// + /// The manufacturers of the archetype, as a comma-separated list. + /// [XmlAttribute("manufacturers")] public string Manufacturers { get; set; } + /// + /// The vendor-specific definition document describing the tool. + /// [XmlAttribute("CuttingToolDefinition")] public XmlCuttingToolDefinition CuttingToolDefinition { get; set; } + /// + /// The default life-cycle state the archetype prescribes. + /// [XmlElement("CuttingToolLifeCycle")] public XmlCuttingToolLifeCycle CuttingToolLifeCycle { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , splitting the + /// comma-separated manufacturers and projecting the nested elements. + /// public override IAsset ToAsset() { var asset = new CuttingToolArchetypeAsset(); @@ -48,6 +74,12 @@ public override IAsset ToAsset() return asset; } + /// + /// Writes the given to + /// as a CuttingToolArchetype element, + /// joining the manufacturers list and omitting optional elements that + /// are not set. + /// public static void WriteXml(XmlWriter writer, IAsset asset) { if (asset != null) diff --git a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolArchetypeReference.cs b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolArchetypeReference.cs index 50b219987..5fa500ac4 100644 --- a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolArchetypeReference.cs +++ b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolArchetypeReference.cs @@ -7,15 +7,33 @@ namespace MTConnect.Assets.Xml.CuttingTools { + /// + /// XML serialization surrogate for a CuttingToolArchetypeReference, + /// linking a CuttingTool instance to the archetype that defines its + /// reusable, instance-independent characteristics. + /// public class XmlCuttingToolArchetypeReference { + /// + /// An optional URI locating the archetype definition, carried by the + /// source attribute. + /// [XmlAttribute("source")] public string Source { get; set; } + /// + /// The assetId of the referenced cutting tool archetype, carried + /// as the element's text content. + /// [XmlText] public string Value { get; set; } + /// + /// Converts this surrogate to a strongly-typed + /// , copying the source URI + /// and referenced archetype id. + /// public ICuttingToolArchetypeReference ToCuttingToolArchetypeReference() { var location = new CuttingToolArchetypeReference(); @@ -24,6 +42,11 @@ public ICuttingToolArchetypeReference ToCuttingToolArchetypeReference() return location; } + /// + /// Writes the CuttingToolArchetypeReference element, emitting the + /// optional source attribute and the archetype id as element + /// content. + /// public static void WriteXml(XmlWriter writer, ICuttingToolArchetypeReference cuttingToolArchetypeReference) { if (cuttingToolArchetypeReference != null) diff --git a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolAsset.cs b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolAsset.cs index 3c17831e8..9fb121542 100644 --- a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolAsset.cs +++ b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolAsset.cs @@ -7,28 +7,57 @@ namespace MTConnect.Assets.Xml.CuttingTools { + /// + /// XML serialization surrogate for an MTConnect CuttingTool asset. + /// Mirrors the on-the-wire element and converts to and from the + /// strongly-typed model. + /// [XmlRoot("CuttingTool")] public class XmlCuttingToolAsset : XmlAsset { + /// + /// The serial number that uniquely identifies the physical tool. + /// [XmlAttribute("serialNumber")] public string SerialNumber { get; set; } + /// + /// The identifier the tool is referenced by in programs. + /// [XmlAttribute("toolId")] public string ToolId { get; set; } + /// + /// The manufacturers of the tool, as a comma-separated list. + /// [XmlAttribute("manufacturers")] public string Manufacturers { get; set; } + /// + /// The measured state of the tool, including its life counters and + /// cutting items. + /// [XmlElement("CuttingToolLifeCycle")] public XmlCuttingToolLifeCycle CuttingToolLifeCycle { get; set; } + /// + /// The reference to the archetype this tool is an instance of. + /// [XmlElement("cuttingToolArchetypeReference")] public XmlCuttingToolArchetypeReference CuttingToolArchetypeReference { get; set; } + /// + /// The vendor-specific definition document describing the tool. + /// [XmlElement("CuttingToolDefinition")] public XmlCuttingToolDefinition CuttingToolDefinition { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , splitting the comma-separated + /// manufacturers and projecting the nested elements. + /// public override IAsset ToAsset() { var asset = new CuttingToolAsset(); @@ -53,6 +82,12 @@ public override IAsset ToAsset() return asset; } + /// + /// Writes the given to + /// as a CuttingTool element, joining + /// the manufacturers list and omitting optional elements that are not + /// set. + /// public static void WriteXml(XmlWriter writer, IAsset asset) { if (asset != null) diff --git a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolDefinition.cs b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolDefinition.cs index 528b6a176..074a7bde2 100644 --- a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolDefinition.cs +++ b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolDefinition.cs @@ -7,12 +7,26 @@ namespace MTConnect.Assets.Xml.CuttingTools { + /// + /// XML serialization surrogate for a CuttingTool CuttingToolDefinition, + /// the vendor-specific tool definition payload whose encoding is described + /// by its format. + /// public class XmlCuttingToolDefinition { + /// + /// The encoding of the definition payload, carried by the + /// format attribute (for example XML or TEXT). + /// [XmlAttribute("format")] public string Format { get; set; } + /// + /// Converts this surrogate to a strongly-typed + /// , mapping the format string to + /// its enumeration. + /// public ICuttingToolDefinition ToCuttingToolDefinition() { var cuttingToolDefinition = new CuttingToolDefinition(); @@ -20,6 +34,10 @@ public ICuttingToolDefinition ToCuttingToolDefinition() return cuttingToolDefinition; } + /// + /// Writes the CuttingToolDefinition element, emitting the + /// format attribute. + /// public static void WriteXml(XmlWriter writer, ICuttingToolDefinition cuttingToolDefinition) { if (cuttingToolDefinition != null) diff --git a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolLifeCycle.cs b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolLifeCycle.cs index b74a499cf..b9aa3fb23 100644 --- a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolLifeCycle.cs +++ b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolLifeCycle.cs @@ -8,39 +8,81 @@ namespace MTConnect.Assets.Xml.CuttingTools { + /// + /// Hand-written part of the XML serialization surrogate for a + /// CuttingToolLifeCycle. Carries the life-cycle properties that are + /// not model-generated and converts the whole element to and from the + /// strongly-typed model. + /// public partial class XmlCuttingToolLifeCycle { + /// + /// The status of the cutting tool, such as NEW or USED. + /// [XmlElement("CutterStatus")] public List CutterStatus { get; set; } + /// + /// The number of times the tool has been reconditioned. + /// [XmlElement("ReconditionCount")] public XmlReconditionCount ReconditionCount { get; set; } + /// + /// The accumulated and remaining life of the tool. + /// [XmlElement("ToolLife")] public List ToolLife { get; set; } + /// + /// Where the tool currently resides in a tool-handling system. + /// [XmlElement("Location")] public XmlLocation Location { get; set; } + /// + /// The identifier of the tool group the program refers to the tool by. + /// [XmlElement("ProgramToolGroup")] public string ProgramToolGroup { get; set; } + /// + /// The number the program refers to the tool by. + /// [XmlElement("ProgramToolNumber")] public string ProgramToolNumber { get; set; } + /// + /// The connection code identifying the machine-side interface of the + /// tool. + /// [XmlElement("ConnectionCodeMachineSide")] public string ConnectionCodeMachineSide { get; set; } + /// + /// The spindle speed limits the tool is expected to operate within. + /// [XmlElement("ProcessSpindleSpeed")] public XmlProcessSpindleSpeed ProcessSpindleSpeed { get; set; } + /// + /// The feed rate limits the tool is expected to operate within. + /// [XmlElement("ProcessFeedRate")] public XmlProcessFeedRate ProcessFeedRate { get; set; } + /// + /// The individual cutting items (edges) the tool comprises. + /// [XmlElement("CuttingItems")] public XmlCuttingItems CuttingItems { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , projecting each nested + /// collection into its model representation. + /// public ICuttingToolLifeCycle ToCuttingToolLifeCycle() { var cuttingToolLifeCycle = new CuttingToolLifeCycle(); @@ -99,6 +141,11 @@ public ICuttingToolLifeCycle ToCuttingToolLifeCycle() return cuttingToolLifeCycle; } + /// + /// Writes the given to + /// as a CuttingToolLifeCycle element, + /// emitting only the properties and collections that are present. + /// public static void WriteXml(XmlWriter writer, ICuttingToolLifeCycle cuttingToolLifeCycle) { if (cuttingToolLifeCycle != null) diff --git a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolLifeCycle.g.cs b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolLifeCycle.g.cs index 4895d10c6..8d645c866 100644 --- a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolLifeCycle.g.cs +++ b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlCuttingToolLifeCycle.g.cs @@ -9,6 +9,11 @@ namespace MTConnect.Assets.Xml.CuttingTools { public partial class XmlCuttingToolLifeCycle { + /// + /// The set of physical and geometric measurements that characterize the cutting tool + /// over its life cycle. Each element is deserialized into the concrete + /// subclass registered for its MTConnect measurement type. + /// [XmlArray("Measurements")] [XmlArrayItem(BodyDiameterMaxMeasurement.TypeId, typeof(XmlBodyDiameterMaxMeasurement))] [XmlArrayItem(BodyLengthMaxMeasurement.TypeId, typeof(XmlBodyLengthMaxMeasurement))] diff --git a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlItemLife.cs b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlItemLife.cs index f7a043904..0d2943883 100644 --- a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlItemLife.cs +++ b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlItemLife.cs @@ -8,27 +8,59 @@ namespace MTConnect.Assets.Xml.CuttingTools { + /// + /// XML serialization surrogate for a cutting item's ItemLife counter. + /// Mirrors the on-the-wire element, where the accumulated value is the + /// element text and its metadata are attributes, and converts to the + /// strongly-typed model. + /// public class XmlItemLife { + /// + /// The current accumulated life value, carried as the element text. + /// [XmlText] public double Value { get; set; } + /// + /// The kind of life counter, such as MINUTES or PART_COUNT, + /// as the raw attribute text. + /// [XmlAttribute("type")] public string Type { get; set; } + /// + /// Whether the counter counts UP or DOWN, as the raw + /// attribute text. + /// [XmlAttribute("countDirection")] public string CountDirection { get; set; } + /// + /// The value at which a warning is raised, as the raw attribute text. + /// [XmlAttribute("warning")] public string Warning { get; set; } + /// + /// The value at which the item is considered expired, as the raw + /// attribute text. + /// [XmlAttribute("limit")] public string Limit { get; set; } + /// + /// The value the counter started from, as the raw attribute text. + /// [XmlAttribute("initial")] public string Initial { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , parsing the type, count direction, and + /// numeric metadata. + /// public IItemLife ToItemLife() { var itemLife = new ItemLife(); @@ -41,6 +73,11 @@ public IItemLife ToItemLife() return itemLife; } + /// + /// Writes the given item-life counters to , + /// one ItemLife element per counter, omitting the warning, + /// limit, and initial attributes that are not set. + /// public static void WriteXml(XmlWriter writer, IEnumerable itemLifes) { if (itemLifes != null) diff --git a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlLocation.cs b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlLocation.cs index fdd32897b..426bd25f8 100644 --- a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlLocation.cs +++ b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlLocation.cs @@ -8,36 +8,76 @@ namespace MTConnect.Assets.Xml.CuttingTools { + /// + /// XML serialization surrogate for a cutting tool's Location within + /// a tool-handling system. Mirrors the on-the-wire element and converts to + /// the strongly-typed model. + /// public class XmlLocation { + /// + /// The location's position value, carried as the element text. + /// [XmlAttribute("value")] public string Value { get; set; } + /// + /// The kind of location, such as POT or SPINDLE, as the + /// raw attribute text. + /// [XmlAttribute("type")] public string Type { get; set; } + /// + /// The number of pots beyond this one, in the positive direction, the + /// tool occupies, as the raw attribute text. + /// [XmlAttribute("positiveOverlap")] public string PositiveOverlap { get; set; } + /// + /// The number of pots beyond this one, in the negative direction, the + /// tool occupies, as the raw attribute text. + /// [XmlAttribute("negativeOverlap")] public string NegativeOverlap { get; set; } + /// + /// The identifier of the turret holding the tool. + /// [XmlAttribute("turret")] public string Turret { get; set; } + /// + /// The identifier of the tool magazine holding the tool. + /// [XmlAttribute("toolMagazine")] public string ToolMagazine { get; set; } + /// + /// The identifier of the tool bar holding the tool. + /// [XmlAttribute("toolBar")] public string ToolBar { get; set; } + /// + /// The identifier of the tool rack holding the tool. + /// [XmlAttribute("toolRack")] public string ToolRack { get; set; } + /// + /// The identifier of the automatic tool changer handling the tool. + /// [XmlAttribute("automaticToolChanger")] public string AutomaticToolChanger { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , parsing the overlap values and the location + /// type. + /// public ILocation ToLocation() { var location = new Location(); @@ -53,6 +93,11 @@ public ILocation ToLocation() return location; } + /// + /// Writes the given to + /// as a Location element, omitting the optional tool-handling + /// identifiers that are not set. + /// public static void WriteXml(XmlWriter writer, ILocation location) { if (location != null) diff --git a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlMeasurement.cs b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlMeasurement.cs index 209fff8e9..d8fa261b6 100644 --- a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlMeasurement.cs +++ b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlMeasurement.cs @@ -8,36 +8,77 @@ namespace MTConnect.Assets.Xml.CuttingTools { + /// + /// XML serialization surrogate for a cutting-tool Measurement. + /// Mirrors the on-the-wire element, where the dimension is carried as the + /// element text and its metadata as attributes, and converts to the + /// strongly-typed model. + /// public class XmlMeasurement { + /// + /// The kind of measurement, such as OverallToolLength or + /// BodyDiameterMax. + /// [XmlAttribute("type")] public string Type { get; set; } + /// + /// The number of significant digits in the reported value, as the raw + /// attribute text. + /// [XmlAttribute("significantDigits")] public string SignificantDigits { get; set; } + /// + /// The engineering units the value is reported in. + /// [XmlAttribute("units")] public string Units { get; set; } + /// + /// The units the value was originally measured in before conversion. + /// [XmlAttribute("nativeUnits")] public string NativeUnits { get; set; } + /// + /// The short code identifying the measurement on tooling data sheets. + /// [XmlAttribute("code")] public string Code { get; set; } + /// + /// The maximum tolerated value, as the raw attribute text. + /// [XmlAttribute("maximum")] public string Maximum { get; set; } + /// + /// The minimum tolerated value, as the raw attribute text. + /// [XmlAttribute("minimum")] public string Minimum { get; set; } + /// + /// The nominal (target) value, as the raw attribute text. + /// [XmlAttribute("nominal")] public string Nominal { get; set; } + /// + /// The measured value, carried as the element text. + /// [XmlText] public string Value { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , parsing the numeric text values + /// and instantiating the concrete measurement class that matches + /// . + /// public IToolingMeasurement ToMeasurement() { var measurement = new ToolingMeasurement(); @@ -53,6 +94,11 @@ public IToolingMeasurement ToMeasurement() return ToolingMeasurement.Create(Type, measurement); } + /// + /// Writes the given measurements to wrapped in + /// a Measurements element, one element per measurement named + /// after its type, omitting optional attributes that are not set. + /// public static void WriteXml(XmlWriter writer, IEnumerable measurements) { if (!measurements.IsNullOrEmpty()) diff --git a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlMeasurements.g.cs b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlMeasurements.g.cs index acecbc731..100a7fe7d 100644 --- a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlMeasurements.g.cs +++ b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlMeasurements.g.cs @@ -5,68 +5,388 @@ namespace MTConnect.Assets.Xml.CuttingTools { - public class XmlBodyDiameterMaxMeasurement : XmlMeasurement { public XmlBodyDiameterMaxMeasurement() { Type = BodyDiameterMaxMeasurement.TypeId; } } - - public class XmlBodyLengthMaxMeasurement : XmlMeasurement { public XmlBodyLengthMaxMeasurement() { Type = BodyLengthMaxMeasurement.TypeId; } } - - public class XmlChamferFlatLengthMeasurement : XmlMeasurement { public XmlChamferFlatLengthMeasurement() { Type = ChamferFlatLengthMeasurement.TypeId; } } - - public class XmlChamferWidthMeasurement : XmlMeasurement { public XmlChamferWidthMeasurement() { Type = ChamferWidthMeasurement.TypeId; } } - - public class XmlCornerRadiusMeasurement : XmlMeasurement { public XmlCornerRadiusMeasurement() { Type = CornerRadiusMeasurement.TypeId; } } - - public class XmlCuttingDiameterMaxMeasurement : XmlMeasurement { public XmlCuttingDiameterMaxMeasurement() { Type = CuttingDiameterMaxMeasurement.TypeId; } } - - public class XmlCuttingDiameterMeasurement : XmlMeasurement { public XmlCuttingDiameterMeasurement() { Type = CuttingDiameterMeasurement.TypeId; } } - - public class XmlCuttingEdgeLengthMeasurement : XmlMeasurement { public XmlCuttingEdgeLengthMeasurement() { Type = CuttingEdgeLengthMeasurement.TypeId; } } - - public class XmlCuttingHeightMeasurement : XmlMeasurement { public XmlCuttingHeightMeasurement() { Type = CuttingHeightMeasurement.TypeId; } } - - public class XmlCuttingReferencePointMeasurement : XmlMeasurement { public XmlCuttingReferencePointMeasurement() { Type = CuttingReferencePointMeasurement.TypeId; } } - - public class XmlDepthOfCutMaxMeasurement : XmlMeasurement { public XmlDepthOfCutMaxMeasurement() { Type = DepthOfCutMaxMeasurement.TypeId; } } - - public class XmlDriveAngleMeasurement : XmlMeasurement { public XmlDriveAngleMeasurement() { Type = DriveAngleMeasurement.TypeId; } } - - public class XmlFlangeDiameterMaxMeasurement : XmlMeasurement { public XmlFlangeDiameterMaxMeasurement() { Type = FlangeDiameterMaxMeasurement.TypeId; } } - - public class XmlFlangeDiameterMeasurement : XmlMeasurement { public XmlFlangeDiameterMeasurement() { Type = FlangeDiameterMeasurement.TypeId; } } - - public class XmlFunctionalLengthMeasurement : XmlMeasurement { public XmlFunctionalLengthMeasurement() { Type = FunctionalLengthMeasurement.TypeId; } } - - public class XmlFunctionalWidthMeasurement : XmlMeasurement { public XmlFunctionalWidthMeasurement() { Type = FunctionalWidthMeasurement.TypeId; } } - - public class XmlIncribedCircleDiameterMeasurement : XmlMeasurement { public XmlIncribedCircleDiameterMeasurement() { Type = IncribedCircleDiameterMeasurement.TypeId; } } - - public class XmlInsertWidthMeasurement : XmlMeasurement { public XmlInsertWidthMeasurement() { Type = InsertWidthMeasurement.TypeId; } } - - public class XmlOverallToolLengthMeasurement : XmlMeasurement { public XmlOverallToolLengthMeasurement() { Type = OverallToolLengthMeasurement.TypeId; } } - - public class XmlPointAngleMeasurement : XmlMeasurement { public XmlPointAngleMeasurement() { Type = PointAngleMeasurement.TypeId; } } - - public class XmlProtrudingLengthMeasurement : XmlMeasurement { public XmlProtrudingLengthMeasurement() { Type = ProtrudingLengthMeasurement.TypeId; } } - - public class XmlShankDiameterMeasurement : XmlMeasurement { public XmlShankDiameterMeasurement() { Type = ShankDiameterMeasurement.TypeId; } } - - public class XmlShankHeightMeasurement : XmlMeasurement { public XmlShankHeightMeasurement() { Type = ShankHeightMeasurement.TypeId; } } - - public class XmlShankLengthMeasurement : XmlMeasurement { public XmlShankLengthMeasurement() { Type = ShankLengthMeasurement.TypeId; } } - - public class XmlStepDiameterLengthMeasurement : XmlMeasurement { public XmlStepDiameterLengthMeasurement() { Type = StepDiameterLengthMeasurement.TypeId; } } - - public class XmlStepIncludedAngleMeasurement : XmlMeasurement { public XmlStepIncludedAngleMeasurement() { Type = StepIncludedAngleMeasurement.TypeId; } } - - public class XmlToolCuttingEdgeAngleMeasurement : XmlMeasurement { public XmlToolCuttingEdgeAngleMeasurement() { Type = ToolCuttingEdgeAngleMeasurement.TypeId; } } - - public class XmlToolLeadAngleMeasurement : XmlMeasurement { public XmlToolLeadAngleMeasurement() { Type = ToolLeadAngleMeasurement.TypeId; } } - - public class XmlToolOrientationMeasurement : XmlMeasurement { public XmlToolOrientationMeasurement() { Type = ToolOrientationMeasurement.TypeId; } } - - public class XmlUsableLengthMaxMeasurement : XmlMeasurement { public XmlUsableLengthMaxMeasurement() { Type = UsableLengthMaxMeasurement.TypeId; } } - - public class XmlWeightMeasurement : XmlMeasurement { public XmlWeightMeasurement() { Type = WeightMeasurement.TypeId; } } - - public class XmlWiperEdgeLengthMeasurement : XmlMeasurement { public XmlWiperEdgeLengthMeasurement() { Type = WiperEdgeLengthMeasurement.TypeId; } } - -} \ No newline at end of file + /// + /// XML serialization wrapper for the BodyDiameterMax cutting-tool measurement. + /// Largest diameter of the body of a tool item. + /// + public class XmlBodyDiameterMaxMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (BodyDiameterMax). + /// + public XmlBodyDiameterMaxMeasurement() { Type = BodyDiameterMaxMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the BodyLengthMax cutting-tool measurement. + /// Distance measured along the X axis from that point of the item closest to the workpiece, including the cutting item for a tool item but excluding a protruding locking mechanism for an adaptive item, to either the front of the flange on a flanged body or the beginning of the connection interface feature on the machine side for cylindrical or prismatic shanks. + /// + public class XmlBodyLengthMaxMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (BodyLengthMax). + /// + public XmlBodyLengthMaxMeasurement() { Type = BodyLengthMaxMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the ChamferFlatLength cutting-tool measurement. + /// Flat length of a chamfer. + /// + public class XmlChamferFlatLengthMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (ChamferFlatLength). + /// + public XmlChamferFlatLengthMeasurement() { Type = ChamferFlatLengthMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the ChamferWidth cutting-tool measurement. + /// Width of the chamfer. + /// + public class XmlChamferWidthMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (ChamferWidth). + /// + public XmlChamferWidthMeasurement() { Type = ChamferWidthMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the CornerRadius cutting-tool measurement. + /// Nominal radius of a rounded corner measured in the X Y-plane. + /// + public class XmlCornerRadiusMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (CornerRadius). + /// + public XmlCornerRadiusMeasurement() { Type = CornerRadiusMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the CuttingDiameterMax cutting-tool measurement. + /// Maximum diameter of a circle on which the defined point Pk of each of the master inserts is located on a tool item. The normal of the machined peripheral surface points towards the axis of the cutting tool. + /// + public class XmlCuttingDiameterMaxMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (CuttingDiameterMax). + /// + public XmlCuttingDiameterMaxMeasurement() { Type = CuttingDiameterMaxMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the CuttingDiameter cutting-tool measurement. + /// Diameter of a circle on which the defined point Pk located on this cutting tool. The normal of the machined peripheral surface points towards the axis of the cutting tool. + /// + public class XmlCuttingDiameterMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (CuttingDiameter). + /// + public XmlCuttingDiameterMeasurement() { Type = CuttingDiameterMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the CuttingEdgeLength cutting-tool measurement. + /// Theoretical length of the cutting edge of a cutting item over sharp corners. + /// + public class XmlCuttingEdgeLengthMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (CuttingEdgeLength). + /// + public XmlCuttingEdgeLengthMeasurement() { Type = CuttingEdgeLengthMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the CuttingHeight cutting-tool measurement. + /// Distance from the basal plane of the tool item to the cutting point. + /// + public class XmlCuttingHeightMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (CuttingHeight). + /// + public XmlCuttingHeightMeasurement() { Type = CuttingHeightMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the CuttingReferencePoint cutting-tool measurement. + /// Theoretical sharp point of the cutting tool from which the major functional dimensions are taken. + /// + public class XmlCuttingReferencePointMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (CuttingReferencePoint). + /// + public XmlCuttingReferencePointMeasurement() { Type = CuttingReferencePointMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the DepthOfCutMax cutting-tool measurement. + /// Maximum engagement of the cutting edge or edges with the workpiece measured perpendicular to the feed motion. + /// + public class XmlDepthOfCutMaxMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (DepthOfCutMax). + /// + public XmlDepthOfCutMaxMeasurement() { Type = DepthOfCutMaxMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the DriveAngle cutting-tool measurement. + /// Angle between the driving mechanism locator on a tool item and the main cutting edge. + /// + public class XmlDriveAngleMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (DriveAngle). + /// + public XmlDriveAngleMeasurement() { Type = DriveAngleMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the FlangeDiameterMax cutting-tool measurement. + /// Dimension between two parallel tangents on the outside edge of a flange. + /// + public class XmlFlangeDiameterMaxMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (FlangeDiameterMax). + /// + public XmlFlangeDiameterMaxMeasurement() { Type = FlangeDiameterMaxMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the FlangeDiameter cutting-tool measurement. + /// Dimension between two parallel tangents on the outside edge of a flange. + /// + public class XmlFlangeDiameterMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (FlangeDiameter). + /// + public XmlFlangeDiameterMeasurement() { Type = FlangeDiameterMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the FunctionalLength cutting-tool measurement. + /// Distance from the gauge plane or from the end of the shank to the furthest point on the tool, if a gauge plane does not exist, to the cutting reference point determined by the main function of the tool.The CuttingTool functional length will be the length of the entire tool, not a single cutting item. Each CuttingItem can have an independent FunctionalLength represented in its measurements. + /// + public class XmlFunctionalLengthMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (FunctionalLength). + /// + public XmlFunctionalLengthMeasurement() { Type = FunctionalLengthMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the FunctionalWidth cutting-tool measurement. + /// Distance between the cutting reference point and the rear backing surface of a turning tool or the axis of a boring bar. + /// + public class XmlFunctionalWidthMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (FunctionalWidth). + /// + public XmlFunctionalWidthMeasurement() { Type = FunctionalWidthMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the IncribedCircleDiameter cutting-tool measurement. + /// Diameter of a circle to which all edges of a equilateral and round regular insert are tangential. + /// + public class XmlIncribedCircleDiameterMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (IncribedCircleDiameter). + /// + public XmlIncribedCircleDiameterMeasurement() { Type = IncribedCircleDiameterMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the InsertWidth cutting-tool measurement. + /// W1 is used for the insert width when an inscribed circle diameter is not practical. + /// + public class XmlInsertWidthMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (InsertWidth). + /// + public XmlInsertWidthMeasurement() { Type = InsertWidthMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the OverallToolLength cutting-tool measurement. + /// Largest length dimension of the cutting tool including the master insert where applicable. + /// + public class XmlOverallToolLengthMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (OverallToolLength). + /// + public XmlOverallToolLengthMeasurement() { Type = OverallToolLengthMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the PointAngle cutting-tool measurement. + /// Angle between the major cutting edge and the same cutting edge rotated by 180 degrees about the tool axis. + /// + public class XmlPointAngleMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (PointAngle). + /// + public XmlPointAngleMeasurement() { Type = PointAngleMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the ProtrudingLength cutting-tool measurement. + /// Dimension from the yz-plane to the furthest point of the tool item or adaptive item measured in the -X direction. + /// + public class XmlProtrudingLengthMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (ProtrudingLength). + /// + public XmlProtrudingLengthMeasurement() { Type = ProtrudingLengthMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the ShankDiameter cutting-tool measurement. + /// Dimension of the diameter of a cylindrical portion of a tool item or an adaptive item that can participate in a connection. + /// + public class XmlShankDiameterMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (ShankDiameter). + /// + public XmlShankDiameterMeasurement() { Type = ShankDiameterMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the ShankHeight cutting-tool measurement. + /// Dimension of the height of the shank. + /// + public class XmlShankHeightMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (ShankHeight). + /// + public XmlShankHeightMeasurement() { Type = ShankHeightMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the ShankLength cutting-tool measurement. + /// Dimension of the length of the shank. + /// + public class XmlShankLengthMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (ShankLength). + /// + public XmlShankLengthMeasurement() { Type = ShankLengthMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the StepDiameterLength cutting-tool measurement. + /// Length of a portion of a stepped tool that is related to a corresponding cutting diameter measured from the cutting reference point of that cutting diameter to the point on the next cutting edge at which the diameter starts to change. + /// + public class XmlStepDiameterLengthMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (StepDiameterLength). + /// + public XmlStepDiameterLengthMeasurement() { Type = StepDiameterLengthMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the StepIncludedAngle cutting-tool measurement. + /// Angle between a major edge on a step of a stepped tool and the same cutting edge rotated 180 degrees about its tool axis. + /// + public class XmlStepIncludedAngleMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (StepIncludedAngle). + /// + public XmlStepIncludedAngleMeasurement() { Type = StepIncludedAngleMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the ToolCuttingEdgeAngle cutting-tool measurement. + /// Angle between the tool cutting edge plane and the tool feed plane measured in a plane parallel the xy-plane. + /// + public class XmlToolCuttingEdgeAngleMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (ToolCuttingEdgeAngle). + /// + public XmlToolCuttingEdgeAngleMeasurement() { Type = ToolCuttingEdgeAngleMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the ToolLeadAngle cutting-tool measurement. + /// Angle between the tool cutting edge plane and a plane perpendicular to the tool feed plane measured in a plane parallel the xy-plane. + /// + public class XmlToolLeadAngleMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (ToolLeadAngle). + /// + public XmlToolLeadAngleMeasurement() { Type = ToolLeadAngleMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the ToolOrientation cutting-tool measurement. + /// Angle of the tool with respect to the workpiece for a given process. The value is application specific. + /// + public class XmlToolOrientationMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (ToolOrientation). + /// + public XmlToolOrientationMeasurement() { Type = ToolOrientationMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the UsableLengthMax cutting-tool measurement. + /// Maximum length of a cutting tool that can be used in a particular cutting operation including the non-cutting portions of the tool. + /// + public class XmlUsableLengthMaxMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (UsableLengthMax). + /// + public XmlUsableLengthMaxMeasurement() { Type = UsableLengthMaxMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the Weight cutting-tool measurement. + /// Total weight of the cutting tool in grams. The force exerted by the mass of the cutting tool. + /// + public class XmlWeightMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (Weight). + /// + public XmlWeightMeasurement() { Type = WeightMeasurement.TypeId; } + } + + /// + /// XML serialization wrapper for the WiperEdgeLength cutting-tool measurement. + /// Measure of the length of a wiper edge of a cutting item. + /// + public class XmlWiperEdgeLengthMeasurement : XmlMeasurement + { + /// + /// Initializes a new instance and fixes the measurement type to (WiperEdgeLength). + /// + public XmlWiperEdgeLengthMeasurement() { Type = WiperEdgeLengthMeasurement.TypeId; } + } + +} diff --git a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlProcessFeedRate.cs b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlProcessFeedRate.cs index 20afeed5e..efa484fff 100644 --- a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlProcessFeedRate.cs +++ b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlProcessFeedRate.cs @@ -7,21 +7,46 @@ namespace MTConnect.Assets.Xml.CuttingTools { + /// + /// XML serialization surrogate for the ProcessFeedRate of a + /// CuttingTool life cycle, carrying the feed rate the tool is intended to + /// run at with optional min/max/nominal bounds. + /// public class XmlProcessFeedRate { + /// + /// The maximum recommended feed rate, carried by the maximum + /// attribute. + /// [XmlAttribute("maximum")] public string Maximum { get; set; } + /// + /// The minimum recommended feed rate, carried by the minimum + /// attribute. + /// [XmlAttribute("minimum")] public string Minimum { get; set; } + /// + /// The nominal (target) feed rate, carried by the nominal + /// attribute. + /// [XmlAttribute("nominal")] public string Nominal { get; set; } + /// + /// The feed rate value, carried as the element's text content. + /// [XmlText] public string Value { get; set; } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing each populated attribute and + /// the value to a number. + /// public IProcessFeedRate ToProcessFeedRate() { var processFeedRate = new ProcessFeedRate(); @@ -32,6 +57,10 @@ public IProcessFeedRate ToProcessFeedRate() return processFeedRate; } + /// + /// Writes the ProcessFeedRate element, emitting the + /// min/max/nominal attributes and value only when populated. + /// public static void WriteXml(XmlWriter writer, IProcessFeedRate processFeedRate) { if (processFeedRate != null) diff --git a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlProcessSpindleSpeed.cs b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlProcessSpindleSpeed.cs index 10380f744..e2bedee82 100644 --- a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlProcessSpindleSpeed.cs +++ b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlProcessSpindleSpeed.cs @@ -7,21 +7,46 @@ namespace MTConnect.Assets.Xml.CuttingTools { + /// + /// XML serialization surrogate for the ProcessSpindleSpeed of a + /// CuttingTool life cycle, carrying the spindle speed the tool is intended + /// to run at with optional min/max/nominal bounds. + /// public class XmlProcessSpindleSpeed { + /// + /// The maximum recommended spindle speed, carried by the + /// maximum attribute. + /// [XmlAttribute("maximum")] public string Maximum { get; set; } + /// + /// The minimum recommended spindle speed, carried by the + /// minimum attribute. + /// [XmlAttribute("minimum")] public string Minimum { get; set; } + /// + /// The nominal (target) spindle speed, carried by the nominal + /// attribute. + /// [XmlAttribute("nominal")] public string Nominal { get; set; } + /// + /// The spindle speed value, carried as the element's text content. + /// [XmlText] public string Value { get; set; } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing each populated attribute + /// and the value to a number. + /// public IProcessSpindleSpeed ToProcessSpindleSpeed() { var processSpindleSpeed = new ProcessSpindleSpeed(); @@ -32,6 +57,10 @@ public IProcessSpindleSpeed ToProcessSpindleSpeed() return processSpindleSpeed; } + /// + /// Writes the ProcessSpindleSpeed element, emitting the + /// min/max/nominal attributes and value only when populated. + /// public static void WriteXml(XmlWriter writer, IProcessSpindleSpeed processSpindleSpeed) { if (processSpindleSpeed != null) diff --git a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlReconditionCount.cs b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlReconditionCount.cs index b6b6952c8..5497a46be 100644 --- a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlReconditionCount.cs +++ b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlReconditionCount.cs @@ -7,15 +7,33 @@ namespace MTConnect.Assets.Xml.CuttingTools { + /// + /// XML serialization surrogate for the ReconditionCount of a + /// CuttingTool life cycle, recording how many times the tool has been + /// reconditioned and the maximum number of reconditioning cycles allowed. + /// public class XmlReconditionCount { + /// + /// The maximum number of reconditioning cycles permitted, carried by + /// the maximumCount attribute. + /// [XmlAttribute("maximumCount")] public string MaximumCount { get; set; } + /// + /// The number of times the tool has been reconditioned, carried as the + /// element's text content. + /// [XmlText] public string Value { get; set; } + /// + /// Converts this surrogate to a strongly-typed + /// , parsing the maximum count (when + /// present) and the value to integers. + /// public IReconditionCount ToReconditionCount() { var reconditionCount = new ReconditionCount(); @@ -24,6 +42,11 @@ public IReconditionCount ToReconditionCount() return reconditionCount; } + /// + /// Writes the ReconditionCount element, emitting the + /// maximumCount attribute only when present and the count as + /// element content. + /// public static void WriteXml(XmlWriter writer, IReconditionCount reconditionCount) { if (reconditionCount != null) diff --git a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlToolLife.cs b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlToolLife.cs index 071cb0be5..f8d19c2cc 100644 --- a/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlToolLife.cs +++ b/libraries/MTConnect.NET-XML/Assets/CuttingTools/XmlToolLife.cs @@ -8,27 +8,59 @@ namespace MTConnect.Assets.Xml.CuttingTools { + /// + /// XML serialization surrogate for a cutting tool's ToolLife counter. + /// Mirrors the on-the-wire element, where the accumulated value is the + /// element text and its metadata are attributes, and converts to the + /// strongly-typed model. + /// public class XmlToolLife { + /// + /// The kind of life counter, such as MINUTES or PART_COUNT, + /// as the raw attribute text. + /// [XmlAttribute("type")] public string Type { get; set; } + /// + /// Whether the counter counts UP or DOWN, as the raw + /// attribute text. + /// [XmlAttribute("countDirection")] public string CountDirection { get; set; } + /// + /// The value at which a warning is raised, as the raw attribute text. + /// [XmlAttribute("warning")] public string Warning { get; set; } + /// + /// The value at which the tool is considered expired, as the raw + /// attribute text. + /// [XmlAttribute("limit")] public string Limit { get; set; } + /// + /// The value the counter started from, as the raw attribute text. + /// [XmlAttribute("initial")] public string Initial { get; set; } + /// + /// The current accumulated life value, carried as the element text. + /// [XmlText] public double Value { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , parsing the type, count direction, and + /// numeric metadata. + /// public IToolLife ToToolLife() { var toolLife = new ToolLife(); @@ -41,6 +73,11 @@ public IToolLife ToToolLife() return toolLife; } + /// + /// Writes the given tool-life counters to , + /// one ToolLife element per counter, omitting the warning, + /// limit, and initial attributes that are not set. + /// public static void WriteXml(XmlWriter writer, IEnumerable toolLifes) { if (toolLifes != null) diff --git a/libraries/MTConnect.NET-XML/Assets/Files/XmlAbstractFileAsset.cs b/libraries/MTConnect.NET-XML/Assets/Files/XmlAbstractFileAsset.cs index 656563efb..3c7d6ba8f 100644 --- a/libraries/MTConnect.NET-XML/Assets/Files/XmlAbstractFileAsset.cs +++ b/libraries/MTConnect.NET-XML/Assets/Files/XmlAbstractFileAsset.cs @@ -6,23 +6,52 @@ namespace MTConnect.Assets.Xml.Files { + /// + /// Base XML serialization surrogate shared by the File and FileArchetype + /// asset surrogates, carrying the file metadata attributes and the optional + /// file property and comment collections. + /// public abstract class XmlAbstractFileAsset { + /// + /// The file name, carried by the name attribute. + /// [XmlAttribute("name")] public string Name { get; set; } + /// + /// The MIME media type of the file, carried by the mediaType + /// attribute. + /// [XmlAttribute("mediaType")] public string MediaType { get; set; } + /// + /// The functional category of the file (for example + /// INSTALLATION or DESIGN), carried by the + /// applicationCategory attribute. + /// [XmlAttribute("applicationCategory")] public string ApplicationCategory { get; set; } + /// + /// The kind of application the file targets, carried by the + /// applicationType attribute. + /// [XmlAttribute("applicationType")] public string ApplicationType { get; set; } + /// + /// Vendor-defined name/value file properties, serialized within the + /// FileProperties element. + /// [XmlElement("FileProperties")] public List FileProperties { get; set; } + /// + /// Timestamped comments associated with the file, serialized within the + /// FileComments element. + /// [XmlElement("FileComments")] public List FileComments { get; set; } } diff --git a/libraries/MTConnect.NET-XML/Assets/Files/XmlDestination.cs b/libraries/MTConnect.NET-XML/Assets/Files/XmlDestination.cs index fcda79f32..ed546cfde 100644 --- a/libraries/MTConnect.NET-XML/Assets/Files/XmlDestination.cs +++ b/libraries/MTConnect.NET-XML/Assets/Files/XmlDestination.cs @@ -8,12 +8,23 @@ namespace MTConnect.Assets.Xml.Files { + /// + /// XML serialization surrogate for a File asset Destination, + /// identifying a device the file is intended to be deployed to. + /// public class XmlDestination { + /// + /// The uuid of the target device, carried by the + /// deviceUuid attribute. + /// [XmlAttribute("deviceUuid")] public string DeviceUuid { get; set; } + /// + /// Converts this surrogate to a strongly-typed . + /// public IDestination ToDestination() { var destination = new Destination(); @@ -21,6 +32,10 @@ public IDestination ToDestination() return destination; } + /// + /// Writes the Destinations container with one Destination + /// element per device; nothing is written when the collection is empty. + /// public static void WriteXml(XmlWriter writer, IEnumerable destinations) { if (!destinations.IsNullOrEmpty()) diff --git a/libraries/MTConnect.NET-XML/Assets/Files/XmlFileAsset.cs b/libraries/MTConnect.NET-XML/Assets/Files/XmlFileAsset.cs index fb3eb9cf6..eb08cd01d 100644 --- a/libraries/MTConnect.NET-XML/Assets/Files/XmlFileAsset.cs +++ b/libraries/MTConnect.NET-XML/Assets/Files/XmlFileAsset.cs @@ -8,59 +8,117 @@ namespace MTConnect.Assets.Xml.Files { + /// + /// XML serialization surrogate for an MTConnect File asset. Mirrors + /// the on-the-wire element so the XML serializer can read and write it, then + /// converts to and from the strongly-typed model. + /// [XmlRoot("File")] public class XmlFileAsset : XmlAsset { + /// + /// The name of the file. + /// [XmlAttribute("name")] public string Name { get; set; } + /// + /// The MIME media type of the file's contents. + /// [XmlAttribute("mediaType")] public string MediaType { get; set; } + /// + /// The category of application that consumes the file, as the raw + /// attribute text. + /// [XmlAttribute("applicationCategory")] public string ApplicationCategory { get; set; } + /// + /// The type of application the file represents, as the raw attribute + /// text. + /// [XmlAttribute("applicationType")] public string ApplicationType { get; set; } + /// + /// The key/value properties that further describe the file. + /// [XmlArray("FileProperties")] [XmlArrayItem("FileProperty")] public List FileProperties { get; set; } + /// + /// The free-form comments associated with the file. + /// [XmlArray("FileComments")] [XmlArrayItem("FileComment")] public List FileComments { get; set; } + /// + /// The size of the file in bytes. + /// [XmlAttribute("size")] public int Size { get; set; } + /// + /// The version identifier of the file. + /// [XmlAttribute("versionId")] public string VersionId { get; set; } + /// + /// The lifecycle state of the file (for example PRODUCTION or + /// EXPERIMENTAL), as the raw attribute text. + /// [XmlAttribute("state")] public string State { get; set; } + /// + /// Where the file's contents can be retrieved from. + /// [XmlElement("FileLocation")] public XmlFileLocation FileLocation { get; set; } + /// + /// The cryptographic signature used to verify the file's integrity. + /// [XmlElement("Signature")] public string Signature { get; set; } + /// + /// The public key used to verify the file's signature. + /// [XmlElement("PublicKey")] public string PublicKey { get; set; } + /// + /// The destinations the file is intended to be distributed to. + /// [XmlArray("Destinations")] [XmlArrayItem("Destination")] public List Destinations { get; set; } + /// + /// The time the file was created, as the raw element text. + /// [XmlElement("CreationTime")] public string CreationTime { get; set; } + /// + /// The time the file was last modified, as the raw element text. + /// [XmlElement("ModificationTime")] public string ModificationTime { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , parsing each raw value and projecting the + /// nested collections into their model representations. + /// public override IAsset ToAsset() { var asset = new FileAsset(); @@ -122,6 +180,11 @@ public override IAsset ToAsset() return asset; } + /// + /// Writes the given to + /// as a File element, omitting optional values and collections + /// that are not set. + /// public static void WriteXml(XmlWriter writer, IAsset asset) { if (asset != null) diff --git a/libraries/MTConnect.NET-XML/Assets/Files/XmlFileComment.cs b/libraries/MTConnect.NET-XML/Assets/Files/XmlFileComment.cs index 59742141d..48a7b6a4d 100644 --- a/libraries/MTConnect.NET-XML/Assets/Files/XmlFileComment.cs +++ b/libraries/MTConnect.NET-XML/Assets/Files/XmlFileComment.cs @@ -9,15 +9,29 @@ namespace MTConnect.Assets.Xml.Files { + /// + /// XML serialization surrogate for a single FileComment, a + /// timestamped free-text note attached to a File asset. + /// public class XmlFileComment { + /// + /// When the comment was made, carried by the timestamp + /// attribute in ISO 8601 round-trip form. + /// [XmlAttribute("timestamp")] public DateTime Timestamp { get; set; } + /// + /// The comment text, carried as the element's text content. + /// [XmlText] public string Value { get; set; } + /// + /// Converts this surrogate to a strongly-typed . + /// public IFileComment ToFileComment() { var fileComment = new FileComment(); @@ -26,6 +40,11 @@ public IFileComment ToFileComment() return fileComment; } + /// + /// Writes the FileComments container with one FileComment + /// element per comment, formatting each timestamp in ISO 8601 + /// round-trip form; nothing is written when the collection is empty. + /// public static void WriteXml(XmlWriter writer, IEnumerable fileComments) { if (!fileComments.IsNullOrEmpty()) diff --git a/libraries/MTConnect.NET-XML/Assets/Files/XmlFileLocation.cs b/libraries/MTConnect.NET-XML/Assets/Files/XmlFileLocation.cs index 80bc7c0f3..f76b329bf 100644 --- a/libraries/MTConnect.NET-XML/Assets/Files/XmlFileLocation.cs +++ b/libraries/MTConnect.NET-XML/Assets/Files/XmlFileLocation.cs @@ -7,15 +7,29 @@ namespace MTConnect.Assets.Xml.Files { + /// + /// XML serialization surrogate for a File asset FileLocation, the + /// XLink that points to where the file content can be retrieved. + /// public class XmlFileLocation { + /// + /// The URI of the file content, carried by the href attribute. + /// [XmlAttribute("href")] public string Href { get; set; } + /// + /// The XLink type of the reference, carried by the xlink:type + /// attribute. + /// [XmlAttribute("xLinkType")] public string XLinkType { get; set; } + /// + /// Converts this surrogate to a strongly-typed . + /// public IFileLocation ToFileLocation() { var fileLocation = new FileLocation(); @@ -24,6 +38,10 @@ public IFileLocation ToFileLocation() return fileLocation; } + /// + /// Writes the FileLocation element, emitting the required + /// href attribute and the optional xlink:type attribute. + /// public static void WriteXml(XmlWriter writer, IFileLocation fileLocation) { if (fileLocation != null) diff --git a/libraries/MTConnect.NET-XML/Assets/Files/XmlFileProperty.cs b/libraries/MTConnect.NET-XML/Assets/Files/XmlFileProperty.cs index 66d99334a..a6fa9c6ef 100644 --- a/libraries/MTConnect.NET-XML/Assets/Files/XmlFileProperty.cs +++ b/libraries/MTConnect.NET-XML/Assets/Files/XmlFileProperty.cs @@ -8,15 +8,28 @@ namespace MTConnect.Assets.Xml.Files { + /// + /// XML serialization surrogate for a single FileProperty, a + /// vendor-defined name/value pair describing a File asset. + /// public class XmlFileProperty { + /// + /// The property name, carried by the name attribute. + /// [XmlAttribute("name")] public string Name { get; set; } + /// + /// The property value, carried as the element's text content. + /// [XmlText] public string Value { get; set; } + /// + /// Converts this surrogate to a strongly-typed . + /// public IFileProperty ToFileProperty() { var fileProperty = new FileProperty(); @@ -25,6 +38,11 @@ public IFileProperty ToFileProperty() return fileProperty; } + /// + /// Writes the FileProperties container with one + /// FileProperty element per property; nothing is written when + /// the collection is empty. + /// public static void WriteXml(XmlWriter writer, IEnumerable fileProperties) { if (!fileProperties.IsNullOrEmpty()) diff --git a/libraries/MTConnect.NET-XML/Assets/QIF/XmlQIFDocument.cs b/libraries/MTConnect.NET-XML/Assets/QIF/XmlQIFDocument.cs index 6e71db33c..57e669372 100644 --- a/libraries/MTConnect.NET-XML/Assets/QIF/XmlQIFDocument.cs +++ b/libraries/MTConnect.NET-XML/Assets/QIF/XmlQIFDocument.cs @@ -7,18 +7,35 @@ namespace MTConnect.Assets.QIF { + /// + /// XML serialization surrogate that captures an embedded QIF (Quality + /// Information Framework) document verbatim. Custom + /// handling is used so the foreign QIF XML + /// is preserved as raw markup rather than mapped to a typed model. + /// public class XmlQIFDocument : IXmlSerializable { + /// + /// The embedded QIF document as a raw XML fragment. + /// public string QIFDocument { get; set; } #region "Xml Serialization" + /// + /// No-op; QIF content is written by the owning asset surrogate via its + /// static WriteXml. + /// public void WriteXml(XmlWriter writer) { // Use static WriteXml() } + /// + /// Reads the QIF document by capturing the element's outer XML + /// verbatim, then advancing past it. + /// public void ReadXml(XmlReader reader) { QIFDocument = reader.ReadOuterXml(); @@ -27,6 +44,10 @@ public void ReadXml(XmlReader reader) reader.Skip(); } + /// + /// Returns null; no inline schema is provided for the foreign + /// QIF content. + /// public XmlSchema GetSchema() { return (null); diff --git a/libraries/MTConnect.NET-XML/Assets/QIF/XmlQIFDocumentWrapperAsset.cs b/libraries/MTConnect.NET-XML/Assets/QIF/XmlQIFDocumentWrapperAsset.cs index f23942e13..0c4778997 100644 --- a/libraries/MTConnect.NET-XML/Assets/QIF/XmlQIFDocumentWrapperAsset.cs +++ b/libraries/MTConnect.NET-XML/Assets/QIF/XmlQIFDocumentWrapperAsset.cs @@ -7,15 +7,33 @@ namespace MTConnect.Assets.QIF { + /// + /// XML serialization surrogate for a QIFDocumentWrapper asset, which + /// embeds a foreign QIF (Quality Information Framework) document inside an + /// MTConnect asset envelope. + /// [XmlRoot("QIFDocumentWrapper")] public class XmlQIFDocumentWrapperAsset : XmlAsset { + /// + /// The QIF document classification, carried by the + /// qifDocumentType attribute. + /// [XmlAttribute("qifDocumentType")] public string QIFDocumentType { get; set; } - + + /// + /// The embedded QIF document, captured verbatim as raw XML. + /// public XmlQIFDocument QIFDocument { get; set; } + /// + /// Converts this surrogate to a strongly-typed + /// , copying the shared asset + /// fields, mapping the document type to its enumeration, and copying + /// the embedded QIF markup. + /// public override IAsset ToAsset() { var asset = new QIFDocumentWrapperAsset(); @@ -34,6 +52,11 @@ public override IAsset ToAsset() return asset; } + /// + /// Writes the QIFDocumentWrapper element, emitting the shared + /// asset attributes, the qifDocumentType attribute, and the + /// embedded QIF document as raw markup. + /// public static void WriteXml(XmlWriter writer, IAsset asset) { if (asset != null) diff --git a/libraries/MTConnect.NET-XML/Assets/RawMaterials/XmlMaterial.cs b/libraries/MTConnect.NET-XML/Assets/RawMaterials/XmlMaterial.cs index 98f78c324..5c8cd40fc 100644 --- a/libraries/MTConnect.NET-XML/Assets/RawMaterials/XmlMaterial.cs +++ b/libraries/MTConnect.NET-XML/Assets/RawMaterials/XmlMaterial.cs @@ -7,33 +7,66 @@ namespace MTConnect.Assets.Xml.RawMaterials { + /// + /// XML serialization surrogate for the Material a raw-material asset + /// is made of. Mirrors the on-the-wire element and converts to and from the + /// strongly-typed model. + /// public class XmlMaterial { + /// + /// The identifier of the material. + /// [XmlAttribute("id")] public string Id { get; set; } + /// + /// The name of the material. + /// [XmlAttribute("name")] public string Name { get; set; } + /// + /// The type of the material. + /// [XmlAttribute("type")] public string Type { get; set; } + /// + /// The lot the material belongs to. + /// [XmlElement("Lot")] public string Lot { get; set; } + /// + /// The manufacturer of the material. + /// [XmlElement("Manufacturer")] public string Manufacturer { get; set; } + /// + /// The date the material was manufactured, as the raw element text. + /// [XmlElement("ManufacturingDate")] public string ManufacturingDate { get; set; } + /// + /// The manufacturer's code for the material. + /// [XmlElement("ManufacturingCode")] public string ManufacturingCode { get; set; } + /// + /// The standardized material code. + /// [XmlElement("MaterialCode")] public string MaterialCode { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , parsing the manufacturing date. + /// public IMaterial ToMaterial() { var material = new Material(); @@ -48,6 +81,11 @@ public IMaterial ToMaterial() return material; } + /// + /// Writes the given to + /// as a Material element, omitting optional child elements that + /// are not set. + /// public static void WriteXml(XmlWriter writer, IMaterial material) { if (material != null) diff --git a/libraries/MTConnect.NET-XML/Assets/RawMaterials/XmlRawMaterialAsset.cs b/libraries/MTConnect.NET-XML/Assets/RawMaterials/XmlRawMaterialAsset.cs index 80d6854d7..fe8ff32c9 100644 --- a/libraries/MTConnect.NET-XML/Assets/RawMaterials/XmlRawMaterialAsset.cs +++ b/libraries/MTConnect.NET-XML/Assets/RawMaterials/XmlRawMaterialAsset.cs @@ -7,58 +7,124 @@ namespace MTConnect.Assets.Xml.RawMaterials { + /// + /// XML serialization surrogate for an MTConnect RawMaterial asset. + /// Mirrors the on-the-wire element so the XML serializer can read and write + /// it, then converts to and from the strongly-typed + /// model. + /// [XmlRoot("RawMaterial")] public class XmlRawMaterialAsset : XmlAsset { + /// + /// The optional human-readable name of the raw material. + /// [XmlAttribute("name")] public string Name { get; set; } + /// + /// The type of container holding the raw material, such as a bottle or + /// cartridge. + /// [XmlAttribute("containerType")] public string ContainerType { get; set; } + /// + /// The manufacturing process the raw material is intended for. + /// [XmlAttribute("processKind")] public string ProcessKind { get; set; } + /// + /// The serial number that uniquely identifies this raw material. + /// [XmlAttribute("serialNumber")] public string SerialNumber { get; set; } + /// + /// The physical form of the material (for example BAR, + /// BLOCK, or POWDER) as the raw element text. + /// [XmlElement("Form")] public string Form { get; set; } + /// + /// Whether the container currently holds material, as the raw boolean + /// element text. + /// [XmlElement("HasMaterial")] public string HasMaterial { get; set; } + /// + /// The date the raw material was manufactured, as the raw element text. + /// [XmlElement("ManufacturingDate")] public string ManufacturingDate { get; set; } + /// + /// The date the raw material was first used, as the raw element text. + /// [XmlElement("FirstUseDate")] public string FirstUseDate { get; set; } + /// + /// The date the raw material was last used, as the raw element text. + /// [XmlElement("LastUseDate")] public string LastUseDate { get; set; } + /// + /// The volume of unused material when first received, as the raw + /// element text. + /// [XmlElement("InitialVolume")] public string InitialVolume { get; set; } + /// + /// The dimension of unused material when first received, as the raw + /// element text. + /// [XmlElement("InitialDimension")] public string InitialDimension { get; set; } + /// + /// The number of individual pieces of material when first received, as + /// the raw element text. + /// [XmlElement("InitialQuantity")] public string InitialQuantity { get; set; } + /// + /// The current volume of unused material, as the raw element text. + /// [XmlElement("CurrentVolume")] public string CurrentVolume { get; set; } + /// + /// The current dimension of unused material, as the raw element text. + /// [XmlElement("CurrentDimension")] public string CurrentDimension { get; set; } + /// + /// The current number of individual pieces of material, as the raw + /// element text. + /// [XmlElement("CurrentQuantity")] public string CurrentQuantity { get; set; } + /// + /// The material the raw material is made of. + /// [XmlElement("Material")] public XmlMaterial Material { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , parsing each raw element value into + /// its model representation. + /// public override IAsset ToAsset() { var asset = new RawMaterialAsset(); @@ -96,6 +162,11 @@ public override IAsset ToAsset() return asset; } + /// + /// Writes the given to + /// as a RawMaterial element, omitting optional values that are + /// not set. + /// public static void WriteXml(XmlWriter writer, IAsset asset) { if (asset != null) diff --git a/libraries/MTConnect.NET-XML/Assets/XmlAsset.cs b/libraries/MTConnect.NET-XML/Assets/XmlAsset.cs index 65c1229e8..a8701e58d 100644 --- a/libraries/MTConnect.NET-XML/Assets/XmlAsset.cs +++ b/libraries/MTConnect.NET-XML/Assets/XmlAsset.cs @@ -13,6 +13,12 @@ namespace MTConnect.Assets.Xml { + /// + /// Base XML serialization surrogate for MTConnect assets. Carries the + /// attributes common to every asset and provides the type-driven + /// (de)serialization plumbing that dispatches to the concrete asset + /// surrogate matching an asset's type. + /// public class XmlAsset { private static readonly Dictionary _serializers = new Dictionary(); @@ -20,28 +26,56 @@ public class XmlAsset private static Dictionary _types; + /// + /// The identifier that uniquely identifies the asset. + /// [XmlAttribute("assetId")] public string AssetId { get; set; } + /// + /// The MTConnect asset type, such as CuttingTool or File. + /// [XmlAttribute("type")] public string Type { get; set; } + /// + /// The time the asset was last modified. + /// [XmlAttribute("timestamp")] public DateTime Timestamp { get; set; } + /// + /// The UUID of the device that supplied the asset. + /// [XmlAttribute("deviceUuid")] public string DeviceUuid { get; set; } + /// + /// Whether the asset has been removed. + /// [XmlAttribute("removed")] public bool Removed { get; set; } + /// + /// The free-form description of the asset. + /// [XmlAttribute("description")] public string Description { get; set; } + /// + /// Converts this surrogate into the strongly-typed asset model. + /// Overridden by each concrete asset surrogate; the base implementation + /// returns null. + /// public virtual IAsset ToAsset() { return null; } + /// + /// Deserializes an asset XML document into a strongly-typed + /// , selecting the surrogate that matches the given + /// asset type name. + /// public static IAsset FromXml(string type, byte[] xmlBytes) { var asset = Asset.Create(type); @@ -56,6 +90,12 @@ public static IAsset FromXml(string type, byte[] xmlBytes) return default; } + /// + /// Deserializes an asset XML document into a strongly-typed + /// using the given surrogate + /// , caching the per + /// type. Returns the default value if the input cannot be parsed. + /// public static IAsset FromXml(Type type, byte[] xmlBytes) { if (type != null && xmlBytes != null && xmlBytes.Length > 0) @@ -102,6 +142,11 @@ public static IAsset FromXml(Type type, byte[] xmlBytes) return default; } + /// + /// Writes the given to by + /// dispatching to the WriteXml method of the concrete surrogate + /// that matches the asset's type. + /// public static void WriteXml(XmlWriter writer, IAsset asset) { try @@ -123,19 +168,30 @@ public static void WriteXml(XmlWriter writer, IAsset asset) catch { } } + /// + /// Writes the attributes common to every asset (assetId, + /// deviceUuid, timestamp, and removed) onto the + /// current element. Intended to be called by concrete surrogates after + /// opening their root element. + /// public static void WriteCommonXml(XmlWriter writer, IAsset asset) { if (asset != null) { // Write Properties writer.WriteAttributeString("assetId", asset.AssetId); - writer.WriteAttributeString("deviceUuid", asset.DeviceUuid); - writer.WriteAttributeString("timestamp", asset.Timestamp.ToString("o")); - if (asset.Removed) writer.WriteAttributeString("removed", "true"); + writer.WriteAttributeString("deviceUuid", asset.DeviceUuid); + writer.WriteAttributeString("timestamp", asset.Timestamp.ToString("o")); + if (asset.Removed) writer.WriteAttributeString("removed", "true"); } } + /// + /// Serializes the given to a + /// of XML, optionally indented, returning null if serialization + /// fails. + /// public static Stream ToXml(IAsset asset, bool indent = false) { try @@ -176,6 +232,11 @@ public static Stream ToXml(IAsset asset, bool indent = false) return null; } + /// + /// Resolves the concrete surrogate registered for + /// the given asset type name, or null when none is known. The + /// surrogate map is built once on first use. + /// public static Type GetAssetType(string type) { if (!string.IsNullOrEmpty(type)) diff --git a/libraries/MTConnect.NET-XML/Assets/XmlAssetCollection.cs b/libraries/MTConnect.NET-XML/Assets/XmlAssetCollection.cs index 9d33bdec5..3c71568f3 100644 --- a/libraries/MTConnect.NET-XML/Assets/XmlAssetCollection.cs +++ b/libraries/MTConnect.NET-XML/Assets/XmlAssetCollection.cs @@ -9,18 +9,34 @@ namespace MTConnect.Assets.Xml { + /// + /// XML serialization helper for the Assets container of an + /// MTConnectAssets document. Holds the strongly-typed assets and writes or + /// reads them as their type-named child elements, dispatching to the + /// per-type asset surrogates. + /// public class XmlAssetCollection { private readonly bool _indentOutput = false; + /// + /// The assets contained in the collection. + /// [XmlArray("Assets")] [XmlArrayItem(typeof(XmlCuttingToolAsset), ElementName = "CuttingTool")] public List Assets { get; set; } + /// + /// Creates an empty collection. + /// public XmlAssetCollection() { Assets = new List(); } + /// + /// Creates a collection containing the single given asset, recording + /// the indentation preference for output. + /// public XmlAssetCollection(IAsset asset, bool indentOutput = false) { _indentOutput = indentOutput; @@ -28,6 +44,10 @@ public XmlAssetCollection(IAsset asset, bool indentOutput = false) if (asset != null) Assets.Add(asset); } + /// + /// Creates a collection containing the given assets, recording the + /// indentation preference for output. + /// public XmlAssetCollection(IEnumerable assets, bool indentOutput = false) { _indentOutput = indentOutput; @@ -38,6 +58,10 @@ public XmlAssetCollection(IEnumerable assets, bool indentOutput = false) #region "Xml Serialization" + /// + /// Writes each contained asset to by + /// dispatching to its concrete asset surrogate. + /// public void WriteXml(XmlWriter writer) { if (!Assets.IsNullOrEmpty()) @@ -105,6 +129,11 @@ public void WriteXml(XmlWriter writer) // } //} + /// + /// Reads the asset child elements from , + /// resolving each element name to its asset type and deserializing it + /// into the collection. + /// public void ReadXml(XmlReader reader) { try @@ -149,6 +178,10 @@ public void ReadXml(XmlReader reader) reader.Skip(); } + /// + /// Returns null; the collection does not advertise an inline XML + /// schema, as required by . + /// public XmlSchema GetSchema() { return (null); diff --git a/libraries/MTConnect.NET-XML/Assets/XmlAssetsDocument.cs b/libraries/MTConnect.NET-XML/Assets/XmlAssetsDocument.cs index 9e03cd6b0..5a5194063 100644 --- a/libraries/MTConnect.NET-XML/Assets/XmlAssetsDocument.cs +++ b/libraries/MTConnect.NET-XML/Assets/XmlAssetsDocument.cs @@ -18,16 +18,29 @@ namespace MTConnect.Assets.Xml { + /// + /// XML serialization surrogate for an MTConnectAssets response + /// document. Mirrors the on-the-wire document, dispatching each asset + /// element to its concrete surrogate, and converts to and from the + /// strongly-typed model. + /// [XmlRoot("MTConnectAssets")] public class XmlAssetsResponseDocument { private static readonly XmlSerializer _serializer = new XmlSerializer(typeof(XmlAssetsResponseDocument)); + /// + /// The document header carrying agent and buffer metadata. + /// [XmlElement("Header")] public XmlAssetsHeader Header { get; set; } + /// + /// The assets in the document, each mapped to its concrete surrogate by + /// element name. + /// [XmlArray("Assets")] [XmlArrayItem(typeof(XmlComponentConfigurationParametersAsset), ElementName = ComponentConfigurationParametersAsset.TypeId)] [XmlArrayItem(typeof(XmlCuttingToolAsset), ElementName = CuttingToolAsset.TypeId)] @@ -36,10 +49,18 @@ public class XmlAssetsResponseDocument [XmlArrayItem(typeof(XmlRawMaterialAsset), ElementName = RawMaterialAsset.TypeId)] public List Assets { get; set; } + /// + /// The MTConnect version the document was produced for; not serialized. + /// [XmlIgnore] public Version Version { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , converting each asset via its + /// concrete surrogate. + /// public AssetsResponseDocument ToAssetsDocument() { var assetsDocument = new AssetsResponseDocument(); @@ -53,7 +74,7 @@ public AssetsResponseDocument ToAssetsDocument() foreach (var asset in Assets) { // ComponentConfigurationParameters - if (asset.GetType() == typeof(XmlComponentConfigurationParametersAsset)) + if (asset.GetType() == typeof(XmlComponentConfigurationParametersAsset)) { var componentConfigurationParametersAsset = ((XmlComponentConfigurationParametersAsset)asset).ToAsset(); if (componentConfigurationParametersAsset != null) assets.Add(componentConfigurationParametersAsset); @@ -95,6 +116,12 @@ public AssetsResponseDocument ToAssetsDocument() } + /// + /// Deserializes an MTConnectAssets XML document into a + /// strongly-typed , detecting the + /// MTConnect version and clearing namespaces first; returns null + /// if the input cannot be parsed. + /// public static AssetsResponseDocument FromXml(byte[] xmlBytes) { if (xmlBytes != null && xmlBytes.Length > 0) @@ -128,6 +155,11 @@ public static AssetsResponseDocument FromXml(byte[] xmlBytes) return null; } + /// + /// Serializes the given to a + /// of XML, returning null when the document + /// or its header is missing. + /// public static Stream ToXmlStream( IAssetsResponseDocument document, bool indentOutput = false, @@ -155,6 +187,13 @@ public static Stream ToXmlStream( return null; } + /// + /// Writes the given to + /// as a complete MTConnectAssets + /// document, including the XML declaration, optional stylesheet + /// instruction, provenance comment, namespace declarations, header, and + /// assets. + /// public static void WriteXml( XmlWriter writer, IAssetsResponseDocument document, diff --git a/libraries/MTConnect.NET-XML/Assets/XmlAssetsHeader.cs b/libraries/MTConnect.NET-XML/Assets/XmlAssetsHeader.cs index dd5a7a19d..7abe42e99 100644 --- a/libraries/MTConnect.NET-XML/Assets/XmlAssetsHeader.cs +++ b/libraries/MTConnect.NET-XML/Assets/XmlAssetsHeader.cs @@ -8,36 +8,73 @@ namespace MTConnect.Assets.Xml { + /// + /// XML serialization surrogate for the Header of an MTConnectAssets + /// response document. Mirrors the on-the-wire element and converts to the + /// strongly-typed model. + /// public class XmlAssetsHeader { + /// + /// The agent instance identifier; changes whenever the agent restarts. + /// [XmlAttribute("instanceId")] public ulong InstanceId { get; set; } + /// + /// The version of the MTConnect Standard the document conforms to. + /// [XmlAttribute("version")] public string Version { get; set; } + /// + /// The identifier of the agent that produced the document. + /// [XmlAttribute("sender")] public string Sender { get; set; } + /// + /// The maximum number of assets the agent can store. + /// [XmlAttribute("assetBufferSize")] public ulong AssetBufferSize { get; set; } + /// + /// The current number of assets the agent is storing. + /// [XmlAttribute("assetCount")] public ulong AssetCount { get; set; } + /// + /// The time the device model last changed, as the raw attribute text. + /// [XmlAttribute("deviceModelChangeTime")] public string DeviceModelChangeTime { get; set; } + /// + /// Whether the agent is operating in a test capacity rather than + /// production. + /// [XmlAttribute("testIndicator")] public bool TestIndicator { get; set; } + /// + /// Whether the agent validates documents against the MTConnect schema. + /// [XmlAttribute("validation")] public bool Validation { get; set; } + /// + /// The time the document was created. + /// [XmlAttribute("creationTime")] public DateTime CreationTime { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// . + /// public virtual IMTConnectAssetsHeader ToErrorHeader() { var header = new MTConnectAssetsHeader(); @@ -53,6 +90,11 @@ public virtual IMTConnectAssetsHeader ToErrorHeader() return header; } + /// + /// Writes the given to + /// as a Header element, omitting the + /// test and validation indicators when they are not set. + /// public static void WriteXml(XmlWriter writer, IMTConnectAssetsHeader header) { if (header != null) diff --git a/libraries/MTConnect.NET-XML/Assets/XmlUnknownAsset.cs b/libraries/MTConnect.NET-XML/Assets/XmlUnknownAsset.cs index 7f2fdc048..9b47a3e00 100644 --- a/libraries/MTConnect.NET-XML/Assets/XmlUnknownAsset.cs +++ b/libraries/MTConnect.NET-XML/Assets/XmlUnknownAsset.cs @@ -11,12 +11,27 @@ namespace MTConnect.Assets.Xml { + /// + /// XML serialization surrogate used when an asset element is encountered + /// whose assetType is not recognized by the strongly-typed model. + /// The raw XML is retained so the asset can still be round-tripped or + /// resolved later once its concrete type is known. + /// public class XmlUnknownAsset : XmlAsset { + /// + /// The raw XML fragment of the unrecognized asset element, preserved + /// verbatim so no information is lost during deserialization. + /// [XmlIgnore] public string Xml { get; set; } + /// + /// Attempts to resolve the asset to its concrete type by name and + /// deserialize the supplied XML bytes; returns null when the + /// name is not a registered asset type. + /// public static IAsset FromXml(string type, byte[] xmlBytes) { var asset = Asset.Create(type); diff --git a/libraries/MTConnect.NET-XML/Configurations/INamespaceConfiguration.cs b/libraries/MTConnect.NET-XML/Configurations/INamespaceConfiguration.cs index 04e4a6340..10ce89835 100644 --- a/libraries/MTConnect.NET-XML/Configurations/INamespaceConfiguration.cs +++ b/libraries/MTConnect.NET-XML/Configurations/INamespaceConfiguration.cs @@ -3,6 +3,11 @@ namespace MTConnect.Configurations { + /// + /// Configuration for an extended XML schema namespace declared on + /// MTConnect response documents, allowing custom or vendor schema + /// extensions to be referenced and validated. + /// public interface INamespaceConfiguration { /// @@ -10,6 +15,9 @@ public interface INamespaceConfiguration /// string Alias { get; } + /// + /// The URN that uniquely identifies the extended schema namespace. + /// string Urn { get; } /// @@ -17,6 +25,9 @@ public interface INamespaceConfiguration /// string Location { get; } + /// + /// The local file system path to the xsd file when it is served by the agent. + /// string Path { get; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-XML/Configurations/IStyleConfiguration.cs b/libraries/MTConnect.NET-XML/Configurations/IStyleConfiguration.cs index 76fedef7c..a01fc9de1 100644 --- a/libraries/MTConnect.NET-XML/Configurations/IStyleConfiguration.cs +++ b/libraries/MTConnect.NET-XML/Configurations/IStyleConfiguration.cs @@ -3,10 +3,21 @@ namespace MTConnect.Configurations { + /// + /// Configuration for an XSLT/CSS stylesheet referenced by MTConnect + /// response documents so a browser can render the XML response. + /// public interface IStyleConfiguration { + /// + /// The URL location of the stylesheet emitted in the document's + /// stylesheet processing instruction. + /// string Location { get; } + /// + /// The local file system path to the stylesheet when it is served by the agent. + /// string Path { get; } } } \ No newline at end of file diff --git a/libraries/MTConnect.NET-XML/Configurations/NamespaceConfiguration.cs b/libraries/MTConnect.NET-XML/Configurations/NamespaceConfiguration.cs index 963a86a9b..f271af4c6 100644 --- a/libraries/MTConnect.NET-XML/Configurations/NamespaceConfiguration.cs +++ b/libraries/MTConnect.NET-XML/Configurations/NamespaceConfiguration.cs @@ -5,6 +5,11 @@ namespace MTConnect.Configurations { + /// + /// Default implementation, also + /// serializable to JSON so the extended schema namespace can be supplied + /// through agent configuration files. + /// public class NamespaceConfiguration : INamespaceConfiguration { /// @@ -13,6 +18,9 @@ public class NamespaceConfiguration : INamespaceConfiguration [JsonPropertyName("alias")] public string Alias { get; set; } + /// + /// The URN that uniquely identifies the extended schema namespace. + /// [JsonPropertyName("urn")] public string Urn { get; set; } @@ -22,6 +30,9 @@ public class NamespaceConfiguration : INamespaceConfiguration [JsonPropertyName("location")] public string Location { get; set; } + /// + /// The local file system path to the xsd file when it is served by the agent. + /// [JsonPropertyName("path")] public string Path { get; set; } } diff --git a/libraries/MTConnect.NET-XML/Configurations/StyleConfiguration.cs b/libraries/MTConnect.NET-XML/Configurations/StyleConfiguration.cs index 7efed84cf..381177eac 100644 --- a/libraries/MTConnect.NET-XML/Configurations/StyleConfiguration.cs +++ b/libraries/MTConnect.NET-XML/Configurations/StyleConfiguration.cs @@ -5,11 +5,23 @@ namespace MTConnect.Configurations { + /// + /// Default implementation, also + /// serializable to JSON so the response document stylesheet can be + /// supplied through agent configuration files. + /// public class StyleConfiguration : IStyleConfiguration { + /// + /// The URL location of the stylesheet emitted in the document's + /// stylesheet processing instruction. + /// [JsonPropertyName("location")] public string Location { get; set; } + /// + /// The local file system path to the stylesheet when it is served by the agent. + /// [JsonPropertyName("path")] public string Path { get; set; } } diff --git a/libraries/MTConnect.NET-XML/Devices/XmlAbstractDataItemRelationship.cs b/libraries/MTConnect.NET-XML/Devices/XmlAbstractDataItemRelationship.cs index 939bb530d..7dcdecf30 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlAbstractDataItemRelationship.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlAbstractDataItemRelationship.cs @@ -6,17 +6,38 @@ namespace MTConnect.Devices.Xml { + /// + /// Base XML serialization surrogate shared by the data-item relationship + /// surrogates (for example DataItemRelationship and + /// SpecificationRelationship), carrying the common + /// name/idRef attributes. + /// public abstract class XmlAbstractDataItemRelationship { + /// + /// The optional relationship name, carried by the name attribute. + /// [XmlAttribute("name")] public string Name { get; set; } + /// + /// The id of the related entity, carried by the idRef + /// attribute. + /// [XmlAttribute("idRef")] public string IdRef { get; set; } + /// + /// Converts this surrogate to a strongly-typed relationship. The base + /// implementation returns null; concrete subclasses override it. + /// public virtual IAbstractDataItemRelationship ToRelationship() { return null; } + /// + /// Writes the relationship attributes shared by every subclass, + /// emitting idRef and name only when populated. + /// public static void WriteCommonXml(XmlWriter writer, IAbstractDataItemRelationship relationship) { if (!string.IsNullOrEmpty(relationship.IdRef)) writer.WriteAttributeString("idRef", relationship.IdRef); diff --git a/libraries/MTConnect.NET-XML/Devices/XmlAbstractSpecification.cs b/libraries/MTConnect.NET-XML/Devices/XmlAbstractSpecification.cs index 95ffd5f78..d2a0ae966 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlAbstractSpecification.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlAbstractSpecification.cs @@ -7,36 +7,75 @@ namespace MTConnect.Devices.Xml { + /// + /// Base XML serialization surrogate for MTConnect specifications. Carries + /// the identification attributes shared by every specification kind and + /// provides the default conversion to the strongly-typed + /// model. + /// public class XmlAbstractSpecification { + /// + /// The unique identifier of the specification within the device. + /// [XmlAttribute("id")] public string Id { get; set; } + /// + /// The optional human-readable name of the specification. + /// [XmlAttribute("name")] public string Name { get; set; } + /// + /// The type of the measured value the specification constrains. + /// [XmlAttribute("type")] public string Type { get; set; } + /// + /// The optional subtype that further qualifies . + /// [XmlAttribute("subType")] public string SubType { get; set; } + /// + /// The id of the data item the specification applies to. + /// [XmlAttribute("dataItemIdRef")] public string DataItemIdRef { get; set; } + /// + /// The engineering units the limits are expressed in. + /// [XmlAttribute("units")] public string Units { get; set; } + /// + /// The id of the composition the specification applies to. + /// [XmlAttribute("compositionIdRef")] public string CompositionIdRef { get; set; } + /// + /// The id of the coordinate system the limits are expressed in. + /// [XmlAttribute("coordinateSystemIdRef")] public string CoordinateSystemIdRef { get; set; } + /// + /// Who defined the specification, such as MANUFACTURER or + /// USER, as the raw attribute text. + /// [XmlAttribute("originator")] public string Originator { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// using the identification attributes + /// common to every specification kind. + /// public virtual ISpecification ToSpecification() { var specification = new Specification(); diff --git a/libraries/MTConnect.NET-XML/Devices/XmlAgent.cs b/libraries/MTConnect.NET-XML/Devices/XmlAgent.cs index 7862c09c7..3bbec15fb 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlAgent.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlAgent.cs @@ -5,9 +5,19 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for an MTConnect Agent device. The + /// agent is a specialized device that reports the state of the MTConnect + /// Agent itself; this surrogate maps the Agent element of an + /// MTConnectDevices document onto the strongly-typed model. + /// [XmlRoot("Agent")] - public class XmlAgent : XmlDevice + public class XmlAgent : XmlDevice { + /// + /// Converts this surrogate to a strongly-typed , + /// applying the shared device deserialization defined by . + /// public override IDevice ToDevice() { var device = new Agent(); diff --git a/libraries/MTConnect.NET-XML/Devices/XmlAlarmLimits.cs b/libraries/MTConnect.NET-XML/Devices/XmlAlarmLimits.cs index 98c92e622..afa4a21bb 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlAlarmLimits.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlAlarmLimits.cs @@ -7,22 +7,47 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for the AlarmLimits element of a + /// Specification, carrying the upper/lower alarm and warning bounds as + /// optional child elements. + /// [XmlRoot("AlarmLimits")] public class XmlAlarmLimits { + /// + /// The upper alarm bound, serialized as the optional UpperLimit + /// element. + /// [XmlElement("UpperLimit")] public double? UpperLimit { get; set; } + /// + /// The upper warning bound, serialized as the optional + /// UpperWarning element. + /// [XmlElement("UpperWarning")] public double? UpperWarning { get; set; } + /// + /// The lower alarm bound, serialized as the optional LowerLimit + /// element. + /// [XmlElement("LowerLimit")] public double? LowerLimit { get; set; } + /// + /// The lower warning bound, serialized as the optional + /// LowerWarning element. + /// [XmlElement("LowerWarning")] public double? LowerWarning { get; set; } + /// + /// Converts this surrogate to a strongly-typed , + /// copying each present bound. + /// public IAlarmLimits ToAlarmLimits() { var alarmLimits = new AlarmLimits(); @@ -33,6 +58,10 @@ public IAlarmLimits ToAlarmLimits() return alarmLimits; } + /// + /// Writes the alarm limits element, emitting only the bounds that are + /// present. + /// public static void WriteXml(XmlWriter writer, IAlarmLimits alarmLimits) { if (alarmLimits != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlAssetRelationship.cs b/libraries/MTConnect.NET-XML/Devices/XmlAssetRelationship.cs index b14f92d61..1a65f0503 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlAssetRelationship.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlAssetRelationship.cs @@ -7,19 +7,42 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for an AssetRelationship, associating + /// a Component with an asset (for example a cutting tool) it depends on or + /// otherwise relates to. + /// [XmlRoot("AssetRelationship")] public class XmlAssetRelationship : XmlConfigurationRelationship { + /// + /// The assetId of the related asset, carried by the + /// assetIdRef attribute. + /// [XmlAttribute("assetIdRef")] public string AssetIdRef { get; set; } + /// + /// The type of the related asset, carried by the assetType + /// attribute. + /// [XmlAttribute("assetType")] public string AssetType { get; set; } + /// + /// An optional URI locating the related asset, carried by the + /// href attribute. + /// [XmlAttribute("href")] public string Href { get; set; } + /// + /// Converts this surrogate to a strongly-typed + /// , copying the shared relationship + /// fields, mapping the optional criticality, and copying the asset + /// reference attributes. + /// public override IConfigurationRelationship ToRelationship() { var relationship = new AssetRelationship(); @@ -33,6 +56,11 @@ public override IConfigurationRelationship ToRelationship() return relationship; } + /// + /// Writes the relationship element, emitting the shared relationship + /// attributes followed by the asset reference attributes that are + /// populated. + /// public static void WriteXml(XmlWriter writer, IAssetRelationship relationship) { if (relationship != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlAxis.cs b/libraries/MTConnect.NET-XML/Devices/XmlAxis.cs index 96fdf20e4..b2d0f7837 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlAxis.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlAxis.cs @@ -12,13 +12,24 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for the Axis element of a Component + /// Configuration Motion, carrying the direction vector of the + /// motion axis as simple element content. + /// [XmlRoot("Axis")] public class XmlAxis { + /// + /// The axis direction values as the raw, space-delimited element text content. + /// [XmlText] public string Value { get; set; } + /// + /// Converts this surrogate to a strongly-typed . + /// public IAxis ToAxis() { var axis = new Axis(); @@ -26,6 +37,10 @@ public IAxis ToAxis() return axis; } + /// + /// Writes the Axis element for the supplied model, emitting the + /// value as element text and omitting an empty value. + /// public static void WriteXml(XmlWriter writer, IAxis axis) { if (axis != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlAxisDataSet.cs b/libraries/MTConnect.NET-XML/Devices/XmlAxisDataSet.cs index b50984331..5a8fe1f29 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlAxisDataSet.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlAxisDataSet.cs @@ -15,13 +15,27 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for the AxisDataSet element, the + /// keyed-entry representation of a motion axis direction where each + /// component is carried as an Entry keyed X, Y, or + /// Z. + /// [XmlRoot("AxisDataSet")] public class XmlAxisDataSet { + /// + /// The per-axis direction entries as serialized Entry elements. + /// [XmlElement("Entry")] public List Entries { get; set; } + /// + /// Converts the keyed entries to a strongly-typed + /// , mapping each X/Y/Z + /// entry to its component property and ignoring unkeyed entries. + /// public IAxisDataSet ToAxisDataSet() { var dataSet = new AxisDataSet(); @@ -42,6 +56,10 @@ public IAxisDataSet ToAxisDataSet() return dataSet; } + /// + /// Writes the AxisDataSet element, emitting one keyed + /// Entry per component using invariant-culture number formatting. + /// public static void WriteXml(XmlWriter writer, IAxisDataSet dataSet) { if (dataSet != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlCellDefinition.cs b/libraries/MTConnect.NET-XML/Devices/XmlCellDefinition.cs index d21052456..51240d491 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlCellDefinition.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlCellDefinition.cs @@ -6,27 +6,55 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for a CellDefinition, the schema + /// describing one column of a table data item. Mirrors the on-the-wire + /// element and converts to and from the strongly-typed + /// model. + /// public class XmlCellDefinition { + /// + /// The key that identifies the cell within a table entry. + /// [XmlAttribute("key")] public string Key { get; set; } + /// + /// The semantic meaning of the cell's key. + /// [XmlAttribute("keyType")] public string KeyType { get; set; } + /// + /// The engineering units of the cell's value. + /// [XmlAttribute("units")] public string Units { get; set; } + /// + /// The type of the cell's value. + /// [XmlAttribute("type")] public string Type { get; set; } + /// + /// The optional subtype that further qualifies . + /// [XmlAttribute("subType")] public string SubType { get; set; } + /// + /// The free-form description of the cell. + /// [XmlElement("Description")] public XmlDescription Description { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// . + /// public ICellDefinition ToCellDefinition() { var definition = new CellDefinition(); @@ -40,6 +68,11 @@ public ICellDefinition ToCellDefinition() return definition; } + /// + /// Writes the given to + /// as a CellDefinition element, + /// omitting optional attributes that are not set. + /// public static void WriteXml(XmlWriter writer, ICellDefinition cellDefinition) { if (cellDefinition != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlChannel.cs b/libraries/MTConnect.NET-XML/Devices/XmlChannel.cs index c87c09f13..a64f591d8 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlChannel.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlChannel.cs @@ -8,28 +8,55 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for a sensor Channel, one calibrated + /// input of a sensor configuration. Mirrors the on-the-wire element and + /// converts to and from the strongly-typed model. + /// [XmlRoot("Channel")] public class XmlChannel { + /// + /// The number that identifies the channel within the sensor. + /// [XmlAttribute("number")] public string Number { get; set; } + /// + /// The optional human-readable name of the channel. + /// [XmlAttribute("name")] public string Name { get; set; } + /// + /// The free-form description of the channel. + /// [XmlElement("Description")] public XmlDescription Description { get; set; } + /// + /// The date the channel was last calibrated. + /// [XmlElement("CalibrationDate")] public DateTime? CalibrationDate { get; set; } + /// + /// The date the channel is next due for calibration. + /// [XmlElement("NextCalibrationDate")] public DateTime? NextCalibrationDate { get; set; } + /// + /// The initials of the person who performed the calibration. + /// [XmlElement("CalibrationInitials")] public string CalibrationInitials { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// . + /// public IChannel ToChannel() { var channel = new Channel(); @@ -43,6 +70,11 @@ public IChannel ToChannel() return channel; } + /// + /// Writes the given to + /// as a Channel element, omitting calibration dates and initials + /// that are not set. + /// public static void WriteXml(XmlWriter writer, IChannel channel) { if (channel != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlComponent.cs b/libraries/MTConnect.NET-XML/Devices/XmlComponent.cs index 6640b9960..529c84703 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlComponent.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlComponent.cs @@ -12,62 +12,128 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for an MTConnect Component. Mirrors a + /// component element of an MTConnectDevices document so the XML serializer + /// can read and write the on-the-wire shape, then converts to and from the + /// strongly-typed model. + /// [XmlRoot("Component")] public class XmlComponent { private static readonly XmlSerializer _serializer = new XmlSerializer(typeof(XmlComponent)); + /// + /// The unique id of the component within the device. + /// [XmlAttribute("id")] public string Id { get; set; } + /// + /// The MTConnect component type. Carried out of band because the + /// element name itself encodes the type in the MTConnect XML schema. + /// [XmlIgnore] public string Type { get; set; } + /// + /// The optional human-readable name of the component. + /// [XmlAttribute("name")] public string Name { get; set; } + /// + /// The name the component is known by on its native control. + /// [XmlAttribute("nativeName")] public string NativeName { get; set; } + /// + /// The interval, in milliseconds, between samples the component reports. + /// [XmlAttribute("sampleInterval")] public double SampleInterval { get; set; } + /// + /// The deprecated sample rate, in samples per second; superseded by + /// . + /// [XmlAttribute("sampleRate")] public double SampleRate { get; set; } + /// + /// The optional globally unique uuid of the component. + /// [XmlAttribute("uuid")] public string Uuid { get; set; } + /// + /// Reference to the id of the CoordinateSystem the component's + /// values are expressed relative to. + /// [XmlAttribute("coordinateSystemIdRef")] public string CoordinateSystemIdRef { get; set; } + /// + /// The Description element carrying manufacturer, model, serial + /// number, and free-text description. + /// [XmlElement("Description")] public XmlDescription Description { get; set; } + /// + /// The Configuration element holding the component's + /// configuration sub-elements. + /// [XmlElement("Configuration")] public XmlConfiguration Configuration { get; set; } + /// + /// The DataItems the component reports directly. + /// [XmlArray("DataItems")] [XmlArrayItem("DataItem")] public List DataItems { get; set; } + /// + /// The Components element containing the component's child + /// component tree. + /// [XmlElement("Components")] public XmlComponentCollection ComponentCollection { get; set; } + /// + /// The Compositions describing the lower-level structural parts + /// of the component. + /// [XmlArray("Compositions")] [XmlArrayItem("Composition")] public List Compositions { get; set; } + /// + /// The component and data-item References the component depends + /// on. + /// [XmlArray("References")] [XmlArrayItem("ComponentRef", typeof(XmlComponentReference))] [XmlArrayItem("DataItemRef", typeof(XmlDataItemReference))] public List References { get; set; } + /// + /// The human-readable description of the component's type as defined by + /// the MTConnect Standard; emitted as an XML comment when requested. + /// [XmlIgnore] public string TypeDescription { get; set; } + /// + /// Converts this XML surrogate into the strongly-typed + /// model, optionally associating it with + /// , and recursively projecting data items, + /// compositions, and child components. + /// public Component ToComponent(IDevice device = null) { var component = Component.Create(Type); @@ -138,6 +204,12 @@ public Component ToComponent(IDevice device = null) return component; } + /// + /// Deserializes a single component XML document from + /// , recovering the component type from the + /// root element name, and returns it as an , or + /// null when the bytes are empty or not well-formed. + /// public static IComponent FromXml(byte[] xmlBytes) { if (xmlBytes != null && xmlBytes.Length > 0) @@ -220,6 +292,14 @@ public static IComponent FromXml(byte[] xmlBytes) // return null; //} + /// + /// Writes as its MTConnect element to + /// , emitting only the attributes that differ + /// from their defaults and recursing into description, configuration, + /// references, data items, compositions, and child components. When + /// is true, the type + /// description is written as a preceding XML comment. + /// public static void WriteXml(XmlWriter writer, IComponent component, bool outputComments = false) { if (component != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlComponentCollection.cs b/libraries/MTConnect.NET-XML/Devices/XmlComponentCollection.cs index 6a86b873e..365ffabdb 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlComponentCollection.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlComponentCollection.cs @@ -9,6 +9,13 @@ namespace MTConnect.Devices.Xml { + /// + /// Custom for the child components of a + /// component or device. Because MTConnect encodes a component's type in its + /// element name, this collection serializes each component through the + /// shared base surrogate and rewrites the element name to the concrete + /// component type, and reverses that on read. + /// public class XmlComponentCollection : IXmlSerializable { private static readonly XmlSerializer _serializer = new XmlSerializer(typeof(XmlComponent)); @@ -16,6 +23,10 @@ public class XmlComponentCollection : IXmlSerializable private List _components; + + /// + /// The child components held by the collection; never null. + /// [XmlIgnore] public List Components { @@ -31,8 +42,15 @@ public List Components } + /// + /// Creates an empty collection. + /// public XmlComponentCollection() { } + /// + /// Creates an empty collection, recording whether component type + /// descriptions should be emitted as comments. + /// public XmlComponentCollection(bool outputComments = false) { _outputComments = outputComments; @@ -41,6 +59,11 @@ public XmlComponentCollection(bool outputComments = false) #region "Xml Serialization" + /// + /// Writes each component to , serializing + /// through the base surrogate and renaming the element to the concrete + /// component type, optionally preceded by a type-description comment. + /// public void WriteXml(XmlWriter writer) { if (!Components.IsNullOrEmpty()) @@ -98,6 +121,11 @@ public void WriteXml(XmlWriter writer) } } + /// + /// Reads the component child elements from , + /// rewriting each type-named element to the base Component name + /// so it can be deserialized, then restoring the concrete type. + /// public void ReadXml(XmlReader reader) { try @@ -149,6 +177,10 @@ public void ReadXml(XmlReader reader) reader.Skip(); } + /// + /// Returns null; the collection does not advertise an inline XML + /// schema, as required by . + /// public XmlSchema GetSchema() { return (null); diff --git a/libraries/MTConnect.NET-XML/Devices/XmlComponentReference.cs b/libraries/MTConnect.NET-XML/Devices/XmlComponentReference.cs index 2196d4375..ea81c5d32 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlComponentReference.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlComponentReference.cs @@ -5,8 +5,17 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for an MTConnect ComponentRef. Resolves + /// the inherited idRef/name attributes to a reference to a + /// Component defined elsewhere in the device model. + /// public class XmlComponentReference : XmlReference { + /// + /// Converts this surrogate to a strongly-typed , + /// copying the referenced component id and optional display name. + /// public override IReference ToReference() { var reference = new ComponentReference(); diff --git a/libraries/MTConnect.NET-XML/Devices/XmlComponentRelationship.cs b/libraries/MTConnect.NET-XML/Devices/XmlComponentRelationship.cs index a42d47bba..4f8d8e7c2 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlComponentRelationship.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlComponentRelationship.cs @@ -7,13 +7,28 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for a ComponentRelationship, + /// associating a Component with another component it depends on, is a + /// parent or child of, or otherwise relates to. + /// [XmlRoot("ComponentRelationship")] public class XmlComponentRelationship : XmlConfigurationRelationship { + /// + /// The id of the related component, carried by the idRef + /// attribute. + /// [XmlAttribute("idRef")] public string IdRef { get; set; } + /// + /// Converts this surrogate to a strongly-typed + /// , copying the shared relationship + /// fields, mapping the optional criticality to its enumeration, and + /// copying the referenced component id. + /// public override IConfigurationRelationship ToRelationship() { var relationship = new ComponentRelationship(); @@ -25,6 +40,10 @@ public override IConfigurationRelationship ToRelationship() return relationship; } + /// + /// Writes the relationship element, emitting the shared relationship + /// attributes followed by the optional idRef attribute. + /// public static void WriteXml(XmlWriter writer, IComponentRelationship relationship) { if (relationship != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlComposition.cs b/libraries/MTConnect.NET-XML/Devices/XmlComposition.cs index dfda14411..af4ca1cdc 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlComposition.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlComposition.cs @@ -9,45 +9,93 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for an MTConnect Composition, a + /// lower-level functional building block of a component. Mirrors the + /// on-the-wire element and converts to and from the strongly-typed + /// model. + /// [XmlRoot("Composition")] public class XmlComposition { private static readonly XmlSerializer _serializer = new XmlSerializer(typeof(XmlComposition)); + /// + /// The unique identifier of the composition within the device. + /// [XmlAttribute("id")] public string Id { get; set; } + /// + /// The MTConnect composition type, such as MOTOR or + /// SENSING_ELEMENT. + /// [XmlAttribute("type")] public string Type { get; set; } + /// + /// The optional human-readable name of the composition. + /// [XmlAttribute("name")] public string Name { get; set; } + /// + /// The name the composition is known by on its native control. + /// [XmlAttribute("nativeName")] public string NativeName { get; set; } + /// + /// The interval, in milliseconds, between samples the composition + /// reports. + /// [XmlAttribute("sampleInterval")] public double SampleInterval { get; set; } + /// + /// The deprecated sample rate, in samples per second; superseded by + /// . + /// [XmlAttribute("sampleRate")] public double SampleRate { get; set; } + /// + /// The optional globally unique identifier of the composition. + /// [XmlAttribute("uuid")] public string Uuid { get; set; } + /// + /// The free-form description of the composition. + /// [XmlElement("Description")] public XmlDescription Description { get; set; } + /// + /// The configuration metadata that applies to the composition. + /// [XmlElement("Configuration")] public XmlConfiguration Configuration { get; set; } + /// + /// The references to components and data items related to this + /// composition. + /// [XmlArray("References")] [XmlArrayItem("ComponentRef", typeof(XmlComponentReference))] [XmlArrayItem("DataItemRef", typeof(XmlDataItemReference))] public List References { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , instantiating the + /// concrete composition class that matches when one + /// exists. + /// + /// The owning device, supplied for context where + /// the conversion needs it. public Composition ToComposition(IDevice device = null) { var composition = Composition.Create(Type.ToPascalCase()); @@ -78,6 +126,11 @@ public Composition ToComposition(IDevice device = null) return composition; } + /// + /// Deserializes a standalone Composition XML document into a + /// strongly-typed , returning null if + /// the input is empty or cannot be parsed. + /// public static IComposition FromXml(byte[] xmlBytes) { if (xmlBytes != null && xmlBytes.Length > 0) @@ -102,6 +155,15 @@ public static IComposition FromXml(byte[] xmlBytes) return null; } + /// + /// Writes the given to + /// as a Composition element, optionally preceding it with a + /// comment describing the composition type. + /// + /// The XML writer to emit to. + /// The composition to serialize. + /// When true, emits the human-readable + /// type description as an XML comment. public static void WriteXml(XmlWriter writer, IComposition composition, bool outputComments = false) { if (composition != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlConfiguration.cs b/libraries/MTConnect.NET-XML/Devices/XmlConfiguration.cs index 5c808ccf7..0b1c675da 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlConfiguration.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlConfiguration.cs @@ -8,38 +8,69 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for a component's Configuration, the + /// container for its coordinate systems, motion, relationships, sensor + /// settings, geometry, and specifications. Mirrors the on-the-wire element + /// and converts to and from the strongly-typed + /// model. + /// [XmlRoot("Configuration")] public class XmlConfiguration { + /// + /// The coordinate systems the component's geometry is expressed in. + /// [XmlArray("CoordinateSystems")] [XmlArrayItem("CoordinateSystem", typeof(XmlCoordinateSystem))] public List CoordinateSystems { get; set; } + /// + /// The kinematic relationship of the component to its parent. + /// [XmlElement("Motion")] public XmlMotion Motion { get; set; } + /// + /// The relationships from this component to assets, devices, and other + /// components. + /// [XmlArray("Relationships")] [XmlArrayItem("AssetRelationship", typeof(XmlAssetRelationship))] [XmlArrayItem("DeviceRelationship", typeof(XmlDeviceRelationship))] [XmlArrayItem("ComponentRelationship", typeof(XmlComponentRelationship))] public List Relationships { get; set; } + /// + /// The sensor calibration and channel settings of the component. + /// [XmlElement("SensorConfiguration")] public XmlSensorConfiguration SensorConfiguration { get; set; } + /// + /// The 3D geometry reference for the component. + /// [XmlElement("SolidModel")] public XmlSolidModel SolidModel { get; set; } + /// + /// The specifications constraining the component's measured values. + /// [XmlArray("Specifications")] [XmlArrayItem("Specification", typeof(XmlSpecification))] [XmlArrayItem("ProcessSpecification", typeof(XmlProcessSpecification))] public List Specifications { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , projecting each nested collection into + /// its model representation. + /// public IConfiguration ToConfiguration() { var configuration = new Configuration(); - + // Coordinate Systems if (!CoordinateSystems.IsNullOrEmpty()) { @@ -94,6 +125,12 @@ public IConfiguration ToConfiguration() return configuration; } + /// + /// Writes the given to + /// as a Configuration element, + /// dispatching each relationship to its concrete writer and optionally + /// preceding the element with an explanatory comment. + /// public static void WriteXml(XmlWriter writer, IConfiguration configuration, bool outputComments) { if (configuration != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlConfigurationRelationship.cs b/libraries/MTConnect.NET-XML/Devices/XmlConfigurationRelationship.cs index 02f14578a..17c9bb9ca 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlConfigurationRelationship.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlConfigurationRelationship.cs @@ -7,23 +7,49 @@ namespace MTConnect.Devices.Xml { + /// + /// Base XML serialization surrogate for the configuration relationships of + /// a component. Carries the identification attributes shared by every + /// relationship kind and the common attribute-writing helper. + /// public abstract class XmlConfigurationRelationship { + /// + /// The unique identifier of the relationship within the device. + /// [XmlAttribute("id")] public string Id { get; set; } + /// + /// The optional human-readable name of the relationship. + /// [XmlAttribute("name")] public string Name { get; set; } + /// + /// The kind of relationship, such as PARENT or CHILD. + /// [XmlAttribute("type")] public RelationshipType Type { get; set; } + /// + /// How critical the relationship is, as the raw attribute text. + /// [XmlAttribute("criticality")] public string Criticality { get; set; } + /// + /// Converts this surrogate into the strongly-typed relationship model. + /// Overridden by each concrete relationship surrogate; the base + /// implementation returns null. + /// public virtual IConfigurationRelationship ToRelationship() { return null; } + /// + /// Writes the identification attributes shared by every relationship + /// kind, omitting the optional attributes that are not set. + /// public static void WriteCommonXml(XmlWriter writer, IConfigurationRelationship relationship) { if (!string.IsNullOrEmpty(relationship.Id)) writer.WriteAttributeString("id", relationship.Id); diff --git a/libraries/MTConnect.NET-XML/Devices/XmlConstraints.cs b/libraries/MTConnect.NET-XML/Devices/XmlConstraints.cs index 2bf0cec63..93242ad45 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlConstraints.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlConstraints.cs @@ -7,24 +7,48 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for the Constraints on a data item's + /// reported value. Mirrors the on-the-wire element and converts to and from + /// the strongly-typed model. + /// public class XmlConstraints { + /// + /// The maximum value the data item may report. + /// [XmlElement("Maximum")] public double? Maximum { get; set; } + /// + /// The minimum value the data item may report. + /// [XmlElement("Minimum")] public double? Minimum { get; set; } + /// + /// The nominal (target) value of the data item. + /// [XmlElement("Nominal")] public double? Nominal { get; set; } + /// + /// The discrete set of values the data item is constrained to. + /// [XmlElement("Value")] public List Values { get; set; } + /// + /// The filter applied to the data item's reported values. + /// [XmlElement("Filter")] public XmlFilter Filter { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// . + /// public IConstraints ToConstraints() { var constraints = new Constraints(); @@ -35,6 +59,11 @@ public IConstraints ToConstraints() return constraints; } + /// + /// Writes the given to + /// as a Constraints element, emitting + /// only the bounds, enumerated values, and filter that are set. + /// public static void WriteXml(XmlWriter writer, IConstraints constraints) { if (constraints != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlControlLimits.cs b/libraries/MTConnect.NET-XML/Devices/XmlControlLimits.cs index 54c8cbc85..149300b36 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlControlLimits.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlControlLimits.cs @@ -7,25 +7,50 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for the ControlLimits of a process + /// specification, the statistical-control boundaries of a measured value. + /// Mirrors the on-the-wire element and converts to and from the + /// strongly-typed model. + /// [XmlRoot("ControlLimits")] public class XmlControlLimits { + /// + /// The upper control limit. + /// [XmlElement("UpperLimit")] public double? UpperLimit { get; set; } + /// + /// The upper boundary indicating a warning condition. + /// [XmlElement("UpperWarning")] public double? UpperWarning { get; set; } + /// + /// The centre line (target) value. + /// [XmlElement("Nominal")] public double? Nominal { get; set; } + /// + /// The lower control limit. + /// [XmlElement("LowerLimit")] public double? LowerLimit { get; set; } + /// + /// The lower boundary indicating a warning condition. + /// [XmlElement("LowerWarning")] public double? LowerWarning { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// . + /// public IControlLimits ToControlLimits() { var controlLimits = new ControlLimits(); @@ -37,6 +62,11 @@ public IControlLimits ToControlLimits() return controlLimits; } + /// + /// Writes the given to + /// as a ControlLimits element, + /// emitting only the limit elements that are set. + /// public static void WriteXml(XmlWriter writer, IControlLimits controlLimits) { if (controlLimits != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlCoordinateSystem.cs b/libraries/MTConnect.NET-XML/Devices/XmlCoordinateSystem.cs index 01b696377..1a8139e5a 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlCoordinateSystem.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlCoordinateSystem.cs @@ -13,37 +13,81 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for an MTConnect CoordinateSystem, + /// the spatial reference frame a component's geometry is expressed in. + /// Mirrors the on-the-wire element and converts to and from the + /// strongly-typed model. + /// [XmlRoot("CoordinateSystem")] public class XmlCoordinateSystem { + /// + /// The unique identifier of the coordinate system within the device. + /// [XmlAttribute("id")] public string Id { get; set; } + /// + /// The optional human-readable name of the coordinate system. + /// [XmlAttribute("name")] public string Name { get; set; } + /// + /// The name the coordinate system is known by on its native control. + /// [XmlAttribute("nativeName")] public string NativeName { get; set; } + /// + /// The id of the parent coordinate system this one is defined + /// relative to. + /// [XmlAttribute("parentIdRef")] public string ParentIdRef { get; set; } + /// + /// The kind of coordinate system, such as MACHINE or + /// WORK. + /// [XmlAttribute("type")] public CoordinateSystemType Type { get; set; } + /// + /// The origin expressed as a coordinate triple; mutually exclusive with + /// and . + /// [XmlElement("Origin")] public XmlOrigin Origin { get; set; } + /// + /// The origin expressed as a data set; mutually exclusive with + /// and . + /// [XmlElement("OriginDataSet")] public XmlOriginDataSet OriginDataSet { get; set; } + /// + /// The translation and rotation from the parent coordinate system; + /// mutually exclusive with and + /// . + /// [XmlElement("Transformation")] public XmlTransformation Transformation { get; set; } + /// + /// The free-form description of the coordinate system. + /// [XmlElement("Description")] public string Description { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , resolving the origin choice in + /// favour of the data-set form when present. + /// public ICoordinateSystem ToCoordinateSystem() { var coordinateSystem = new CoordinateSystem(); @@ -59,6 +103,11 @@ public ICoordinateSystem ToCoordinateSystem() return coordinateSystem; } + /// + /// Writes the given to + /// as a CoordinateSystem element, + /// emitting the data-set form of the origin when the model carries it. + /// public static void WriteXml(XmlWriter writer, ICoordinateSystem coordinateSystem) { if (coordinateSystem != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlDataItem.cs b/libraries/MTConnect.NET-XML/Devices/XmlDataItem.cs index 26997e155..356fbec8b 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlDataItem.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlDataItem.cs @@ -8,84 +8,184 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for an MTConnect DataItem. Mirrors the + /// DataItem element of an MTConnectDevices document so the XML + /// serializer can read and write the on-the-wire attribute and child-element + /// shape, then converts to and from the strongly-typed + /// model. + /// public class XmlDataItem { private static readonly XmlSerializer _serializer = new XmlSerializer(typeof(XmlDataItem)); + /// + /// The category attribute classifying the data item as SAMPLE, + /// EVENT, or CONDITION. + /// [XmlAttribute("category")] public string DataItemCategory { get; set; } + /// + /// The unique id of the data item within the device. + /// [XmlAttribute("id")] public string Id { get; set; } + /// + /// The MTConnect type identifying the kind of data reported. + /// [XmlAttribute("type")] public string Type { get; set; } + /// + /// The coordinate system the reported values are expressed in (for + /// example MACHINE or WORK). + /// [XmlAttribute("coordinateSystem")] public string CoordinateSystem { get; set; } + /// + /// Reference to the id of a CoordinateSystem component the + /// values are expressed relative to. + /// [XmlAttribute("coordinateSystemIdRef")] public string CoordinateSystemIdRef { get; set; } + /// + /// The optional human-readable name of the data item. + /// [XmlAttribute("name")] public string Name { get; set; } + /// + /// Reference to the id of the Composition the data item belongs to. + /// [XmlAttribute("compositionId")] public string CompositionId { get; set; } + /// + /// The power-of-ten scaling applied to native values before conversion + /// to the reported units. + /// [XmlAttribute("nativeScale")] public int NativeScale { get; set; } + /// + /// The units the data source natively reports values in, prior to + /// conversion to the MTConnect . + /// [XmlAttribute("nativeUnits")] public string NativeUnits { get; set; } + /// + /// The optional subType further qualifying the data item's + /// . + /// [XmlAttribute("subType")] public string SubType { get; set; } + /// + /// The statistical operation (for example AVERAGE or MAXIMUM) applied + /// to the reported values. + /// [XmlAttribute("statistic")] public string Statistic { get; set; } + /// + /// The engineering units the reported values are expressed in. + /// [XmlAttribute("units")] public string Units { get; set; } + /// + /// The rate, in samples per second, at which the data source samples + /// values for a TIME_SERIES representation. + /// [XmlAttribute("sampleRate")] public double SampleRate { get; set; } + /// + /// Indicates whether the reported values are discrete events rather + /// than a continuously varying signal. + /// [XmlAttribute("discrete")] public string Discrete { get; set; } + /// + /// The data item's representation (for example VALUE, DATA_SET, + /// TABLE, or TIME_SERIES). + /// [XmlAttribute("representation")] public string Representation { get; set; } + /// + /// The number of significant digits retained when reporting numeric + /// values. + /// [XmlAttribute("significantDigits")] public int SignificantDigits { get; set; } + /// + /// The Source element identifying the component, sensor, or data + /// item the values originate from. + /// [XmlElement("Source")] public XmlSource Source { get; set; } + /// + /// The Constraints element bounding the values the data item may + /// report. + /// [XmlElement("Constraints")] public XmlConstraints Constraints { get; set; } + /// + /// The Filters applied to the data item's values, such as a + /// minimum-delta or period filter. + /// [XmlArray("Filters")] [XmlArrayItem("Filter")] public List Filters { get; set; } + /// + /// The starting value reported for the data item before any + /// observation is recorded. + /// [XmlElement("InitialValue")] public string InitialValue { get; set; } + /// + /// The condition under which a measured or accumulated value resets. + /// [XmlElement("ResetTrigger")] public string ResetTrigger { get; set; } + /// + /// The Definition element providing additional descriptive + /// metadata, including entry and cell definitions for DATA_SET and + /// TABLE data items. + /// [XmlElement("Definition")] public XmlDataItemDefinition Definition { get; set; } + /// + /// The relationships associating this data item with other data items + /// or specifications. + /// [XmlArray("Relationships")] [XmlArrayItem("DataItemRelationship", typeof(XmlDataItemRelationship))] [XmlArrayItem("SpecificationRelationship", typeof(XmlSpecificationRelationship))] public List Relationships { get; set; } + /// + /// Converts this XML surrogate into the strongly-typed + /// model, resolving enum-valued attributes and + /// projecting the nested Source, Constraints, Definition, Filters, and + /// Relationships. + /// public DataItem ToDataItem() { var dataItem = DataItem.Create(Type); @@ -145,6 +245,12 @@ public DataItem ToDataItem() } + /// + /// Deserializes a single DataItem XML document from + /// and returns it as an + /// , or null when the bytes are empty or + /// not well-formed. + /// public static IDataItem FromXml(byte[] xmlBytes) { if (xmlBytes != null && xmlBytes.Length > 0) @@ -170,6 +276,13 @@ public static IDataItem FromXml(byte[] xmlBytes) } + /// + /// Writes as a DataItem element to + /// , emitting only the attributes that differ + /// from their MTConnect defaults. When + /// is true, the type and subType descriptions are written as + /// preceding XML comments. + /// public static void WriteXml(XmlWriter writer, IDataItem dataItem, bool outputComments = false) { if (dataItem != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlDataItemDefinition.cs b/libraries/MTConnect.NET-XML/Devices/XmlDataItemDefinition.cs index a1c65a04c..b7160ab74 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlDataItemDefinition.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlDataItemDefinition.cs @@ -7,24 +7,47 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for a DataItem Definition, describing + /// the structure of complex DATA_SET/TABLE observations through entry and + /// cell definitions. + /// public class XmlDataItemDefinition { + /// + /// The optional free-text description of the definition, serialized as + /// a Description element. + /// [XmlElement("Description")] public XmlDescription Description { get; set; } + /// + /// The definitions of the keyed entries the data item may report, + /// serialized as EntryDefinition elements within + /// EntryDefinitions. + /// [XmlArray("EntryDefinitions")] [XmlArrayItem("EntryDefinition")] public List EntryDefinitions { get; set; } + /// + /// The definitions of the cells within each table entry, serialized as + /// CellDefinition elements within CellDefinitions. + /// [XmlArray("CellDefinitions")] [XmlArrayItem("CellDefinition")] public List CellDefinitions { get; set; } + /// + /// Converts this surrogate to a strongly-typed + /// , copying the description and + /// converting each entry and cell definition. + /// public IDataItemDefinition ToDefinition() { var definition = new DataItemDefinition(); - + if (Description != null) definition.Description = Description?.CDATA; //if (Description != null) definition.Description = Description.ToDescription(); @@ -53,6 +76,11 @@ public IDataItemDefinition ToDefinition() return definition; } + /// + /// Writes the Definition element, emitting the + /// EntryDefinitions and CellDefinitions containers only + /// when populated. + /// public static void WriteXml(XmlWriter writer, IDataItemDefinition dataItemDefinition) { if (dataItemDefinition != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlDataItemReference.cs b/libraries/MTConnect.NET-XML/Devices/XmlDataItemReference.cs index d67bed0f1..8e40313d7 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlDataItemReference.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlDataItemReference.cs @@ -5,8 +5,17 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for an MTConnect DataItemRef. Resolves + /// the inherited idRef/name attributes to a reference to a + /// DataItem defined elsewhere in the device model. + /// public class XmlDataItemReference : XmlReference { + /// + /// Converts this surrogate to a strongly-typed , + /// copying the referenced data item id and optional display name. + /// public override IReference ToReference() { var reference = new DataItemReference(); diff --git a/libraries/MTConnect.NET-XML/Devices/XmlDataItemRelationship.cs b/libraries/MTConnect.NET-XML/Devices/XmlDataItemRelationship.cs index 59a4e1f3e..b592d6d20 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlDataItemRelationship.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlDataItemRelationship.cs @@ -6,13 +6,27 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for a DataItemRelationship, + /// associating a DataItem with another data item it depends on, limits, or + /// otherwise relates to. + /// [XmlRoot("DataItemRelationship")] public class XmlDataItemRelationship : XmlAbstractDataItemRelationship { + /// + /// The kind of relationship to the referenced data item, carried by the + /// type attribute (for example LIMIT or OBSERVATION). + /// [XmlAttribute("type")] public DataItemRelationshipType Type { get; set; } + /// + /// Converts this surrogate to a strongly-typed + /// , copying the relationship name, + /// referenced id, and relationship type. + /// public override IAbstractDataItemRelationship ToRelationship() { var relationship = new DataItemRelationship(); @@ -22,6 +36,10 @@ public override IAbstractDataItemRelationship ToRelationship() return relationship; } + /// + /// Writes the relationship element, emitting the shared relationship + /// attributes followed by the type attribute. + /// public static void WriteXml(XmlWriter writer, IDataItemRelationship relationship) { if (relationship != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlDescription.cs b/libraries/MTConnect.NET-XML/Devices/XmlDescription.cs index aaf1796f5..2569d4300 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlDescription.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlDescription.cs @@ -6,24 +6,49 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for a component's Description. + /// Mirrors the on-the-wire element, where the free text is carried as the + /// element body and the identification fields as attributes, and converts + /// to and from the strongly-typed model. + /// public class XmlDescription { + /// + /// The manufacturer of the component being described. + /// [XmlAttribute("manufacturer")] public string Manufacturer { get; set; } + /// + /// The model of the component being described. + /// [XmlAttribute("model")] public string Model { get; set; } + /// + /// The serial number of the component being described. + /// [XmlAttribute("serialNumber")] public string SerialNumber { get; set; } + /// + /// The station the component being described belongs to. + /// [XmlAttribute("station")] public string Station { get; set; } + /// + /// The free-text description, carried as the element body. + /// [XmlText] public string CDATA { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , trimming the free-text body. + /// public IDescription ToDescription() { var description = new Description(); @@ -35,6 +60,11 @@ public IDescription ToDescription() return description; } + /// + /// Writes the given to + /// as a Description element, skipping + /// the element entirely when every field is empty. + /// public static void WriteXml(XmlWriter writer, IDescription description) { if (description != null && @@ -56,6 +86,10 @@ public static void WriteXml(XmlWriter writer, IDescription description) } } + /// + /// Writes a plain string as a Description element, skipping the + /// element when the string is empty. + /// public static void WriteXml(XmlWriter writer, string description) { if (!string.IsNullOrEmpty(description)) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlDevice.cs b/libraries/MTConnect.NET-XML/Devices/XmlDevice.cs index 0968a9193..9506ab35b 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlDevice.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlDevice.cs @@ -10,71 +10,143 @@ namespace MTConnect.Devices.Xml { - [XmlRoot("Device")] + /// + /// XML serialization surrogate for an MTConnect Device. Mirrors the + /// Device element of an MTConnectDevices document so the XML + /// serializer can read and write the on-the-wire shape, then converts to + /// and from the strongly-typed model. + /// + [XmlRoot("Device")] public class XmlDevice { private static readonly XmlSerializer _serializer = new XmlSerializer(typeof(XmlDevice)); + /// + /// The unique id of the device within the MTConnectDevices document. + /// [XmlAttribute("id")] public string Id { get; set; } + /// + /// The human-readable name of the device. + /// [XmlAttribute("name")] public string Name { get; set; } + /// + /// The globally unique uuid identifying the physical device. + /// [XmlAttribute("uuid")] public string Uuid { get; set; } + /// + /// The ISO 841 classification of the device. + /// [XmlAttribute("iso841Class")] public string Iso841Class { get; set; } + /// + /// The name the device is known by on its native control. + /// [XmlAttribute("nativeName")] public string NativeName { get; set; } + /// + /// The interval, in milliseconds, between samples the device reports. + /// [XmlAttribute("sampleInterval")] public double SampleInterval { get; set; } + /// + /// The deprecated sample rate, in samples per second; superseded by + /// . + /// [XmlAttribute("sampleRate")] public double SampleRate { get; set; } + /// + /// Reference to the id of the CoordinateSystem the device's + /// values are expressed relative to. + /// [XmlAttribute("coordinateSystemIdRef")] public string CoordinateSystemIdRef { get; set; } + /// + /// The version of the MTConnect Standard the device's information model + /// conforms to. + /// [XmlAttribute("mtconnectVersion")] public string MTConnectVersion { get; set; } + /// + /// The change hash identifying the current revision of the device's + /// model, used to detect configuration changes. + /// [XmlAttribute("hash")] - public string Hash { get; set; } + public string Hash { get; set; } + /// + /// The Description element carrying manufacturer, model, serial + /// number, and free-text description. + /// [XmlElement("Description")] public XmlDescription Description { get; set; } + /// + /// The Configuration element holding the device's configuration + /// sub-elements. + /// [XmlElement("Configuration")] public XmlConfiguration Configuration { get; set; } + /// + /// The DataItems the device reports directly (not via a child + /// component). + /// [XmlArray("DataItems")] [XmlArrayItem("DataItem")] public List DataItems { get; set; } + /// + /// The Components element containing the device's child + /// component tree. + /// [XmlElement("Components")] public XmlComponentCollection ComponentCollection { get; set; } + /// + /// The Compositions describing the lower-level structural parts + /// of the device. + /// [XmlArray("Compositions")] [XmlArrayItem("Composition")] public List Compositions { get; set; } + /// + /// The component and data-item References the device depends on. + /// [XmlArray("References")] [XmlArrayItem("ComponentRef", typeof(XmlComponentReference))] [XmlArrayItem("DataItemRef", typeof(XmlDataItemReference))] public List References { get; set; } + /// + /// Converts this XML surrogate into a new strongly-typed + /// model. + /// public virtual IDevice ToDevice() { var device = new Device(); return ToDevice(device); } + /// + /// Populates from this XML surrogate, + /// projecting the description, configuration, references, data items, + /// compositions, and child components, and wiring up container links. + /// protected IDevice ToDevice(Device device) { device.Id = Id; @@ -148,6 +220,13 @@ protected IDevice ToDevice(Device device) return device; } + /// + /// Deserializes a single Device XML document from + /// , optionally overriding the device + /// uuid with , and returns it as an + /// , or null when the bytes are empty or not + /// well-formed. + /// public static IDevice FromXml(byte[] xmlBytes, string deviceUuid = null) { if (xmlBytes != null && xmlBytes.Length > 0) @@ -183,6 +262,11 @@ public static IDevice FromXml(byte[] xmlBytes, string deviceUuid = null) return null; } + /// + /// Serializes to a UTF-8 Device XML + /// byte array, optionally ed, or null + /// when serialization fails. + /// public static byte[] ToXml(IDevice device, bool indent = true) { if (device != null) @@ -209,6 +293,14 @@ public static byte[] ToXml(IDevice device, bool indent = true) return null; } + /// + /// Writes as its MTConnect element to + /// , emitting only the attributes that differ + /// from their defaults and recursing into description, configuration, + /// references, data items, compositions, and components. When + /// is true, type descriptions + /// are written as preceding XML comments. + /// public static void WriteXml(XmlWriter writer, IDevice device, bool outputComments = false) { if (device != null) @@ -238,8 +330,8 @@ public static void WriteXml(XmlWriter writer, IDevice device, bool outputComment if (device.MTConnectVersion != null) writer.WriteAttributeString("mtconnectVersion", device.MTConnectVersion.ToString()); if (!string.IsNullOrEmpty(device.Hash)) writer.WriteAttributeString("hash", device.Hash); - // Write Description - XmlDescription.WriteXml(writer, device.Description); + // Write Description + XmlDescription.WriteXml(writer, device.Description); // Write Configuration XmlConfiguration.WriteXml(writer, device.Configuration, outputComments); diff --git a/libraries/MTConnect.NET-XML/Devices/XmlDeviceRelationship.cs b/libraries/MTConnect.NET-XML/Devices/XmlDeviceRelationship.cs index 76913478f..2f5271043 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlDeviceRelationship.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlDeviceRelationship.cs @@ -7,22 +7,45 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for a DeviceRelationship, which links + /// a component to another device. Mirrors the on-the-wire element and + /// converts to the strongly-typed model. + /// [XmlRoot("DeviceRelationship")] public class XmlDeviceRelationship : XmlConfigurationRelationship { + /// + /// The UUID of the related device. + /// [XmlAttribute("deviceUuidRef")] public string DeviceUuidRef { get; set; } + /// + /// The role the related device plays, such as SYSTEM or + /// AUXILIARY, as the raw attribute text. + /// [XmlAttribute("role")] public string Role { get; set; } + /// + /// The URL the related device's information can be retrieved from. + /// [XmlAttribute("href")] public string Href { get; set; } + /// + /// The XLink type of the reference. + /// [XmlAttribute("type", Namespace = "http://www.w3.org/1999/xlink")] public string XLinkType { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , including the inherited + /// identification attributes and parsing the criticality and role. + /// public override IConfigurationRelationship ToRelationship() { var relationship = new DeviceRelationship(); @@ -37,6 +60,11 @@ public override IConfigurationRelationship ToRelationship() return relationship; } + /// + /// Writes the given to + /// , naming the element after the concrete + /// relationship type and omitting optional attributes that are not set. + /// public static void WriteXml(XmlWriter writer, IDeviceRelationship relationship) { if (relationship != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlDevicesHeader.cs b/libraries/MTConnect.NET-XML/Devices/XmlDevicesHeader.cs index 133b4b879..ab42c9beb 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlDevicesHeader.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlDevicesHeader.cs @@ -8,39 +8,81 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for the Header of an + /// MTConnectDevices response document. Mirrors the on-the-wire element and + /// converts to the strongly-typed + /// model. + /// public class XmlDevicesHeader { + /// + /// The agent instance identifier; changes whenever the agent restarts. + /// [XmlAttribute("instanceId")] public ulong InstanceId { get; set; } + /// + /// The version of the MTConnect Standard the document conforms to. + /// [XmlAttribute("version")] public string Version { get; set; } + /// + /// The identifier of the agent that produced the document. + /// [XmlAttribute("sender")] public string Sender { get; set; } + /// + /// The maximum number of observations the agent's streaming buffer can + /// hold. + /// [XmlAttribute("bufferSize")] public ulong BufferSize { get; set; } + /// + /// The maximum number of assets the agent can store. + /// [XmlAttribute("assetBufferSize")] public ulong AssetBufferSize { get; set; } + /// + /// The current number of assets the agent is storing. + /// [XmlAttribute("assetCount")] public ulong AssetCount { get; set; } + /// + /// The time the device model last changed, as the raw attribute text. + /// [XmlAttribute("deviceModelChangeTime")] public string DeviceModelChangeTime { get; set; } + /// + /// Whether the agent is operating in a test capacity rather than + /// production. + /// [XmlAttribute("testIndicator")] public bool TestIndicator { get; set; } + /// + /// Whether the agent validates documents against the MTConnect schema. + /// [XmlAttribute("validation")] public bool Validation { get; set; } + /// + /// The time the document was created. + /// [XmlAttribute("creationTime")] public DateTime CreationTime { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// . + /// public virtual IMTConnectDevicesHeader ToDevicesHeader() { var header = new MTConnectDevicesHeader(); @@ -57,6 +99,11 @@ public virtual IMTConnectDevicesHeader ToDevicesHeader() return header; } + /// + /// Writes the given to + /// as a Header element, omitting + /// optional attributes that are not set. + /// public static void WriteXml(XmlWriter writer, IMTConnectDevicesHeader header) { if (header != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlDevicesResponseDocument.cs b/libraries/MTConnect.NET-XML/Devices/XmlDevicesResponseDocument.cs index c819eb5bd..6c9190a13 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlDevicesResponseDocument.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlDevicesResponseDocument.cs @@ -11,15 +11,28 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for the root MTConnectDevices + /// response document returned by the agent probe request. Mirrors + /// the on-the-wire shape so it can be read and written, then converts to + /// and from the strongly-typed model. + /// [XmlRoot("MTConnectDevices")] public class XmlDevicesResponseDocument { private static readonly XmlSerializer _serializer = new XmlSerializer(typeof(XmlDevicesResponseDocument)); + /// + /// The document Header describing the agent instance and version. + /// [XmlElement("Header")] public XmlDevicesHeader Header { get; set; } + /// + /// The devices in the document, serialized as Device elements + /// (or Agent for the self-describing agent device). + /// [XmlArray("Devices")] [XmlArrayItem("Device", typeof(XmlDevice))] [XmlArrayItem("Agent", typeof(XmlAgent))] @@ -28,10 +41,19 @@ public class XmlDevicesResponseDocument //[XmlArray("Interfaces")] //public List Interfaces { get; set; } + /// + /// The MTConnect schema version detected from the source XML; carried + /// out of band so the correct namespace can be emitted on write. + /// [XmlIgnore] public Version Version { get; set; } + /// + /// Converts this surrogate to a strongly-typed + /// , converting the header and each + /// device and stamping every device with the detected schema version. + /// public IDevicesResponseDocument ToDocument() { var document = new DevicesResponseDocument(); @@ -57,6 +79,11 @@ public IDevicesResponseDocument ToDocument() return document; } + /// + /// Deserializes an MTConnectDevices document from raw XML bytes, + /// sanitizing the input, detecting the schema version, and clearing + /// namespace prefixes before deserialization. + /// /// XML Exception thrown during Serialization public static IDevicesResponseDocument FromXml(byte[] xmlBytes) { @@ -89,6 +116,11 @@ public static IDevicesResponseDocument FromXml(byte[] xmlBytes) return null; } + /// + /// Serializes the devices response document to a UTF-8 XML byte array, + /// choosing indented or compact writer settings and optionally emitting + /// a stylesheet, header comment, and extended schema namespaces. + /// /// XML Exception thrown during Serialization public static byte[] ToXmlBytes( IDevicesResponseDocument document, @@ -117,6 +149,11 @@ public static byte[] ToXmlBytes( return null; } + /// + /// Serializes the devices response document to a new XML stream, + /// choosing indented or compact writer settings and optionally emitting + /// a stylesheet, header comment, and extended schema namespaces. + /// /// XML Exception thrown during Serialization public static Stream ToXmlStream( IDevicesResponseDocument document, @@ -144,6 +181,12 @@ public static Stream ToXmlStream( return null; } + /// + /// Writes the complete MTConnectDevices document, emitting the + /// version-specific namespace, optional extended schema namespaces and + /// schema location, the header, and each device. No document is written + /// when the response has no devices. + /// /// XML Exception thrown during Serialization public static void WriteXml( XmlWriter writer, diff --git a/libraries/MTConnect.NET-XML/Devices/XmlEntry.cs b/libraries/MTConnect.NET-XML/Devices/XmlEntry.cs index d71c8fc5c..84d8d78f8 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlEntry.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlEntry.cs @@ -10,11 +10,23 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for a single keyed entry of a three-dimensional + /// data set (the ThreeDimensionalEntryType used by the polymorphic + /// Configuration data sets such as XYZDataSet and ABCDataSet). + /// public class XmlEntry { + /// + /// The axis the entry applies to, carried by the required key + /// attribute (one of X, Y, Z, A, B, C). + /// [XmlAttribute("key")] public string Key { get; set; } + /// + /// The decimal value for the keyed axis, carried as the element's text content. + /// [XmlText] public string Value { get; set; } } diff --git a/libraries/MTConnect.NET-XML/Devices/XmlEntryDefinition.cs b/libraries/MTConnect.NET-XML/Devices/XmlEntryDefinition.cs index 4f12c9a02..b8860ab74 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlEntryDefinition.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlEntryDefinition.cs @@ -7,31 +7,64 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for an EntryDefinition, the schema + /// describing one keyed entry of a data-set or table data item. Mirrors the + /// on-the-wire element and converts to and from the strongly-typed + /// model. + /// public class XmlEntryDefinition { + /// + /// The key that identifies the entry. + /// [XmlAttribute("key")] public string Key { get; set; } + /// + /// The semantic meaning of the entry's key. + /// [XmlAttribute("keyType")] public string KeyType { get; set; } + /// + /// The engineering units of the entry's value. + /// [XmlAttribute("units")] public string Units { get; set; } + /// + /// The type of the entry's value. + /// [XmlAttribute("type")] public string Type { get; set; } + /// + /// The optional subtype that further qualifies . + /// [XmlAttribute("subType")] public string SubType { get; set; } + /// + /// The free-form description of the entry. + /// [XmlElement("Description")] public XmlDescription Description { get; set; } + /// + /// The definitions of the cells of the entry when it is part of a table + /// data item. + /// [XmlArray("CellDefinitions")] [XmlArrayItem("CellDefinition")] public List CellDefinitions { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , projecting the nested cell + /// definitions into their model representation. + /// public IEntryDefinition ToEntryDefinition() { var definition = new EntryDefinition(); @@ -39,7 +72,7 @@ public IEntryDefinition ToEntryDefinition() definition.KeyType = KeyType; definition.Units = Units; definition.Type = Type; - definition.SubType = SubType;; + definition.SubType = SubType; ; definition.Description = Description?.CDATA; //definition.Description = Description?.ToDescription(); @@ -57,6 +90,11 @@ public IEntryDefinition ToEntryDefinition() return definition; } + /// + /// Writes the given to + /// as an EntryDefinition element, + /// omitting optional attributes and the cell definitions when not set. + /// public static void WriteXml(XmlWriter writer, IEntryDefinition entryDefinition) { if (entryDefinition != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlFilter.cs b/libraries/MTConnect.NET-XML/Devices/XmlFilter.cs index 60c7d0fc8..d3dd5268f 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlFilter.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlFilter.cs @@ -6,15 +6,31 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for a DataItem Filter, which + /// constrains when a data item reports observations (for example a + /// MINIMUM_DELTA or PERIOD filter). + /// public class XmlFilter { + /// + /// The filter kind, carried by the type attribute (for example + /// MINIMUM_DELTA or PERIOD). + /// [XmlAttribute("type")] public DataItemFilterType Type { get; set; } + /// + /// The filter threshold value, carried as the element's text content. + /// [XmlText] public double Value { get; set; } + /// + /// Converts this surrogate to a strongly-typed , + /// copying the filter type and threshold. + /// public IFilter ToFilter() { var filter = new Filter(); @@ -23,6 +39,10 @@ public IFilter ToFilter() return filter; } + /// + /// Writes the Filter element for the supplied model, emitting the + /// type attribute and the threshold value as element content. + /// public static void WriteXml(XmlWriter writer, IFilter filter) { if (filter != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlMotion.cs b/libraries/MTConnect.NET-XML/Devices/XmlMotion.cs index a1cbe97a6..3d0eb611d 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlMotion.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlMotion.cs @@ -13,43 +13,92 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for the MTConnect Motion element that + /// defines the kinematic relationship of a component to its parent. Mirrors + /// the on-the-wire element and converts to and from the strongly-typed + /// model. + /// [XmlRoot("Motion")] public class XmlMotion { + /// + /// The unique identifier of the motion within the device. + /// [XmlAttribute("id")] public string Id { get; set; } + /// + /// The id of the parent motion this motion is defined relative + /// to. + /// [XmlAttribute("parentIdRef")] public string ParentIdRef { get; set; } + /// + /// The id of the coordinate system the motion is defined in. + /// [XmlAttribute("coordinateSystemIdRef")] public string CoordinateSystemIdRef { get; set; } + /// + /// The type of motion, such as REVOLUTE or PRISMATIC. + /// [XmlAttribute("type")] public MotionType Type { get; set; } + /// + /// How the motion is actuated, such as DIRECT or VIRTUAL. + /// [XmlAttribute("actuation")] public MotionActuationType Actuation { get; set; } + /// + /// The free-form description of the motion. + /// [XmlElement("Description")] public XmlDescription Description { get; set; } + /// + /// The origin of the motion expressed as a coordinate triple; mutually + /// exclusive with . + /// [XmlElement("Origin")] public XmlOrigin Origin { get; set; } + /// + /// The origin of the motion expressed as a data set; mutually exclusive + /// with . + /// [XmlElement("OriginDataSet")] public XmlOriginDataSet OriginDataSet { get; set; } + /// + /// The translation and rotation applied relative to the parent motion. + /// [XmlElement("Transformation")] public XmlTransformation Transformation { get; set; } + /// + /// The axis of motion expressed as a coordinate triple; mutually + /// exclusive with . + /// [XmlElement("Axis")] public XmlAxis Axis { get; set; } + /// + /// The axis of motion expressed as a data set; mutually exclusive with + /// . + /// [XmlElement("AxisDataSet")] public XmlAxisDataSet AxisDataSet { get; set; } + /// + /// Converts this surrogate into the strongly-typed , + /// resolving the Origin and Axis choices in favour of the data-set form + /// when present. + /// public IMotion ToMotion() { var motion = new Motion(); @@ -67,6 +116,11 @@ public IMotion ToMotion() return motion; } + /// + /// Writes the given to + /// as a Motion element, emitting the data-set form of Origin and + /// Axis when the model carries it. + /// public static void WriteXml(XmlWriter writer, IMotion motion) { if (motion != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlOrigin.cs b/libraries/MTConnect.NET-XML/Devices/XmlOrigin.cs index c29b11896..5a0e63b46 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlOrigin.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlOrigin.cs @@ -12,13 +12,24 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for the Origin element of a Component + /// Configuration CoordinateSystem, carrying the position of + /// the coordinate-system origin as simple element content. + /// [XmlRoot("Origin")] public class XmlOrigin { + /// + /// The origin values as the raw, space-delimited element text content. + /// [XmlText] public string Value { get; set; } + /// + /// Converts this surrogate to a strongly-typed . + /// public IOrigin ToOrigin() { var origin = new Origin(); @@ -26,6 +37,10 @@ public IOrigin ToOrigin() return origin; } + /// + /// Writes the Origin element for the supplied model, emitting the + /// value as element text and omitting an empty value. + /// public static void WriteXml(XmlWriter writer, IOrigin origin) { if (origin != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlOriginDataSet.cs b/libraries/MTConnect.NET-XML/Devices/XmlOriginDataSet.cs index 9daada977..167834b21 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlOriginDataSet.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlOriginDataSet.cs @@ -14,13 +14,27 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for the OriginDataSet element, the + /// keyed-entry representation of a coordinate-system origin where each + /// position component is carried as an Entry keyed X, + /// Y, or Z. + /// [XmlRoot("OriginDataSet")] public class XmlOriginDataSet { + /// + /// The per-axis origin entries as serialized Entry elements. + /// [XmlElement("Entry")] public List Entries { get; set; } + /// + /// Converts the keyed entries to a strongly-typed + /// , mapping each X/Y/Z + /// entry to its position property and ignoring unkeyed entries. + /// public IOriginDataSet ToOriginDataSet() { var dataSet = new OriginDataSet(); @@ -40,6 +54,10 @@ public IOriginDataSet ToOriginDataSet() return dataSet; } + /// + /// Writes the OriginDataSet element, emitting one keyed + /// Entry per component and omitting components with no value. + /// public static void WriteXml(XmlWriter writer, IOriginDataSet dataSet) { if (dataSet != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlProcessSpecification.cs b/libraries/MTConnect.NET-XML/Devices/XmlProcessSpecification.cs index 10a23b3cd..e14070c2d 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlProcessSpecification.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlProcessSpecification.cs @@ -7,19 +7,40 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for a ProcessSpecification, the + /// specification variant that carries process control, specification, and + /// alarm limit ranges in addition to the shared specification attributes. + /// [XmlRoot("ProcessSpecification")] public class XmlProcessSpecification : XmlAbstractSpecification { + /// + /// The process control limits, serialized as the ControlLimits + /// element. + /// [XmlElement("ControlLimits")] public XmlControlLimits ControlLimits { get; set; } + /// + /// The specification (acceptance) limits, serialized as the + /// SpecificationLimits element. + /// [XmlElement("SpecificationLimits")] public XmlSpecificationLimits SpecificationLimits { get; set; } + /// + /// The alarm limits, serialized as the AlarmLimits element. + /// [XmlElement("AlarmLimits")] public XmlAlarmLimits AlarmLimits { get; set; } + /// + /// Converts this surrogate to a strongly-typed + /// , copying the shared specification + /// attributes and converting each present limit set. + /// public override ISpecification ToSpecification() { var specification = new ProcessSpecification(); diff --git a/libraries/MTConnect.NET-XML/Devices/XmlReference.cs b/libraries/MTConnect.NET-XML/Devices/XmlReference.cs index 0e43ce2de..3b9c6adfb 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlReference.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlReference.cs @@ -7,15 +7,34 @@ namespace MTConnect.Devices.Xml { + /// + /// Base XML serialization surrogate for an MTConnect reference (the + /// DataItemRef / ComponentRef family). Carries the common + /// idRef/name attributes and dispatches element naming on the + /// concrete reference type. + /// public class XmlReference { + /// + /// The id of the referenced data item or component, carried by + /// the idRef attribute. + /// [XmlAttribute("idRef")] public string IdRef { get; set; } + /// + /// The optional display name for the reference, carried by the + /// name attribute. + /// [XmlAttribute("name")] public string Name { get; set; } + /// + /// Converts this surrogate to a strongly-typed reference. The base + /// implementation returns null; concrete subclasses override it + /// to produce the appropriate reference type. + /// public virtual IReference ToReference() { return null; } //public virtual IReference ToReference() @@ -26,6 +45,12 @@ public class XmlReference // return reference; //} + /// + /// Writes the reference element, selecting the element name + /// (DataItemRef, ComponentRef, or generic + /// Reference) from the concrete reference type and emitting the + /// idRef and optional name attributes. + /// public static void WriteXml(XmlWriter writer, IReference reference) { if (reference != null) @@ -42,7 +67,7 @@ public static void WriteXml(XmlWriter writer, IReference reference) // Write Properties writer.WriteAttributeString("idRef", reference.IdRef); if (!string.IsNullOrEmpty(reference.Name)) writer.WriteAttributeString("name", reference.Name); - + writer.WriteEndElement(); } } diff --git a/libraries/MTConnect.NET-XML/Devices/XmlRotation.cs b/libraries/MTConnect.NET-XML/Devices/XmlRotation.cs index a56c011ff..0e7c74d9c 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlRotation.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlRotation.cs @@ -12,13 +12,24 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for the Rotation element of a + /// Component Configuration CoordinateSystem, carrying the + /// rotation about each axis as simple element content. + /// [XmlRoot("Rotation")] public class XmlRotation { + /// + /// The rotation values as the raw, space-delimited element text content. + /// [XmlText] public string Value { get; set; } + /// + /// Converts this surrogate to a strongly-typed . + /// public IRotation ToRotation() { var rotation = new Rotation(); @@ -26,6 +37,10 @@ public IRotation ToRotation() return rotation; } + /// + /// Writes the Rotation element for the supplied model, emitting + /// the value as element text and omitting an empty value. + /// public static void WriteXml(XmlWriter writer, IRotation rotation) { if (rotation != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlRotationDataSet.cs b/libraries/MTConnect.NET-XML/Devices/XmlRotationDataSet.cs index e1b312412..46f4255b6 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlRotationDataSet.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlRotationDataSet.cs @@ -14,13 +14,27 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for the RotationDataSet element, the + /// keyed-entry representation of a coordinate-system rotation where each + /// rotation component is carried as an Entry keyed A, + /// B, or C. + /// [XmlRoot("RotationDataSet")] public class XmlRotationDataSet { + /// + /// The per-axis rotation entries as serialized Entry elements. + /// [XmlElement("Entry")] public List Entries { get; set; } + /// + /// Converts the keyed entries to a strongly-typed + /// , mapping each A/B/C + /// entry to its component property and ignoring unkeyed entries. + /// public IRotationDataSet ToRotationDataSet() { var dataSet = new RotationDataSet(); @@ -40,6 +54,10 @@ public IRotationDataSet ToRotationDataSet() return dataSet; } + /// + /// Writes the RotationDataSet element, emitting one keyed + /// Entry per component and omitting components with no value. + /// public static void WriteXml(XmlWriter writer, IRotationDataSet dataSet) { if (dataSet != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlScale.cs b/libraries/MTConnect.NET-XML/Devices/XmlScale.cs index 792939717..9cd542438 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlScale.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlScale.cs @@ -13,13 +13,24 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for the solid-model Scale element of a + /// Component Configuration, carrying the scale factor(s) applied to a + /// referenced solid model as simple element content. + /// [XmlRoot("Scale")] public class XmlScale { + /// + /// The scale value(s) as the raw, space-delimited element text content. + /// [XmlText] public string Value { get; set; } + /// + /// Converts this surrogate to a strongly-typed . + /// public IScale ToScale() { var scale = new Scale(); @@ -27,6 +38,10 @@ public IScale ToScale() return scale; } + /// + /// Writes the Scale element for the supplied model, emitting the + /// value as element text and omitting an empty value. + /// public static void WriteXml(XmlWriter writer, IScale scale) { if (scale != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlScaleDataSet.cs b/libraries/MTConnect.NET-XML/Devices/XmlScaleDataSet.cs index d8a7c52f6..bd89322bd 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlScaleDataSet.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlScaleDataSet.cs @@ -15,13 +15,26 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for the ScaleDataSet element, the + /// keyed-entry representation of a solid-model scale where each axis factor + /// is carried as an Entry keyed X, Y, or Z. + /// [XmlRoot("ScaleDataSet")] public class XmlScaleDataSet { + /// + /// The per-axis scale entries as serialized Entry elements. + /// [XmlElement("Entry")] public List Entries { get; set; } + /// + /// Converts the keyed entries to a strongly-typed + /// , mapping each X/Y/Z + /// entry to its axis property and ignoring unkeyed entries. + /// public IScaleDataSet ToScaleDataSet() { var dataSet = new ScaleDataSet(); @@ -42,6 +55,10 @@ public IScaleDataSet ToScaleDataSet() return dataSet; } + /// + /// Writes the ScaleDataSet element, emitting one keyed + /// Entry per axis using invariant-culture number formatting. + /// public static void WriteXml(XmlWriter writer, IScaleDataSet dataSet) { if (dataSet != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlSensorConfiguration.cs b/libraries/MTConnect.NET-XML/Devices/XmlSensorConfiguration.cs index e46705091..1204e7c6f 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlSensorConfiguration.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlSensorConfiguration.cs @@ -9,26 +9,52 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for a SensorConfiguration, the + /// calibration metadata and channels of a sensor component. Mirrors the + /// on-the-wire element and converts to and from the strongly-typed + /// model. + /// [XmlRoot("SensorConfiguration")] public class XmlSensorConfiguration { + /// + /// The firmware version running on the sensor. + /// [XmlElement("FirmwareVersion")] public string FirmwareVersion { get; set; } + /// + /// The date the sensor was last calibrated. + /// [XmlElement("CalibrationDate")] public DateTime? CalibrationDate { get; set; } + /// + /// The date the sensor is next due for calibration. + /// [XmlElement("NextCalibrationDate")] public DateTime? NextCalibrationDate { get; set; } + /// + /// The initials of the person who performed the calibration. + /// [XmlElement("CalibrationInitials")] public string CalibrationInitials { get; set; } + /// + /// The individual calibrated input channels of the sensor. + /// [XmlArray("Channels")] [XmlArrayItem("Channel", typeof(XmlChannel))] public List Channels { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , projecting the channels into + /// their model representation. + /// public ISensorConfiguration ToSensorConfiguration() { var sensorConfiguration = new SensorConfiguration(); @@ -51,6 +77,11 @@ public ISensorConfiguration ToSensorConfiguration() return sensorConfiguration; } + /// + /// Writes the given to + /// as a SensorConfiguration element, + /// omitting calibration metadata and channels that are not set. + /// public static void WriteXml(XmlWriter writer, ISensorConfiguration sensorConfiguration) { if (sensorConfiguration != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlSolidModel.cs b/libraries/MTConnect.NET-XML/Devices/XmlSolidModel.cs index 8dd217c6c..b29dcc3b7 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlSolidModel.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlSolidModel.cs @@ -13,37 +13,79 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for an MTConnect SolidModel, the + /// reference to a 3D geometry file describing a component. Mirrors the + /// on-the-wire element and converts to and from the strongly-typed + /// model. + /// [XmlRoot("SolidModel")] public class XmlSolidModel { + /// + /// The unique identifier of the solid model within the device. + /// [XmlAttribute("id")] public string Id { get; set; } + /// + /// The id of another solid model this one is defined relative + /// to. + /// [XmlAttribute("solidModelIdRef")] public string SolidModelIdRef { get; set; } + /// + /// The URL the model file can be retrieved from. + /// [XmlAttribute("href")] public string Href { get; set; } + /// + /// The identifier of the specific item within the referenced model + /// file. + /// [XmlAttribute("itemRef")] public string ItemRef { get; set; } + /// + /// The format of the model file, such as STEP or STL. + /// [XmlAttribute("mediaType")] public MediaType MediaType { get; set; } + /// + /// The id of the coordinate system the model is defined in. + /// [XmlAttribute("coordinateSystemIdRef")] public string CoordinateSystemIdRef { get; set; } + /// + /// The translation and rotation applied to position the model. + /// [XmlElement("Transformation")] public XmlTransformation Transformation { get; set; } + /// + /// The scale applied to the model expressed as a coordinate triple; + /// mutually exclusive with . + /// [XmlElement("Scale")] public XmlScale Scale { get; set; } + /// + /// The scale applied to the model expressed as a data set; mutually + /// exclusive with . + /// [XmlElement("ScaleDataSet")] public XmlScaleDataSet ScaleDataSet { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , resolving the Scale choice in favour of + /// the data-set form when present. + /// public ISolidModel ToSolidModel() { var solidModel = new SolidModel(); @@ -59,6 +101,11 @@ public ISolidModel ToSolidModel() return solidModel; } + /// + /// Writes the given to + /// as a SolidModel element, emitting + /// the data-set form of Scale when the model carries it. + /// public static void WriteXml(XmlWriter writer, ISolidModel solidModel) { if (solidModel != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlSource.cs b/libraries/MTConnect.NET-XML/Devices/XmlSource.cs index 72897c40d..177ab7db0 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlSource.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlSource.cs @@ -7,21 +7,43 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for a data item's Source, which + /// identifies the component, composition, or data item the value + /// originates from. Mirrors the on-the-wire element and converts to and + /// from the strongly-typed model. + /// public class XmlSource { + /// + /// The id of the component the value originates from. + /// [XmlAttribute("componentId")] public string ComponentId { get; set; } + /// + /// The id of the data item the value originates from. + /// [XmlAttribute("dataItemId")] public string DataItemId { get; set; } + /// + /// The id of the composition the value originates from. + /// [XmlAttribute("compositionId")] public string CompositionId { get; set; } + /// + /// The native source identifier, carried as the element text. + /// [XmlText] public string Value { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// . + /// public ISource ToSource() { var source = new Source(); @@ -32,6 +54,11 @@ public ISource ToSource() return source; } + /// + /// Writes the given to + /// as a Source element, skipping the element entirely when every + /// field is empty. + /// public static void WriteXml(XmlWriter writer, ISource source) { if (source != null && (!string.IsNullOrEmpty(source.ComponentId) || !string.IsNullOrEmpty(source.CompositionId) || !string.IsNullOrEmpty(source.DataItemId) || !string.IsNullOrEmpty(source.Value))) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlSpecification.cs b/libraries/MTConnect.NET-XML/Devices/XmlSpecification.cs index 8d8df8486..fb5473749 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlSpecification.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlSpecification.cs @@ -7,31 +7,65 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for an MTConnect Specification, the + /// set of limits a measured value is expected to fall within. Mirrors the + /// on-the-wire element and converts to the strongly-typed + /// model. + /// [XmlRoot("Specification")] public class XmlSpecification : XmlAbstractSpecification { + /// + /// The upper conformance boundary; a value at or above this is + /// non-conforming. + /// [XmlElement("Maximum")] public double? Maximum { get; set; } + /// + /// The upper boundary of the in-specification range. + /// [XmlElement("UpperLimit")] public double? UpperLimit { get; set; } + /// + /// The upper boundary indicating a warning condition. + /// [XmlElement("UpperWarning")] public double? UpperWarning { get; set; } + /// + /// The ideal or target value. + /// [XmlElement("Nominal")] public double? Nominal { get; set; } + /// + /// The lower boundary of the in-specification range. + /// [XmlElement("LowerLimit")] public double? LowerLimit { get; set; } + /// + /// The lower boundary indicating a warning condition. + /// [XmlElement("LowerWarning")] public double? LowerWarning { get; set; } + /// + /// The lower conformance boundary; a value at or below this is + /// non-conforming. + /// [XmlElement("Minimum")] - public double? Minimum { get; set; } + public double? Minimum { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , including the inherited identification + /// attributes and the numeric limits. + /// public override ISpecification ToSpecification() { var specification = new Specification(); @@ -54,6 +88,11 @@ public override ISpecification ToSpecification() return specification; } + /// + /// Writes the given to + /// , choosing the element name and the + /// limit-writing path that match the concrete specification kind. + /// public static void WriteXml(XmlWriter writer, ISpecification specification) { if (specification != null) @@ -75,6 +114,11 @@ public static void WriteXml(XmlWriter writer, ISpecification specification) } } + /// + /// Writes the identification attributes shared by every specification + /// kind, omitting the originator when it is the default + /// (MANUFACTURER). + /// public static void WriteAbstractXml(XmlWriter writer, ISpecification specification) { if (specification != null) @@ -92,6 +136,10 @@ public static void WriteAbstractXml(XmlWriter writer, ISpecification specificati } } + /// + /// Writes the scalar limit elements of a plain + /// , emitting only those that are set. + /// public static void WriteSpecificationXml(XmlWriter writer, ISpecification specification) { if (specification != null) @@ -154,6 +202,11 @@ public static void WriteSpecificationXml(XmlWriter writer, ISpecification specif } } + /// + /// Writes the control, specification, and alarm limit groups of an + /// , emitting only the groups that + /// are present. + /// public static void WriteProcessSpecificationXml(XmlWriter writer, IProcessSpecification specification) { if (specification != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlSpecificationLimits.cs b/libraries/MTConnect.NET-XML/Devices/XmlSpecificationLimits.cs index d61898e6d..6ba3c8160 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlSpecificationLimits.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlSpecificationLimits.cs @@ -7,19 +7,40 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for the SpecificationLimits element + /// of a Specification, carrying the upper/nominal/lower acceptance bounds + /// as optional child elements. + /// [XmlRoot("SpecificationLimits")] public class XmlSpecificationLimits { + /// + /// The upper acceptance bound, serialized as the optional + /// UpperLimit element. + /// [XmlElement("UpperLimit")] public double? UpperLimit { get; set; } + /// + /// The nominal (target) value, serialized as the optional + /// Nominal element. + /// [XmlElement("Nominal")] public double? Nominal { get; set; } + /// + /// The lower acceptance bound, serialized as the optional + /// LowerLimit element. + /// [XmlElement("LowerLimit")] public double? LowerLimit { get; set; } + /// + /// Converts this surrogate to a strongly-typed + /// , copying each present bound. + /// public ISpecificationLimits ToSpecificationLimits() { var specificationLimits = new SpecificationLimits(); @@ -29,6 +50,10 @@ public ISpecificationLimits ToSpecificationLimits() return specificationLimits; } + /// + /// Writes the specification limits element, emitting only the bounds + /// that are present. + /// public static void WriteXml(XmlWriter writer, ISpecificationLimits specificationLimits) { if (specificationLimits != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlSpecificationRelationship.cs b/libraries/MTConnect.NET-XML/Devices/XmlSpecificationRelationship.cs index eafc580ed..4b04462c9 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlSpecificationRelationship.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlSpecificationRelationship.cs @@ -6,13 +6,27 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for a SpecificationRelationship, + /// associating a Specification with another specification it depends on, + /// limits, or otherwise relates to. + /// [XmlRoot("SpecificationRelationship")] public class XmlSpecificationRelationship : XmlAbstractDataItemRelationship { + /// + /// The kind of relationship to the referenced specification, carried by + /// the type attribute (for example LIMIT). + /// [XmlAttribute("type")] public SpecificationRelationshipType Type { get; set; } + /// + /// Converts this surrogate to a strongly-typed + /// , copying the relationship + /// name, referenced id, and relationship type. + /// public override IAbstractDataItemRelationship ToRelationship() { var relationship = new SpecificationRelationship(); @@ -22,6 +36,10 @@ public override IAbstractDataItemRelationship ToRelationship() return relationship; } + /// + /// Writes the relationship element, emitting the shared relationship + /// attributes followed by the type attribute. + /// public static void WriteXml(XmlWriter writer, ISpecificationRelationship relationship) { if (relationship != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlTransformation.cs b/libraries/MTConnect.NET-XML/Devices/XmlTransformation.cs index c5dce408a..92014534f 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlTransformation.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlTransformation.cs @@ -14,22 +14,49 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for a Transformation, the + /// translation and rotation that position a component relative to its + /// parent. Mirrors the on-the-wire element and converts to and from the + /// strongly-typed model. + /// [XmlRoot("Transformation")] public class XmlTransformation { + /// + /// The translation expressed as a coordinate triple; mutually + /// exclusive with . + /// [XmlElement("Translation")] public XmlTranslation Translation { get; set; } + /// + /// The translation expressed as a data set; mutually exclusive with + /// . + /// [XmlElement("TranslationDataSet")] public XmlTranslationDataSet TranslationDataSet { get; set; } + /// + /// The rotation expressed as a coordinate triple; mutually exclusive + /// with . + /// [XmlElement("Rotation")] public XmlRotation Rotation { get; set; } + /// + /// The rotation expressed as a data set; mutually exclusive with + /// . + /// [XmlElement("RotationDataSet")] public XmlRotationDataSet RotationDataSet { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// , resolving the translation and rotation + /// choices in favour of the data-set form when present. + /// public ITransformation ToTransformation() { var transformation = new Transformation(); @@ -40,6 +67,12 @@ public ITransformation ToTransformation() return transformation; } + /// + /// Writes the given to + /// as a Transformation element, + /// emitting the data-set form of translation and rotation when the + /// model carries it. + /// public static void WriteXml(XmlWriter writer, ITransformation transformation) { if (transformation != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlTranslation.cs b/libraries/MTConnect.NET-XML/Devices/XmlTranslation.cs index 2cacc1c34..d3b84d3ff 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlTranslation.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlTranslation.cs @@ -12,13 +12,25 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for the Translation element of a + /// Component Configuration CoordinateSystem, carrying the + /// translation vector relative to the parent coordinate system as simple + /// element content. + /// [XmlRoot("Translation")] public class XmlTranslation { + /// + /// The translation values as the raw, space-delimited element text content. + /// [XmlText] public string Value { get; set; } + /// + /// Converts this surrogate to a strongly-typed . + /// public ITranslation ToTranslation() { var translation = new Translation(); @@ -26,6 +38,10 @@ public ITranslation ToTranslation() return translation; } + /// + /// Writes the Translation element for the supplied model, + /// emitting the value as element text and omitting an empty value. + /// public static void WriteXml(XmlWriter writer, ITranslation translation) { if (translation != null) diff --git a/libraries/MTConnect.NET-XML/Devices/XmlTranslationDataSet.cs b/libraries/MTConnect.NET-XML/Devices/XmlTranslationDataSet.cs index 94f4abf52..dfc14913e 100644 --- a/libraries/MTConnect.NET-XML/Devices/XmlTranslationDataSet.cs +++ b/libraries/MTConnect.NET-XML/Devices/XmlTranslationDataSet.cs @@ -14,13 +14,28 @@ namespace MTConnect.Devices.Xml { + /// + /// XML serialization surrogate for the TranslationDataSet element, + /// the keyed-entry representation of a coordinate-system translation where + /// each component is carried as an Entry keyed X, Y, + /// or Z. + /// [XmlRoot("TranslationDataSet")] public class XmlTranslationDataSet { + /// + /// The per-axis translation entries as serialized Entry elements. + /// [XmlElement("Entry")] public List Entries { get; set; } + /// + /// Converts the keyed entries to a strongly-typed + /// , mapping each + /// X/Y/Z entry to its component property and + /// ignoring unkeyed entries. + /// public ITranslationDataSet ToTranslationDataSet() { var dataSet = new TranslationDataSet(); @@ -40,6 +55,10 @@ public ITranslationDataSet ToTranslationDataSet() return dataSet; } + /// + /// Writes the TranslationDataSet element, emitting one keyed + /// Entry per component and omitting components with no value. + /// public static void WriteXml(XmlWriter writer, ITranslationDataSet dataSet) { if (dataSet != null) diff --git a/libraries/MTConnect.NET-XML/Errors/XmlError.cs b/libraries/MTConnect.NET-XML/Errors/XmlError.cs index 50a79f169..eeb059e4b 100644 --- a/libraries/MTConnect.NET-XML/Errors/XmlError.cs +++ b/libraries/MTConnect.NET-XML/Errors/XmlError.cs @@ -5,15 +5,31 @@ namespace MTConnect.Errors.Xml { + /// + /// XML serialization surrogate for a single Error element within an + /// MTConnectError response document. + /// public class XmlError { + /// + /// The standardized MTConnect error code, carried by the + /// errorCode attribute. + /// [XmlAttribute("errorCode")] public ErrorCode ErrorCode { get; set; } + /// + /// The human-readable error description, carried as the element's text + /// content. + /// [XmlText] public string Value { get; set; } + /// + /// Converts this surrogate to a strongly-typed , + /// copying the error code and message. + /// public IError ToError() { var error = new Error(); diff --git a/libraries/MTConnect.NET-XML/Errors/XmlErrorDocument.cs b/libraries/MTConnect.NET-XML/Errors/XmlErrorDocument.cs index 5c92c8e7f..f8fa6cda1 100644 --- a/libraries/MTConnect.NET-XML/Errors/XmlErrorDocument.cs +++ b/libraries/MTConnect.NET-XML/Errors/XmlErrorDocument.cs @@ -10,22 +10,44 @@ namespace MTConnect.Errors.Xml { + /// + /// XML serialization surrogate for the root MTConnectError response + /// document returned when the agent rejects a request. Mirrors the + /// on-the-wire shape so it can be read and written, then converts to and + /// from the strongly-typed model. + /// [XmlRoot("MTConnectError")] public class XmlErrorResponseDocument { private static readonly XmlSerializer _serializer = new XmlSerializer(typeof(XmlErrorResponseDocument)); + /// + /// The document Header describing the agent instance and version. + /// [XmlElement("Header")] public XmlErrorHeader Header { get; set; } + /// + /// The reported errors, serialized as child Error elements of an + /// Errors container. + /// [XmlArray("Errors")] public List Errors { get; set; } + /// + /// The MTConnect schema version detected from the source XML; carried + /// out of band so the correct namespace can be emitted on write. + /// [XmlIgnore] public Version Version { get; set; } + /// + /// Converts this surrogate to a strongly-typed + /// , converting the header and each + /// error and propagating the detected version. + /// public IErrorResponseDocument ToResponseDocument() { var document = new ErrorResponseDocument(); @@ -46,6 +68,11 @@ public IErrorResponseDocument ToResponseDocument() } + /// + /// Deserializes an MTConnectError document from raw XML bytes, + /// sanitizing the input, detecting the schema version, and clearing + /// namespace prefixes before deserialization. + /// /// XML Exception thrown during Serialization public static IErrorResponseDocument FromXml(byte[] xmlBytes) { @@ -77,6 +104,11 @@ public static IErrorResponseDocument FromXml(byte[] xmlBytes) } + /// + /// Serializes the error response document to a new XML stream, choosing + /// indented or compact writer settings and optionally emitting a + /// stylesheet reference and header comment. + /// public static Stream ToXmlStream( IErrorResponseDocument document, bool indentOutput = true, @@ -104,6 +136,12 @@ public static Stream ToXmlStream( return null; } + /// + /// Writes the complete MTConnectError document, emitting the + /// version-specific namespace and schema location, the header, and one + /// Error element per reported error. No document is written when + /// the response has no errors. + /// public static void WriteXml( XmlWriter writer, IErrorResponseDocument document, diff --git a/libraries/MTConnect.NET-XML/Errors/XmlErrorHeader.cs b/libraries/MTConnect.NET-XML/Errors/XmlErrorHeader.cs index 8f8520eaf..9cd06eb41 100644 --- a/libraries/MTConnect.NET-XML/Errors/XmlErrorHeader.cs +++ b/libraries/MTConnect.NET-XML/Errors/XmlErrorHeader.cs @@ -8,36 +8,74 @@ namespace MTConnect.Errors.Xml { + /// + /// XML serialization surrogate for the Header of an MTConnectError + /// response document. Mirrors the on-the-wire element and converts to the + /// strongly-typed model. + /// public class XmlErrorHeader { + /// + /// The agent instance identifier; changes whenever the agent restarts. + /// [XmlAttribute("instanceId")] public ulong InstanceId { get; set; } + /// + /// The version of the MTConnect Standard the document conforms to. + /// [XmlAttribute("version")] public string Version { get; set; } + /// + /// The identifier of the agent that produced the document. + /// [XmlAttribute("sender")] public string Sender { get; set; } + /// + /// The maximum number of observations the agent's streaming buffer can + /// hold. + /// [XmlAttribute("bufferSize")] public ulong BufferSize { get; set; } + /// + /// The maximum number of assets the agent can store. + /// [XmlAttribute("assetBufferSize")] public ulong AssetBufferSize { get; set; } + /// + /// The current number of assets the agent is storing. + /// [XmlAttribute("assetCount")] public ulong AssetCount { get; set; } + /// + /// The time the device model last changed, as the raw attribute text. + /// [XmlAttribute("deviceModelChangeTime")] public string DeviceModelChangeTime { get; set; } + /// + /// Whether the agent is operating in a test capacity rather than + /// production. + /// [XmlAttribute("testIndicator")] public bool TestIndicator { get; set; } + /// + /// The time the document was created. + /// [XmlAttribute("creationTime")] public DateTime CreationTime { get; set; } + /// + /// Converts this surrogate into the strongly-typed + /// . + /// public virtual IMTConnectErrorHeader ToErrorHeader() { var header = new MTConnectErrorHeader(); @@ -53,6 +91,11 @@ public virtual IMTConnectErrorHeader ToErrorHeader() return header; } + /// + /// Writes the given to + /// as a Header element, omitting the + /// test indicator when it is not set. + /// public static void WriteXml(XmlWriter writer, IMTConnectErrorHeader header) { if (header != null) diff --git a/libraries/MTConnect.NET-XML/Formatters/XmlEntityFormatter.cs b/libraries/MTConnect.NET-XML/Formatters/XmlEntityFormatter.cs index 739773a3c..b331e4bb5 100644 --- a/libraries/MTConnect.NET-XML/Formatters/XmlEntityFormatter.cs +++ b/libraries/MTConnect.NET-XML/Formatters/XmlEntityFormatter.cs @@ -15,13 +15,29 @@ namespace MTConnect.Formatters.Xml { + /// + /// that serializes and deserializes + /// individual MTConnect entities (devices, observations, and assets) to and + /// from the MTConnect XML representation. + /// public class XmlEntityFormatter : IEntityFormatter { + /// + /// The identifier this formatter is selected by; XML. + /// public string Id => "XML"; + /// + /// The MIME content type the formatter produces; + /// application/xml. + /// public string ContentType => "application/xml"; + /// + /// Serializes a single to XML, honouring the + /// indentOutput option. + /// public FormatWriteResult Format(IDevice device, IEnumerable> options = null) { if (device != null) @@ -48,6 +64,10 @@ public FormatWriteResult Format(IDevice device, IEnumerable + /// Serializes a single to XML, honouring the + /// indentOutput option. + /// public FormatWriteResult Format(IObservation observation, IEnumerable> options = null) { if (observation != null) @@ -74,6 +94,10 @@ public FormatWriteResult Format(IObservation observation, IEnumerable + /// Serializes a sequence of values to a + /// single XML stream, honouring the indentOutput option. + /// public FormatWriteResult Format(IEnumerable observations, IEnumerable> options = null) { if (!observations.IsNullOrEmpty()) @@ -103,6 +127,9 @@ public FormatWriteResult Format(IEnumerable observations, IEnumera return FormatWriteResult.Error(); } + /// + /// Serializes a single to indented XML. + /// public FormatWriteResult Format(IAsset asset, IEnumerable> options = null) { if (asset != null) @@ -115,6 +142,10 @@ public FormatWriteResult Format(IAsset asset, IEnumerable + /// Deserializes an from an XML stream, reporting + /// success when an entity was produced. + /// public FormatReadResult CreateDevice(Stream content, IEnumerable> options = null) { var messages = new List(); @@ -135,6 +166,10 @@ public FormatReadResult CreateDevice(Stream content, IEnumerable(entity, success, messages, warnings, errors); } + /// + /// Deserializes an from an XML stream, + /// reporting success when an entity was produced. + /// public FormatReadResult CreateComponent(Stream content, IEnumerable> options = null) { var messages = new List(); @@ -155,6 +190,10 @@ public FormatReadResult CreateComponent(Stream content, IEnumerable< return new FormatReadResult(entity, success, messages, warnings, errors); } + /// + /// Deserializes an from an XML stream, + /// reporting success when an entity was produced. + /// public FormatReadResult CreateComposition(Stream content, IEnumerable> options = null) { var messages = new List(); @@ -175,6 +214,10 @@ public FormatReadResult CreateComposition(Stream content, IEnumera return new FormatReadResult(entity, success, messages, warnings, errors); } + /// + /// Deserializes an from an XML stream, + /// reporting success when an entity was produced. + /// public FormatReadResult CreateDataItem(Stream content, IEnumerable> options = null) { var messages = new List(); @@ -195,6 +238,10 @@ public FormatReadResult CreateDataItem(Stream content, IEnumerable(entity, success, messages, warnings, errors); } + /// + /// Deserializes an of the named type from an XML + /// stream, reporting success when an entity was produced. + /// public FormatReadResult CreateAsset(string assetType, Stream content, IEnumerable> options = null) { var messages = new List(); diff --git a/libraries/MTConnect.NET-XML/Formatters/XmlPathFormatter.cs b/libraries/MTConnect.NET-XML/Formatters/XmlPathFormatter.cs index 7d480e617..a4950e717 100644 --- a/libraries/MTConnect.NET-XML/Formatters/XmlPathFormatter.cs +++ b/libraries/MTConnect.NET-XML/Formatters/XmlPathFormatter.cs @@ -11,11 +11,20 @@ namespace MTConnect.Formatters.Xml { + /// + /// that resolves an MTConnect path + /// request parameter against the XML representation of a device, returning + /// the ids of the data items selected by the supplied XPath expression. + /// public class XmlPathFormatter : IPathFormatter { private readonly Dictionary _documents = new Dictionary(); private readonly object _lock = new object(); + /// + /// The formatter identifier (XML) used to select this path + /// formatter for XML requests. + /// public string Id => "XML"; @@ -56,6 +65,13 @@ private byte[] GetDocumentBytes(IDevice device) return null; } + /// + /// Resolves the given XPath against the XML + /// rendering of each device in the document and returns the ids of the + /// matching data items. When a matched node is a component, the ids of + /// all of its data items are included. Unmatched or malformed + /// expressions yield an empty result. + /// public IEnumerable GetDataItemIds(IDevicesResponseDocument devicesDocument, string path) { var dataItemIds = new List(); diff --git a/libraries/MTConnect.NET-XML/Formatters/XmlResponseDocumentFormatter.cs b/libraries/MTConnect.NET-XML/Formatters/XmlResponseDocumentFormatter.cs index 045023d3b..9041654cf 100644 --- a/libraries/MTConnect.NET-XML/Formatters/XmlResponseDocumentFormatter.cs +++ b/libraries/MTConnect.NET-XML/Formatters/XmlResponseDocumentFormatter.cs @@ -19,13 +19,31 @@ namespace MTConnect.Formatters.Xml { + /// + /// that serializes and + /// deserializes whole MTConnect response documents (Devices, Streams, + /// Assets, and Error) to and from the MTConnect XML representation, with + /// optional XSD validation and stylesheet linking. + /// public class XmlResponseDocumentFormatter : IResponseDocumentFormatter { + /// + /// The identifier this formatter is selected by; XML. + /// public string Id => "XML"; + /// + /// The MIME content type the formatter produces; + /// application/xml. + /// public string ContentType => "application/xml"; + /// + /// Serializes an to XML, + /// honouring the indent, comment, stylesheet, and validation-level + /// options. + /// public FormatWriteResult Format(IDevicesResponseDocument document, IEnumerable> options = null) { // Read XSD Schema @@ -87,6 +105,11 @@ public FormatWriteResult Format(IDevicesResponseDocument document, IEnumerable + /// Serializes an to XML, + /// honouring the indent, comment, extended-namespace, stylesheet, and + /// validation-level options. + /// public FormatWriteResult Format(ref IStreamsResponseOutputDocument document, IEnumerable> options = null) { // Read XSD Schema @@ -151,6 +174,11 @@ public FormatWriteResult Format(ref IStreamsResponseOutputDocument document, IEn return FormatWriteResult.Error(); } + /// + /// Serializes an to XML, + /// honouring the indent, comment, stylesheet, and validation-level + /// options. + /// public FormatWriteResult Format(IAssetsResponseDocument document, IEnumerable> options = null) { // Read XSD Schema @@ -212,6 +240,10 @@ public FormatWriteResult Format(IAssetsResponseDocument document, IEnumerable + /// Serializes an to XML, honouring + /// the indent, comment, stylesheet, and validation-level options. + /// public FormatWriteResult Format(IErrorResponseDocument document, IEnumerable> options = null) { // Read XSD Schema @@ -273,6 +305,12 @@ public FormatWriteResult Format(IErrorResponseDocument document, IEnumerable + /// Deserializes an from an XML + /// stream, optionally validating against the supplied XSD schemas and + /// reporting validation problems as warnings or errors per the + /// validation level. + /// public FormatReadResult CreateDevicesResponseDocument(Stream content, IEnumerable> options = null) { IDevicesResponseDocument document = null; @@ -339,6 +377,12 @@ public FormatReadResult CreateDevicesResponseDocument( return new FormatReadResult(document, success, messages, warnings, errors); } + /// + /// Deserializes an from an XML + /// stream, optionally validating against the supplied XSD schemas and + /// reporting validation problems as warnings or errors per the + /// validation level. + /// public FormatReadResult CreateStreamsResponseDocument(Stream content, IEnumerable> options = null) { IStreamsResponseDocument document = null; @@ -396,10 +440,16 @@ public FormatReadResult CreateStreamsResponseDocument( innerException = innerException.InnerException; } } - + return new FormatReadResult(document, success, messages, warnings, errors); } + /// + /// Deserializes an from an XML + /// stream, optionally validating against the supplied XSD schemas and + /// reporting validation problems as warnings or errors per the + /// validation level. + /// public FormatReadResult CreateAssetsResponseDocument(Stream content, IEnumerable> options = null) { IAssetsResponseDocument document = null; @@ -413,7 +463,7 @@ public FormatReadResult CreateAssetsResponseDocument(St // Read Validation Level Option passed to Formatter (0 = Ignore, 1 = Warning, 2 = Strict) var validationLevel = GetFormatterOption(options, "validationLevel"); - + if (validationLevel > 0) { // Validate XML against XSD Schema @@ -466,6 +516,12 @@ public FormatReadResult CreateAssetsResponseDocument(St return new FormatReadResult(document, success, messages, warnings, errors); } + /// + /// Deserializes an from an XML + /// stream, optionally validating against the supplied XSD schemas and + /// reporting validation problems as warnings or errors per the + /// validation level. + /// public FormatReadResult CreateErrorResponseDocument(Stream content, IEnumerable> options = null) { IErrorResponseDocument document = null; diff --git a/libraries/MTConnect.NET-XML/Namespaces.cs b/libraries/MTConnect.NET-XML/Namespaces.cs index 4df1e6395..f2fa26786 100644 --- a/libraries/MTConnect.NET-XML/Namespaces.cs +++ b/libraries/MTConnect.NET-XML/Namespaces.cs @@ -12,9 +12,9 @@ namespace MTConnect { internal static class Namespaces - { + { internal const string DefaultXmlSchemaInstance = "http://www.w3.org/2001/XMLSchema-instance"; - + private static Regex _streamRemoveNamespaceRegex = new Regex(@"\s{1}xmlns:xsi=\""http:\/\/www\.w3\.org\/2001\/XMLSchema-instance\""\s{1}xmlns:xsd=\""http:\/\/www\.w3\.org\/2001\/XMLSchema\""", RegexOptions.Compiled); private static Regex _streamNamespaceRegex = new Regex(" extendedSchemas = null, bool outputComments = false diff --git a/libraries/MTConnect.NET-XML/Streams/XmlObservationContainer.cs b/libraries/MTConnect.NET-XML/Streams/XmlObservationContainer.cs index 1af8b3bd3..0d3f79e02 100644 --- a/libraries/MTConnect.NET-XML/Streams/XmlObservationContainer.cs +++ b/libraries/MTConnect.NET-XML/Streams/XmlObservationContainer.cs @@ -50,7 +50,7 @@ public XmlObservationContainer(IObservationOutput observation, bool outputCommen public XmlObservationContainer(IEnumerable observations, bool outputComments = false) { _outputComments = outputComments; - + if (!observations.IsNullOrEmpty()) { Observations = new List(observations.Count()); @@ -128,7 +128,7 @@ private static void WriteXml( { writer.WriteComment($"Type = {observation.DataItem.Type} : {observation.DataItem.TypeDescription}"); } - + // Write DataItem SubType Description as Comment if (!string.IsNullOrEmpty(observation.DataItem.SubType) && !string.IsNullOrEmpty(observation.DataItem.SubTypeDescription)) { @@ -276,7 +276,7 @@ private static string GetElementName(ref IObservationOutput observation) type = RemoveNamespacePrefix(type); var elementName = XmlObservation.GetDataItemType(type); - + // Add Suffix based on Representation switch (observation.Representation) { diff --git a/libraries/MTConnect.NET-XML/Streams/XmlStreamsResponseDocument.cs b/libraries/MTConnect.NET-XML/Streams/XmlStreamsResponseDocument.cs index 556f70aba..2304236aa 100644 --- a/libraries/MTConnect.NET-XML/Streams/XmlStreamsResponseDocument.cs +++ b/libraries/MTConnect.NET-XML/Streams/XmlStreamsResponseDocument.cs @@ -11,11 +11,23 @@ namespace MTConnect.Streams.Xml { + /// + /// Streaming XML reader/writer for the root MTConnectStreams + /// response document returned by the agent current and + /// sample requests. Uses an / + /// rather than the XML serializer so very large observation streams can be + /// processed without materializing the whole document. + /// public static class XmlStreamsResponseDocument { #region "Read" + /// + /// Reads a complete MTConnectStreams document, detecting the + /// schema version from the root namespace, reading the header, and + /// reading each DeviceStream in turn. + /// public static IStreamsResponseDocument ReadXml(XmlReader reader) { var document = new StreamsResponseDocument(); @@ -47,6 +59,10 @@ public static IStreamsResponseDocument ReadXml(XmlReader reader) return document; } + /// + /// Reads a single DeviceStream, capturing its name and + /// uuid and reading each contained ComponentStream. + /// public static IDeviceStream ReadDeviceStreamXml(XmlReader reader) { reader.ReadToDescendant("DeviceStream"); @@ -70,6 +86,11 @@ public static IDeviceStream ReadDeviceStreamXml(XmlReader reader) return deviceStream; } + /// + /// Reads a single ComponentStream, capturing its component + /// identification attributes and the observations grouped under its + /// Samples, Events, and Condition containers. + /// public static IComponentStream ReadComponentStreamXml(XmlReader reader) { reader.ReadToDescendant("ComponentStream"); @@ -113,6 +134,11 @@ public static IComponentStream ReadComponentStreamXml(XmlReader reader) return componentStream; } + /// + /// Reads the observations within a category container, selecting the + /// container element name (Samples, Events, or + /// Condition) from the supplied . + /// public static IEnumerable ReadObservationsXml(XmlReader reader, DataItemCategory category) { var observations = new List(); @@ -404,6 +430,11 @@ private static IEnumerable ReadTimeSeries(string text) #region "Write" + /// + /// Serializes the streams response document to a new XML stream, + /// choosing indented or compact writer settings and optionally emitting + /// a stylesheet, header comment, and extended schema namespaces. + /// public static Stream ToXmlStream( ref IStreamsResponseOutputDocument document, IEnumerable extendedSchemas = null, @@ -432,6 +463,12 @@ public static Stream ToXmlStream( return null; } + /// + /// Writes the complete MTConnectStreams document, emitting the + /// version-specific namespace, optional extended schema namespaces and + /// schema location, the header, and each device stream. No document is + /// written when the response has no streams. + /// public static void WriteXml( XmlWriter writer, ref IStreamsResponseOutputDocument document, diff --git a/libraries/MTConnect.NET-XML/XmlFunctions.cs b/libraries/MTConnect.NET-XML/XmlFunctions.cs index 3842283fc..f960803f4 100644 --- a/libraries/MTConnect.NET-XML/XmlFunctions.cs +++ b/libraries/MTConnect.NET-XML/XmlFunctions.cs @@ -12,11 +12,31 @@ namespace MTConnect { + /// + /// Helper routines shared by the MTConnect XML writers, covering the + /// standard writer settings, timestamp formatting, byte-stream + /// sanitization, pretty-printing, and the provenance header comment. + /// public static class XmlFunctions { + /// + /// The XML declaration prepended to MTConnect documents. + /// public const string XmlDeclaration = ""; + + /// + /// The newline string used when indenting output. + /// public const string NewLine = "\n"; + + /// + /// The newline character used when indenting output. + /// public const char NewLineCharacter = '\n'; + + /// + /// The string used for a single level of indentation. + /// public const string Tab = " "; @@ -38,15 +58,31 @@ public static class XmlFunctions }; + /// + /// The shared writer settings that emit compact, non-indented UTF-8 + /// XML. + /// public static XmlWriterSettings XmlWriterSettings => _xmlWriterSettings; + + /// + /// The shared writer settings that emit indented UTF-8 XML. + /// public static XmlWriterSettings XmlWriterSettingsIndent => _xmlWriterSettingsIndent; + /// + /// Formats the given as an ISO 8601 round-trip + /// timestamp. + /// public static string GetTimestamp(DateTime timestamp) { return timestamp.ToString("o"); } + /// + /// Formats the given as an ISO 8601 + /// round-trip timestamp, normalizing zero-offset values to UTC. + /// public static string GetTimestamp(DateTimeOffset timestamp) { if (timestamp.Offset != TimeSpan.Zero) @@ -59,6 +95,11 @@ public static string GetTimestamp(DateTimeOffset timestamp) } } + /// + /// Returns a copy of the given bytes with any leading or trailing + /// whitespace and a UTF-8 byte-order mark stripped, so the result + /// parses cleanly as an XML document. + /// public static byte[] SanitizeBytes(byte[] inputBytes) { if (inputBytes != null) @@ -116,6 +157,11 @@ public static byte[] SanitizeBytes(byte[] inputBytes) return null; } + /// + /// Re-serializes the given XML string with optional indentation, + /// comment preservation, and declaration omission, returning the + /// original input unchanged if it cannot be parsed. + /// public static string FormatXml(string xml, bool indent = true, bool outputComments = false, bool omitXmlDeclaration = false) { try @@ -152,6 +198,11 @@ public static string FormatXml(string xml, bool indent = true, bool outputCommen return xml; } + /// + /// Builds the multi-line provenance comment, naming the producing + /// agent application and the MTConnect.NET library, as a string of + /// concatenated XML comment nodes. + /// public static string CreateHeaderComment() { var assembly = Assembly.GetEntryAssembly(); @@ -212,6 +263,11 @@ public static string CreateHeaderComment() return headerXml; } + /// + /// Writes the multi-line provenance comment directly to + /// , optionally inserting newlines between + /// comment nodes when is set. + /// public static void WriteHeaderComment(XmlWriter writer, bool indentOutput) { var assembly = Assembly.GetEntryAssembly(); diff --git a/tests/IntegrationTests/IntegrationTests.csproj b/tests/IntegrationTests/IntegrationTests.csproj new file mode 100644 index 000000000..12ce73f2a --- /dev/null +++ b/tests/IntegrationTests/IntegrationTests.csproj @@ -0,0 +1,44 @@ + + + + net8.0 + + false + enable + + + + + + + + + + + + + + + + + + + + + + runtime; build; native; contentfiles; analyzers; buildtransitive + all + + + runtime; build; native; contentfiles; analyzers; buildtransitive + all + + + + + + + + + + diff --git a/tests/MTConnect.NET-Common-Tests/Headers/HeaderVersionRegressionTests.cs b/tests/MTConnect.NET-Common-Tests/Headers/HeaderVersionRegressionTests.cs index 0b3bf0f0b..9de5ac6ed 100644 --- a/tests/MTConnect.NET-Common-Tests/Headers/HeaderVersionRegressionTests.cs +++ b/tests/MTConnect.NET-Common-Tests/Headers/HeaderVersionRegressionTests.cs @@ -5,8 +5,8 @@ // not the library assembly version. // // Spec sources: -// - https://docs.mtconnect.org/ Part 1.0 §3 (Header), Part 2.0 §7 -// (Streams envelope), Part 3.0 §5 (Devices envelope), Part 4.0 §5 +// - https://docs.mtconnect.org/ Part 1.0 section 3 (Header), Part 2.0 section 7 +// (Streams envelope), Part 3.0 section 5 (Devices envelope), Part 4.0 section 5 // (Assets envelope) — Header.version is the MTConnect Standard // release the agent serves. // - XSD: MTConnectDevices_.xsd, MTConnectStreams_.xsd, diff --git a/tests/MTConnect.NET-Common-Tests/MTConnect.NET-Common-Tests.csproj b/tests/MTConnect.NET-Common-Tests/MTConnect.NET-Common-Tests.csproj index e8abcf4f4..e06ed7bd0 100644 --- a/tests/MTConnect.NET-Common-Tests/MTConnect.NET-Common-Tests.csproj +++ b/tests/MTConnect.NET-Common-Tests/MTConnect.NET-Common-Tests.csproj @@ -9,10 +9,10 @@ - - - - + + + + diff --git a/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/MTConnectVersionsTests.cs b/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/MTConnectVersionsTests.cs index a93cfca34..5167bb337 100644 --- a/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/MTConnectVersionsTests.cs +++ b/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/MTConnectVersionsTests.cs @@ -14,7 +14,7 @@ namespace MTConnect.NET_Common_Tests.V2_6_V2_7 // - XSD: https://schemas.mtconnect.org/schemas/MTConnectDevices_2.6.xsd // MTConnectDevices_2.7.xsd // (each XSD's targetNamespace embeds the version it represents.) - // - Prose: MTConnect Standard `Part_1.0_Overview_v2.7.pdf` §1 "Versioning" + // - Prose: MTConnect Standard `Part_1.0_Overview_v2.7.pdf` section 1 "Versioning" // (the document numbering scheme — v1.0 through v2.7 with v1.9 // intentionally skipped — is described here.) [TestFixture] @@ -44,7 +44,7 @@ public void Max_equals_Version27() } // Pin that the version list contains no 1.9 entry. - // Source: MTConnect Standard Part_1.0_Overview prose §1 "Versioning"; + // Source: MTConnect Standard Part_1.0_Overview prose section 1 "Versioning"; // confirmed by the absence of an XMI tag `v1.9` in // `mtconnect/mtconnect_sysml_model` (tags: v2.5 b61907fb78, // v2.6 08185447bf, v2.7 25796ac591). diff --git a/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_6ComponentAndEnumTests.cs b/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_6ComponentAndEnumTests.cs index 48b178986..240b50f0b 100644 --- a/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_6ComponentAndEnumTests.cs +++ b/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_6ComponentAndEnumTests.cs @@ -15,8 +15,8 @@ namespace MTConnect.NET_Common_Tests.V2_6_V2_7 // - XSD: schemas.mtconnect.org/schemas/MTConnectDevices_2.6.xsd // (Component element list + MediaType simpleType enumeration) // - Prose: MTConnect Standard Part_3.0_Devices_v2.6 - // §3.4.18 "CuttingTorch" / §3.4.21 "Electrode" - // §4.7.2.5 MediaType (introduces QIF_MBD) + // section 3.4.18 "CuttingTorch" / section 3.4.21 "Electrode" + // section 4.7.2.5 MediaType (introduces QIF_MBD) [TestFixture] public class V2_6ComponentAndEnumTests { @@ -46,7 +46,7 @@ public void ElectrodeComponent_constructs_with_correct_type() // Source: XMI v2.6 enum `MediaTypeEnum` member `QIF_MBD`. XSD v2.6 lists // QIF_MBD inside the MediaType simpleType enumeration. Prose - // Part_3.0_Devices_v2.6 §4.7.2.5 introduces "ISO 10303 QIF model-based + // Part_3.0_Devices_v2.6 section 4.7.2.5 introduces "ISO 10303 QIF model-based // design" as the rationale. [Test] public void MediaType_QIF_MBD_value_present_in_v2_6() diff --git a/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_6DataItemTypeTests.cs b/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_6DataItemTypeTests.cs index 7bbe08031..7486c0d12 100644 --- a/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_6DataItemTypeTests.cs +++ b/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_6DataItemTypeTests.cs @@ -15,7 +15,7 @@ namespace MTConnect.NET_Common_Tests.V2_6_V2_7 // - XSD: schemas.mtconnect.org/schemas/MTConnectStreams_2.6.xsd // (the EVENT category for both new types is encoded in the // MTConnectStreams XSD's enumerations.) - // - Prose: MTConnect Standard Part_2.0_Streams_v2.6 §11.5 "Asset events" + // - Prose: MTConnect Standard Part_2.0_Streams_v2.6 section 11.5 "Asset events" // (clarifies the v2.5 → v2.6 split — `AssetChanged` narrowed to // changes only; `AssetAdded` introduced for additions.) [TestFixture] @@ -74,7 +74,7 @@ public void AssociatedAssetIdDataItem_inherits_from_DataItem() // Source: XMI v2.6 description on `AssetChangedDataItem` (was "added or // changed" in v2.5; now "changed" only). Prose confirms in - // Part_2.0_Streams_v2.6 §11.5. + // Part_2.0_Streams_v2.6 section 11.5. [Test] public void AssetChangedDataItem_description_narrowed_in_v2_6() { diff --git a/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_7ComponentTests.cs b/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_7ComponentTests.cs index 0e67a21b4..9f27b53bd 100644 --- a/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_7ComponentTests.cs +++ b/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_7ComponentTests.cs @@ -11,7 +11,7 @@ namespace MTConnect.NET_Common_Tests.V2_6_V2_7 // * ToolHolder — tool-holder component // - XSD: https://schemas.mtconnect.org/schemas/MTConnectDevices_2.7.xsd // (each TypeId appears in the ComponentType enumeration). - // - Prose: MTConnect Standard Part_2.0_Devices_v2.7 §7 "Component + // - Prose: MTConnect Standard Part_2.0_Devices_v2.7 section 7 "Component // types" — describes intended use of each Component subclass. [TestFixture] public class V2_7ComponentTests diff --git a/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_7ConfigurationDataSetTests.cs b/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_7ConfigurationDataSetTests.cs index 80a473b60..2d6cbbe73 100644 --- a/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_7ConfigurationDataSetTests.cs +++ b/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_7ConfigurationDataSetTests.cs @@ -20,7 +20,7 @@ namespace MTConnect.NET_Common_Tests.V2_6_V2_7 // - XSD: https://schemas.mtconnect.org/schemas/MTConnectDevices_2.7.xsd // (the geometric-primitive complexTypes encode the same shape // on the wire under ). - // - Prose: MTConnect Standard Part_2.0_Devices_v2.7 §10 "Configuration" + // - Prose: MTConnect Standard Part_2.0_Devices_v2.7 section 10 "Configuration" // — describes how Component-level Configuration carries the // geometric primitives that locate a Component in space. [TestFixture] diff --git a/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_7DataItemTypeTests.cs b/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_7DataItemTypeTests.cs index ee74985b2..08f9ba794 100644 --- a/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_7DataItemTypeTests.cs +++ b/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_7DataItemTypeTests.cs @@ -20,7 +20,7 @@ namespace MTConnect.NET_Common_Tests.V2_6_V2_7 // - XSD: schemas.mtconnect.org/schemas/MTConnectStreams_2.7.xsd // (each TypeId is encoded in the EventEnum / SampleEnum // enumerations.) - // - Prose: MTConnect Standard Part_2.0_Streams_v2.7 §11/§13 "Event/Sample + // - Prose: MTConnect Standard Part_2.0_Streams_v2.7 section 11/section 13 "Event/Sample // types" — describes intended use of each type. [TestFixture] public class V2_7DataItemTypeTests diff --git a/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_7SampleObservationTests.cs b/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_7SampleObservationTests.cs index 4b291aeb0..bc44576a8 100644 --- a/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_7SampleObservationTests.cs +++ b/tests/MTConnect.NET-Common-Tests/V2_6_V2_7/V2_7SampleObservationTests.cs @@ -16,7 +16,7 @@ namespace MTConnect.NET_Common_Tests.V2_6_V2_7 // - XSD: schemas.mtconnect.org/schemas/MTConnectStreams_2.7.xsd // enum `SampleEnum` value `WATER_HARDNESS` is the sample-category // element name on the wire. - // - Prose: MTConnect Standard Part_2.0_Streams_v2.7 §11 "Sample observation + // - Prose: MTConnect Standard Part_2.0_Streams_v2.7 section 11 "Sample observation // types" — describes how SAMPLE-category observations carry // continuous-numeric values reported at agent-defined intervals. // diff --git a/tests/MTConnect.NET-Docs-Tests/DocsReferenceGenerationTests.cs b/tests/MTConnect.NET-Docs-Tests/DocsReferenceGenerationTests.cs new file mode 100644 index 000000000..9076fc030 --- /dev/null +++ b/tests/MTConnect.NET-Docs-Tests/DocsReferenceGenerationTests.cs @@ -0,0 +1,161 @@ +// Copyright (c) 2026 TrakHound Inc., All Rights Reserved. +// TrakHound Inc. licenses this file to you under the MIT license. + +using System; +using System.IO; +using System.Linq; +using MTConnect.NET_DocsGen; +using NUnit.Framework; + +namespace MTConnect.NET_Docs_Tests; + +/// +/// Validates that the auto-generated reference pages under +/// `docs/reference/` are in lock-step with what the same Roslyn +/// inventories produce when re-run inside the test process. Adding +/// a new HTTP endpoint, environment-variable read, or configuration +/// property without regenerating the reference fails this fixture +/// and therefore CI. +/// +/// Run locally: +/// +/// dotnet test tests/MTConnect.NET-Docs-Tests +/// +/// Regenerate the reference pages: +/// +/// dotnet run --project build/MTConnect.NET-DocsGen -- --repo . +/// +[TestFixture] +public class DocsReferenceGenerationTests +{ + private static string RepoRoot + { + get + { + // bin/Debug/net8.0/ -> three levels up to test project, + // then one more to `tests/`, then one more to repo root. + // Strip the trailing path separator first so + // GetDirectoryName actually ascends each call. + var dir = AppContext.BaseDirectory.TrimEnd(Path.DirectorySeparatorChar, Path.AltDirectorySeparatorChar); + for (int i = 0; i < 10 && !string.IsNullOrEmpty(dir); i++) + { + if (File.Exists(Path.Combine(dir, "MTConnect.NET.sln"))) return dir; + dir = Path.GetDirectoryName(dir); + } + throw new InvalidOperationException("Could not locate repository root from " + AppContext.BaseDirectory); + } + } + + [Test] + public void HttpApi_Page_Is_In_Sync_With_Source() + { + var endpoints = RouteInventory.Collect(RepoRoot); + Assert.That(endpoints.Count, Is.GreaterThan(0), "expected at least one HTTP route"); + + var expected = HttpApiRenderer.Render(endpoints); + var path = Path.Combine(RepoRoot, "docs", "reference", "http-api.md"); + Assert.That(File.Exists(path), Is.True, $"missing {path}"); + var actual = File.ReadAllText(path); + + if (!string.Equals(actual, expected, StringComparison.Ordinal)) + { + Assert.Fail($"docs/reference/http-api.md is out of sync with the source. Regenerate with:\n dotnet run --project build/MTConnect.NET-DocsGen -- --repo ."); + } + } + + [Test] + public void EnvironmentVariables_Page_Is_In_Sync_With_Source() + { + var vars = EnvVarInventory.Collect(RepoRoot); + + var expected = EnvVarRenderer.Render(vars); + var path = Path.Combine(RepoRoot, "docs", "reference", "environment-variables.md"); + Assert.That(File.Exists(path), Is.True, $"missing {path}"); + var actual = File.ReadAllText(path); + + if (!string.Equals(actual, expected, StringComparison.Ordinal)) + { + Assert.Fail("docs/reference/environment-variables.md is out of sync with the source. Regenerate with:\n dotnet run --project build/MTConnect.NET-DocsGen -- --repo ."); + } + } + + [Test] + public void Configuration_Page_Is_In_Sync_With_Source() + { + var classes = ConfigInventory.Collect(RepoRoot); + Assert.That(classes.Count, Is.GreaterThan(0), "expected at least one configuration option class"); + + var expected = ConfigRenderer.Render(classes); + var path = Path.Combine(RepoRoot, "docs", "reference", "configuration.md"); + Assert.That(File.Exists(path), Is.True, $"missing {path}"); + var actual = File.ReadAllText(path); + + if (!string.Equals(actual, expected, StringComparison.Ordinal)) + { + Assert.Fail("docs/reference/configuration.md is out of sync with the source. Regenerate with:\n dotnet run --project build/MTConnect.NET-DocsGen -- --repo ."); + } + } + + [Test] + public void Cli_Page_Is_In_Sync_With_Source() + { + var clis = CliInventory.Collect(RepoRoot); + Assert.That(clis.Count, Is.GreaterThan(0), "expected at least one CLI tool"); + // Shipped agent + adapter must both be present; if either goes + // missing the inventory has regressed and the page would lose + // critical surface coverage. + Assert.That(clis.Any(c => c.Name == "mtconnect.net-agent"), Is.True, + "mtconnect.net-agent should be discovered as a shipped CLI"); + Assert.That(clis.Any(c => c.Name == "mtconnect.net-adapter"), Is.True, + "mtconnect.net-adapter should be discovered as a shipped CLI"); + + var expected = CliRenderer.Render(clis); + var path = Path.Combine(RepoRoot, "docs", "reference", "cli.md"); + Assert.That(File.Exists(path), Is.True, $"missing {path}"); + var actual = File.ReadAllText(path); + + if (!string.Equals(actual, expected, StringComparison.Ordinal)) + { + Assert.Fail("docs/reference/cli.md is out of sync with the source. Regenerate with:\n dotnet run --project build/MTConnect.NET-DocsGen -- --repo ."); + } + } + + [Test] + public void Endpoint_Code_Has_No_Stale_Entries_In_Markdown() + { + // Inverse check: every fenced `GET /path` heading in the + // markdown must be backed by a row in the freshly collected + // inventory. Catches the case where a route is removed in + // source but the markdown still references it. + var endpoints = RouteInventory.Collect(RepoRoot); + var liveKeys = endpoints + .Select(e => $"{e.Method} {e.PathTemplate} — {e.Source}") + .ToHashSet(); + + var path = Path.Combine(RepoRoot, "docs", "reference", "http-api.md"); + var lines = File.ReadAllLines(path); + foreach (var line in lines) + { + // Look for "### `GET /probe` — Ceen" + if (!line.StartsWith("### `", StringComparison.Ordinal)) continue; + var endTick = line.IndexOf('`', 5); + if (endTick < 0) continue; + var verbPath = line.Substring(5, endTick - 5); + var mdashIdx = line.IndexOf("—", StringComparison.Ordinal); + if (mdashIdx < 0) continue; + var source = line.Substring(mdashIdx + "—".Length).Trim(); + var docKey = $"{verbPath} — {source}"; + Assert.That(liveKeys, Does.Contain(docKey), + $"docs lists endpoint that no longer exists in source: {docKey}"); + } + } + + [Test] + public void Index_Page_Is_In_Sync() + { + var expected = IndexRenderer.Render(); + var path = Path.Combine(RepoRoot, "docs", "reference", "index.md"); + Assert.That(File.Exists(path), Is.True, $"missing {path}"); + Assert.That(File.ReadAllText(path), Is.EqualTo(expected)); + } +} diff --git a/tests/MTConnect.NET-Docs-Tests/MTConnect.NET-Docs-Tests.csproj b/tests/MTConnect.NET-Docs-Tests/MTConnect.NET-Docs-Tests.csproj new file mode 100644 index 000000000..7da64b04e --- /dev/null +++ b/tests/MTConnect.NET-Docs-Tests/MTConnect.NET-Docs-Tests.csproj @@ -0,0 +1,22 @@ + + + + net8.0 + MTConnect.NET_Docs_Tests + enable + + false + + + + + + + + + + + + + + diff --git a/tests/MTConnect.NET-HTTP-Tests/MTConnect.NET-HTTP-Tests.csproj b/tests/MTConnect.NET-HTTP-Tests/MTConnect.NET-HTTP-Tests.csproj index 6a921a727..ee1b75fe7 100644 --- a/tests/MTConnect.NET-HTTP-Tests/MTConnect.NET-HTTP-Tests.csproj +++ b/tests/MTConnect.NET-HTTP-Tests/MTConnect.NET-HTTP-Tests.csproj @@ -9,15 +9,14 @@ - - - - + + + + - diff --git a/tests/MTConnect.NET-JSON-cppagent-Tests/Streams/JsonConditionsArrayShapeTests.cs b/tests/MTConnect.NET-JSON-cppagent-Tests/Streams/JsonConditionsArrayShapeTests.cs new file mode 100644 index 000000000..5c982d9fd --- /dev/null +++ b/tests/MTConnect.NET-JSON-cppagent-Tests/Streams/JsonConditionsArrayShapeTests.cs @@ -0,0 +1,382 @@ +// Copyright (c) 2023 TrakHound Inc., All Rights Reserved. +// TrakHound Inc. licenses this file to you under the MIT license. + +using MTConnect.Streams.Json; +using NUnit.Framework; +using System.Collections.Generic; +using System.Text.Json; + +namespace MTConnect.NET_JSON_cppagent_Tests.Streams +{ + // Pins the cppagent JSON v2 array-of-wrappers wire shape for + // ConditionListType. The XSD declares ConditionListType as + // + // of Normal|Warning|Fault|Unavailable; cppagent v2 emits one + // single-key wrapper object per entry. + // + // Ordering: the typed JsonConditions POCO buckets entries by level + // (Fault, Warning, Normal, Unavailable). The converter emits in + // that fixed level order, with source order preserved within each + // bucket. Mixed-level interleaving on the wire is therefore NOT + // round-trip preserved through the typed model — see the + // Read_ArrayShape_MixedLevelInterleaving_BucketsByLevel test for + // the explicit pin. + // + // Sources: + // - XSD: https://schemas.mtconnect.org/schemas/MTConnectStreams_2.7.xsd + // (complex type ConditionListType). + // - Prose: MTConnect Standard Part 2 section 13 "Condition". + // - cppagent reference (v2.7.0.7): printer/json_printer.cpp + // function print_condition. + [TestFixture] + public class JsonConditionsArrayShapeTests + { + private static JsonCondition MakeEntry(string dataItemId, string type) + { + return new JsonCondition + { + DataItemId = dataItemId, + Type = type, + }; + } + + private static JsonSerializerOptions Options() => new JsonSerializerOptions(); + + private static string FirstPropertyName(JsonElement element) + { + using var enumerator = element.EnumerateObject(); + enumerator.MoveNext(); + return enumerator.Current.Name; + } + + // Case 1 — empty conditions serialize as the array shape, not an object shape. + [Test] + public void Write_EmptyConditions_EmitsEmptyArray() + { + var conditions = new JsonConditions(); + + var json = JsonSerializer.Serialize(conditions, Options()); + + Assert.That(json, Is.EqualTo("[]")); + } + + // Case 2 — one Normal entry produces a 1-element array with a Normal wrapper. + [Test] + public void Write_SingleNormal_EmitsOneNormalWrapper() + { + var conditions = new JsonConditions + { + Normal = new List { MakeEntry("n1", "TEMPERATURE") }, + }; + + var json = JsonSerializer.Serialize(conditions, Options()); + + using var doc = JsonDocument.Parse(json); + var root = doc.RootElement; + Assert.That(root.ValueKind, Is.EqualTo(JsonValueKind.Array)); + Assert.That(root.GetArrayLength(), Is.EqualTo(1)); + + var wrapper = root[0]; + Assert.That(wrapper.ValueKind, Is.EqualTo(JsonValueKind.Object)); + Assert.That(wrapper.TryGetProperty("Normal", out var entry), Is.True); + Assert.That(entry.GetProperty("dataItemId").GetString(), Is.EqualTo("n1")); + } + + // Case 3 — Fault + Warning emit in Fault, Warning order per the converter. + [Test] + public void Write_FaultThenWarning_EmitsInDeclaredEnumerationOrder() + { + var conditions = new JsonConditions + { + Fault = new List { MakeEntry("f1", "TEMPERATURE") }, + Warning = new List { MakeEntry("w1", "POSITION") }, + }; + + var json = JsonSerializer.Serialize(conditions, Options()); + + using var doc = JsonDocument.Parse(json); + var root = doc.RootElement; + Assert.That(root.GetArrayLength(), Is.EqualTo(2)); + + Assert.That(FirstPropertyName(root[0]), Is.EqualTo("Fault")); + Assert.That(FirstPropertyName(root[1]), Is.EqualTo("Warning")); + } + + // Case 4 — all four levels populated emit in Fault, Warning, Normal, Unavailable order. + [Test] + public void Write_AllFourLevels_EmitsInFaultWarningNormalUnavailableOrder() + { + var conditions = new JsonConditions + { + Fault = new List { MakeEntry("f1", "TEMPERATURE") }, + Warning = new List { MakeEntry("w1", "POSITION") }, + Normal = new List { MakeEntry("n1", "AVAILABILITY") }, + Unavailable = new List { MakeEntry("u1", "ROTATION") }, + }; + + var json = JsonSerializer.Serialize(conditions, Options()); + + using var doc = JsonDocument.Parse(json); + var root = doc.RootElement; + Assert.That(root.GetArrayLength(), Is.EqualTo(4)); + + var keys = new List(); + for (var i = 0; i < root.GetArrayLength(); i++) + { + foreach (var prop in root[i].EnumerateObject()) + { + keys.Add(prop.Name); + } + } + + Assert.That(keys, Is.EqualTo(new[] { "Fault", "Warning", "Normal", "Unavailable" })); + } + + // Case 5 — multiple entries on one level produce one wrapper each in source order. + [Test] + public void Write_MultipleFaults_EmitsOneWrapperPerEntry() + { + var conditions = new JsonConditions + { + Fault = new List + { + MakeEntry("f1", "TEMPERATURE"), + MakeEntry("f2", "POSITION"), + MakeEntry("f3", "AVAILABILITY"), + }, + }; + + var json = JsonSerializer.Serialize(conditions, Options()); + + using var doc = JsonDocument.Parse(json); + var root = doc.RootElement; + Assert.That(root.GetArrayLength(), Is.EqualTo(3)); + + var ids = new List(); + foreach (var element in root.EnumerateArray()) + { + Assert.That(element.TryGetProperty("Fault", out var entry), Is.True); + ids.Add(entry.GetProperty("dataItemId").GetString()!); + } + + Assert.That(ids, Is.EqualTo(new[] { "f1", "f2", "f3" })); + } + + // Case 5b — mixed-level interleaving on the input wire is bucketed + // by level on read and re-emitted in level order (Fault, Warning, + // Normal, Unavailable) on write. Pins the documented non-byte- + // identical round-trip for interleaved input — see the type + // comment on JsonConditionsConverter for the design rationale. + [Test] + public void Read_ArrayShape_MixedLevelInterleaving_BucketsByLevel() + { + const string interleaved = + "[{\"Fault\":{\"dataItemId\":\"f1\"}}," + + "{\"Normal\":{\"dataItemId\":\"n1\"}}," + + "{\"Fault\":{\"dataItemId\":\"f2\"}}]"; + + var parsed = JsonSerializer.Deserialize(interleaved, Options()); + + Assert.That(parsed, Is.Not.Null); + Assert.That(parsed!.Fault, Is.Not.Null); + Assert.That(parsed.Normal, Is.Not.Null); + Assert.That(parsed.Warning, Is.Null); + Assert.That(parsed.Unavailable, Is.Null); + + var faultIds = new List(); + foreach (var entry in parsed.Fault!) faultIds.Add(entry.DataItemId); + Assert.That(faultIds, Is.EqualTo(new[] { "f1", "f2" })); + + var normalIds = new List(); + foreach (var entry in parsed.Normal!) normalIds.Add(entry.DataItemId); + Assert.That(normalIds, Is.EqualTo(new[] { "n1" })); + + var rewritten = JsonSerializer.Serialize(parsed, Options()); + using var rewrittenDoc = JsonDocument.Parse(rewritten); + var rewrittenRoot = rewrittenDoc.RootElement; + Assert.That(rewrittenRoot.ValueKind, Is.EqualTo(JsonValueKind.Array)); + Assert.That(rewrittenRoot.GetArrayLength(), Is.EqualTo(3)); + + var rewrittenKeys = new List(); + var rewrittenDataItemIds = new List(); + for (var i = 0; i < rewrittenRoot.GetArrayLength(); i++) + { + foreach (var prop in rewrittenRoot[i].EnumerateObject()) + { + rewrittenKeys.Add(prop.Name); + rewrittenDataItemIds.Add(prop.Value.GetProperty("dataItemId").GetString()!); + } + } + + Assert.That(rewrittenKeys, Is.EqualTo(new[] { "Fault", "Fault", "Normal" })); + Assert.That(rewrittenDataItemIds, Is.EqualTo(new[] { "f1", "f2", "n1" })); + } + + // Case 6 — array JSON round-trips through Deserialize/Serialize without drift. + [Test] + public void RoundTrip_ArrayShape_IsByteIdenticalModuloWhitespace() + { + var original = new JsonConditions + { + Fault = new List { MakeEntry("f1", "TEMPERATURE") }, + Warning = new List { MakeEntry("w1", "POSITION") }, + Normal = new List { MakeEntry("n1", "AVAILABILITY") }, + Unavailable = new List { MakeEntry("u1", "ROTATION") }, + }; + + var json = JsonSerializer.Serialize(original, Options()); + var parsed = JsonSerializer.Deserialize(json, Options()); + var json2 = JsonSerializer.Serialize(parsed, Options()); + + Assert.That(json2, Is.EqualTo(json)); + } + + // Case 7 — legacy MTConnect JSON v1 object-keyed shape parses into the typed POCO. + [Test] + public void Read_LegacyObjectShape_PopulatesTypedProperties() + { + const string legacy = + "{\"Normal\":[{\"dataItemId\":\"n1\",\"type\":\"TEMPERATURE\"}]," + + "\"Fault\":[{\"dataItemId\":\"f1\",\"type\":\"POSITION\"}]}"; + + var parsed = JsonSerializer.Deserialize(legacy, Options()); + + Assert.That(parsed, Is.Not.Null); + Assert.That(parsed!.Normal, Is.Not.Null); + Assert.That(parsed.Fault, Is.Not.Null); + + using var normalEnumerator = parsed.Normal!.GetEnumerator(); + Assert.That(normalEnumerator.MoveNext(), Is.True); + Assert.That(normalEnumerator.Current.DataItemId, Is.EqualTo("n1")); + + using var faultEnumerator = parsed.Fault!.GetEnumerator(); + Assert.That(faultEnumerator.MoveNext(), Is.True); + Assert.That(faultEnumerator.Current.DataItemId, Is.EqualTo("f1")); + } + + // Case 8 — null write emits "null" and round-trips back to a null reference. + [Test] + public void Null_WriteAndRead_RoundTripsToNull() + { + var json = JsonSerializer.Serialize(null!, Options()); + Assert.That(json, Is.EqualTo("null")); + + var parsed = JsonSerializer.Deserialize("null", Options()); + Assert.That(parsed, Is.Null); + } + + // Case 9 — invalid root token (number) raises JsonException with a recognisable message. + [Test] + public void Read_InvalidRootToken_ThrowsJsonException() + { + var ex = Assert.Throws(() => + JsonSerializer.Deserialize("123", Options())); + Assert.That(ex, Is.Not.Null); + Assert.That(ex!.Message, Does.Contain("Unexpected token")); + } + + // Coverage filler — the array-shape read path also handles all four levels + // and rejects unknown level names + malformed wrapper objects. + [Test] + public void Read_ArrayShape_PopulatesAllFourLevels() + { + const string json = + "[{\"Fault\":{\"dataItemId\":\"f1\"}}," + + "{\"Warning\":{\"dataItemId\":\"w1\"}}," + + "{\"Normal\":{\"dataItemId\":\"n1\"}}," + + "{\"Unavailable\":{\"dataItemId\":\"u1\"}}]"; + + var parsed = JsonSerializer.Deserialize(json, Options()); + + Assert.That(parsed, Is.Not.Null); + Assert.That(parsed!.Fault, Is.Not.Null); + Assert.That(parsed.Warning, Is.Not.Null); + Assert.That(parsed.Normal, Is.Not.Null); + Assert.That(parsed.Unavailable, Is.Not.Null); + } + + [Test] + public void Read_ArrayShape_UnknownLevel_ThrowsJsonException() + { + const string json = "[{\"Bogus\":{\"dataItemId\":\"x1\"}}]"; + + var ex = Assert.Throws(() => + JsonSerializer.Deserialize(json, Options())); + Assert.That(ex, Is.Not.Null); + Assert.That(ex!.Message, Does.Contain("Unknown Condition level")); + } + + [Test] + public void Read_ArrayShape_NonObjectElement_ThrowsJsonException() + { + const string json = "[42]"; + + var ex = Assert.Throws(() => + JsonSerializer.Deserialize(json, Options())); + Assert.That(ex, Is.Not.Null); + Assert.That(ex!.Message, Does.Contain("expected object wrapper")); + } + + [Test] + public void Read_ArrayShape_WrapperWithoutPropertyName_ThrowsJsonException() + { + const string json = "[{}]"; + + var ex = Assert.Throws(() => + JsonSerializer.Deserialize(json, Options())); + Assert.That(ex, Is.Not.Null); + Assert.That(ex!.Message, Does.Contain("Expected property name")); + } + + [Test] + public void Read_ArrayShape_WrapperWithMultipleProperties_ThrowsJsonException() + { + const string json = "[{\"Fault\":{\"dataItemId\":\"f1\"},\"Warning\":{\"dataItemId\":\"w1\"}}]"; + + var ex = Assert.Throws(() => + JsonSerializer.Deserialize(json, Options())); + Assert.That(ex, Is.Not.Null); + Assert.That(ex!.Message, Does.Contain("end of JsonConditions wrapper")); + } + + [Test] + public void Read_ArrayShape_NullEntry_ThrowsJsonException() + { + const string json = "[{\"Normal\":null}]"; + + var ex = Assert.Throws(() => + JsonSerializer.Deserialize(json, Options())); + Assert.That(ex, Is.Not.Null); + Assert.That(ex!.Message, Does.Contain("Null Condition entry")); + } + + [Test] + public void Read_ObjectShape_UnknownLevel_ThrowsJsonException() + { + const string json = "{\"Bogus\":[{\"dataItemId\":\"x1\"}]}"; + + var ex = Assert.Throws(() => + JsonSerializer.Deserialize(json, Options())); + Assert.That(ex, Is.Not.Null); + Assert.That(ex!.Message, Does.Contain("Unknown Condition level")); + } + + [Test] + public void Read_ObjectShape_PopulatesAllFourLevels() + { + const string json = + "{\"Fault\":[{\"dataItemId\":\"f1\"}]," + + "\"Warning\":[{\"dataItemId\":\"w1\"}]," + + "\"Normal\":[{\"dataItemId\":\"n1\"}]," + + "\"Unavailable\":[{\"dataItemId\":\"u1\"}]}"; + + var parsed = JsonSerializer.Deserialize(json, Options()); + + Assert.That(parsed, Is.Not.Null); + Assert.That(parsed!.Fault, Is.Not.Null); + Assert.That(parsed.Warning, Is.Not.Null); + Assert.That(parsed.Normal, Is.Not.Null); + Assert.That(parsed.Unavailable, Is.Not.Null); + } + } +} diff --git a/tests/MTConnect.NET-SHDR-Tests/MTConnect.NET-SHDR-Tests.csproj b/tests/MTConnect.NET-SHDR-Tests/MTConnect.NET-SHDR-Tests.csproj index e4e1eae80..05c68a35e 100644 --- a/tests/MTConnect.NET-SHDR-Tests/MTConnect.NET-SHDR-Tests.csproj +++ b/tests/MTConnect.NET-SHDR-Tests/MTConnect.NET-SHDR-Tests.csproj @@ -7,10 +7,10 @@ - - - - + + + + all runtime; build; native; contentfiles; analyzers; buildtransitive diff --git a/tests/MTConnect.NET-XML-Tests/Headers/HeaderVersionXmlRoundTripTests.cs b/tests/MTConnect.NET-XML-Tests/Headers/HeaderVersionXmlRoundTripTests.cs index aa4f8cbc4..683fc8256 100644 --- a/tests/MTConnect.NET-XML-Tests/Headers/HeaderVersionXmlRoundTripTests.cs +++ b/tests/MTConnect.NET-XML-Tests/Headers/HeaderVersionXmlRoundTripTests.cs @@ -8,7 +8,7 @@ // of the agent's DefaultVersion. // // Spec sources: -// - https://docs.mtconnect.org/ Part 1.0 §3 (Header) — defines the +// - https://docs.mtconnect.org/ Part 1.0 section 3 (Header) — defines the // `version` attribute on the Header element as the MTConnect // release the agent serves. // - https://schemas.mtconnect.org/schemas/MTConnectDevices_2.5.xsd diff --git a/tests/MTConnect.NET-XML-Tests/MTConnect.NET-XML-Tests.csproj b/tests/MTConnect.NET-XML-Tests/MTConnect.NET-XML-Tests.csproj index ce1e88e2f..2e1af056a 100644 --- a/tests/MTConnect.NET-XML-Tests/MTConnect.NET-XML-Tests.csproj +++ b/tests/MTConnect.NET-XML-Tests/MTConnect.NET-XML-Tests.csproj @@ -8,10 +8,10 @@ - - - - + + + + all runtime; build; native; contentfiles; analyzers; buildtransitive diff --git a/tools/dotnet.sh b/tools/dotnet.sh index 85bae5899..7af7482f8 100755 --- a/tools/dotnet.sh +++ b/tools/dotnet.sh @@ -27,6 +27,12 @@ # tools/dotnet.sh build MTConnect.NET.sln # tools/dotnet.sh --docker test tests/MTConnect.NET-Common-Tests # MTCONNECT_DOTNET_USE_DOCKER=1 tools/dotnet.sh --version +# +# Flags: +# -d, --docker Run dotnet inside a pinned mcr.microsoft.com/dotnet/sdk +# container (also honored via +# MTCONNECT_DOTNET_USE_DOCKER=1). Everything after the +# flag is forwarded to the `dotnet` CLI verbatim. set -euo pipefail # --- Locate repo root (macOS-safe; no readlink -f) ---------------------