XML Configuration Analysis Report
February 10, 2026 · View on GitHub
Date: 2026-02-10 (Updated)
Ticket: intel/acat#6
Purpose: Comprehensive inventory of XML configuration files for JSON migration planning
Executive Summary
- Total XML Files: 86 configuration files
- Distinct Schemas: 8 major schema types identified
- Total File Size: ~440 KB
- Estimated Migration Effort: 40-60 hours (1-1.5 weeks for 1 developer)
- Critical Path: ActuatorSettings → Panel Configurations → Theme Settings
High-Level Findings
- Panel configurations dominate (73 files, ~85% of total) - these define UI scanners and menus
- ActuatorSettings.xml is the most complex and critical single file (user input device configuration)
- Theme.xml is moderately complex with color schemes and styling
- Configuration maps (PanelConfigMap, UserControlConfigMap) are simple routing tables
- LanguageSettings and SpellCheck are simple data files
- Heavy use of DTD entities for templating (fonts, sizes, colors) in panel configurations
- Variable references (@MinActuationHoldTime, @CmdEnterKey) must be preserved during migration
Schema Inventory
1. ActuatorSettings.xml
Purpose: Configure input devices (switches) for ACAT - keyboard, camera, BCI, external switches
Root Element: <ActuatorConfig>
Instances: 1 (user-specific)
Complexity: High (nested structures, multiple switch types)
Priority: P1 (Critical - controls all user input)
Lines of Code: ~140
Structure:
<ActuatorConfig>
<ActuatorSettings>
<ActuatorSetting>
<Description>string</Description>
<Enabled>boolean</Enabled>
<Id>guid</Id>
<ImageFileName>string</ImageFileName>
<Name>string</Name>
<SwitchSettings>
<SwitchSetting>
<Actuate>boolean</Actuate>
<BeepFile>string</BeepFile>
<Command>string</Command>
<Description>string</Description>
<Enabled>boolean</Enabled>
<MinHoldTime>string</MinHoldTime>
<Name>string</Name>
<Source>string</Source>
</SwitchSetting>
</SwitchSettings>
</ActuatorSetting>
</ActuatorSettings>
</ActuatorConfig>
Sample Data:
<ActuatorSetting>
<Description>Use the computer keyboard as a switch to control ACAT.</Description>
<Enabled>true</Enabled>
<Id>d91a1877-c92b-4d7e-9ab6-f01f30b12df9</Id>
<ImageFileName>KeyboardSwitch.jpg</ImageFileName>
<Name>Keyboard</Name>
<SwitchSettings>
<SwitchSetting>
<Actuate>true</Actuate>
<BeepFile>beep.wav</BeepFile>
<Command>@Trigger</Command>
<Enabled>true</Enabled>
<MinHoldTime>@MinActuationHoldTime</MinHoldTime>
<Name>Trigger</Name>
<Source>F12</Source>
</SwitchSetting>
</SwitchSettings>
</ActuatorSetting>
Special Handling:
- Contains template variables (e.g.,
@MinActuationHoldTime,$ACAT_USER_GUIDE) - GUIDs must be preserved during migration
- Multiple actuator types (Keyboard, Camera, BCI, External, Sample)
- Each actuator has 1-N switch configurations
2. Panel Configuration Files (Scanner/Menu XML)
Purpose: Define UI layouts for scanners, keyboards, menus, and dialogs
Root Element: <ACAT> with <WidgetAttributes>, <Layout>, <Animations>
Instances: 73 files
Complexity: Medium to High (varies by panel complexity)
Priority: P1-P2 (High usage, core UI definitions)
Structure:
<ACAT>
<WidgetAttributes>
<WidgetAttribute name="..." label="..." value="..."
fontsize="..." fontname="..." bold="..."/>
</WidgetAttributes>
<Layout colorScheme="...">
<Widget class="..." name="..." colorScheme="...">
<Widget class="..." name="..." />
</Widget>
</Layout>
<Animations>
<Animation name="..." start="..." autoStart="..."
firstPauseTime="..." scanTime="..." iterations="...">
<Widget name="..." onSelect="..." />
</Animation>
</Animations>
</ACAT>
Examples:
- MainMenu.xml - Main application menu
- TalkApplicationScanner.xml - Primary communication interface
- KeyboardAbcUserControl.xml - ABC keyboard layout
- KeyboardQwertyUserControl.xml - QWERTY keyboard layout
- ChromeBrowserContextMenu.xml - Browser-specific menu
- OutlookContextMenu.xml - Email client menu
Special Handling:
- Uses DTD entities for constants (fonts, colors):
<!ENTITY usebold "false"> - Entity references in attributes:
fontname="&buttonFontName;" - Template variables:
@CmdGoBack,@FirstPauseTime - Unicode characters in labels:
u,¿ - Nested widget hierarchies (recursive structure)
- Animation sequences with state transitions
Note: Per requirements, Animation XMLs should be skipped in Phase 1 (handled in Phase 2).
However, animations are embedded in panel configs, not separate files.
3. Theme.xml
Purpose: Define color schemes and visual styling for all UI elements
Root Element: <ACAT><Theme>
Instances: 1
Complexity: Medium (many color scheme definitions)
Priority: P2 (Important but not critical path)
Lines of Code: ~170
Structure:
<ACAT>
<Theme description="...">
<ColorSchemes>
<ColorScheme name="..."
background="..."
foreground="..."
highlightSelectedBackground="..."
highlightSelectedForeground="..."
highlightBackground="..."
highlightForeground="..." />
</ColorSchemes>
</Theme>
</ACAT>
Color Scheme Types:
- Scanner, ScannerButton, DisabledScannerButton
- WordListItemButton
- Dialog, Menu, MenuTitle, Button
- HighContrast, TalkWindow
- BCIColorCodedRegion (Default, 1-4)
Sample:
<ColorScheme name="Scanner"
background="#232433"
foreground="White"
highlightSelectedBackground="Blue"
highlightSelectedForeground="White"
highlightBackground="#ffaa00"
highlightForeground="#232433" />
Special Handling:
- Color values can be named colors ("White", "Blue") or hex codes ("#232433")
- Optional backgroundImage/highlightBackgroundImage attributes (not shown in sample)
- BCI color schemes have specific contrast requirements (documented in comments)
4. PanelConfigMap.xml
Purpose: Map panel classes to configuration files and form IDs
Root Element: <ACAT><ConfigMapEntries>
Instances: 7 files (one per extension/agent)
Complexity: Simple (flat routing table)
Priority: P1 (Required for panel loading)
Structure:
<ACAT>
<ConfigMapEntries>
<ConfigMapEntry panelClass="..."
configName="..."
configId="..."
formId="..."
configFile="..."
userControls="..." />
</ConfigMapEntries>
</ACAT>
Sample:
<ConfigMapEntry
panelClass="MainMenu"
configName="MainMenu"
configId="EA60C02D-37CA-418F-889B-7767F18A7F00"
formId="148257A1-A8B7-4E75-93F0-56AFCD5B2A3E"
configFile="MainMenu.xml" />
<ConfigMapEntry
panelClass="TalkApplicationScanner"
configName="TalkApplicationScannerQwerty"
configId="F802386C-31CA-4A0D-BC6F-78E71C730D11"
formId="D9A5B53F-7119-445B-BDEA-F76EC53077F1"
configFile="TalkApplicationScanner.xml"
userControls="keyboard=KeyboardQwertyUserControl; wordPrediction=WordPredictionUserControl" />
Special Handling:
- GUIDs (configId, formId) must be preserved
- Optional
userControlsattribute with semicolon-delimited key=value pairs
5. UserControlConfigMap.xml
Purpose: Map user control names to their configuration files
Root Element: <ACAT><UserControlConfigMapEntries>
Instances: 1
Complexity: Simple (flat routing table)
Priority: P1 (Required for user control loading)
Structure:
<ACAT>
<UserControlConfigMapEntries>
<UserControlConfigMapEntry name="..."
configName="..."
configId="..."
userControlId="..."
configFile="..." />
</UserControlConfigMapEntries>
</ACAT>
Sample:
<UserControlConfigMapEntry
name="KeyboardQwertyUserControl"
configName="KeyboardQwertyUserControlConfig"
configId="9681EBF9-3313-4120-A3CD-ADD6A3E99B95"
userControlId="C4668F6A-79D6-4D27-8C68-18172A49F333"
configFile="KeyboardQwertyUserControl.xml" />
Special Handling:
- GUIDs must be preserved
6. PanelClassConfig.xml
Purpose: Define application panel class configurations and layouts
Root Element: <AppPanelClassConfig>
Instances: 1
Complexity: Medium (nested hierarchy)
Priority: P2 (Important but lower usage frequency)
Encoding: UTF-16 (requires special handling)
Structure:
<AppPanelClassConfig>
<PanelClassConfigs>
<PanelClassConfig>
<AppDescription>string</AppDescription>
<AppId>string</AppId>
<AppName>string</AppName>
<PanelClassConfigMaps>
<PanelClassConfigMap>
<Default>boolean</Default>
<Description>string</Description>
<DisplayNameLong>string</DisplayNameLong>
<DisplayNameShort>string</DisplayNameShort>
<Name>string</Name>
<PanelClassConfigMapEntries>
<PanelClassConfigMapEntry>
<ConfigId>guid</ConfigId>
<PanelClass>string</PanelClass>
</PanelClassConfigMapEntry>
</PanelClassConfigMapEntries>
<ScreenshotFileName>string</ScreenshotFileName>
</PanelClassConfigMap>
</PanelClassConfigMaps>
</PanelClassConfig>
</PanelClassConfigs>
</AppPanelClassConfig>
Sample:
<PanelClassConfig>
<AppDescription>Reduced functionality which supports the Talk window to communicate</AppDescription>
<AppId>ACATTalk</AppId>
<AppName>ACAT Talk Application</AppName>
<PanelClassConfigMaps>
<PanelClassConfigMap>
<Default>true</Default>
<Description>An alphabetically arranged keyboard with predictive text</Description>
<DisplayNameLong> ABC Keyboard Layout</DisplayNameLong>
<DisplayNameShort>Alphabetical</DisplayNameShort>
<Name>TalkApplicationABC</Name>
...
</PanelClassConfigMap>
</PanelClassConfigMaps>
</PanelClassConfig>
Special Handling:
- File encoding is UTF-16 - requires explicit encoding handling in parsers
- Contains multiple applications (ACATTalk, ACATDashboard)
- Each app can have multiple panel class configurations
7. SpellCheck.xml
Purpose: Define spelling correction rules (common typos → correct spelling)
Root Element: <ACAT><Spellings>
Instances: 1 (per language - currently only English in default install)
Complexity: Simple (key-value pairs)
Priority: P3 (Nice to have, low usage impact)
Structure:
<ACAT>
<Spellings>
<Spelling word="..." replaceWith="..." />
</Spellings>
</ACAT>
Sample:
<Spellings>
<Spelling word="i" replaceWith="I"/>
<Spelling word="cant" replaceWith="can't"/>
<Spelling word="dont" replaceWith="don't"/>
<Spelling word="shouldnt" replaceWith="shouldn't"/>
</Spellings>
Special Handling:
- None - straightforward key-value mapping
8. LanguageSettings.xml
Purpose: Define language-specific punctuation and spacing rules
Root Element: <LanguageSettings>
Instances: 1 (per language - currently only Spanish in resources)
Complexity: Simple (character lists)
Priority: P3 (Language-specific, low priority)
Structure:
<LanguageSettings>
<DeletePrecedingSpacesChars>string</DeletePrecedingSpacesChars>
<InsertSpaceAfterChars>string</InsertSpaceAfterChars>
<SentenceTerminatorChars>string</SentenceTerminatorChars>
<TerminatorChars>string</TerminatorChars>
</LanguageSettings>
Sample:
<LanguageSettings>
<DeletePrecedingSpacesChars>.? !,:;@})]</DeletePrecedingSpacesChars>
<InsertSpaceAfterChars>.?!,:;})]</InsertSpaceAfterChars>
<SentenceTerminatorChars>¿¡?!.</SentenceTerminatorChars>
<TerminatorChars>¿¡.? !,:;</TerminatorChars>
</LanguageSettings>
Special Handling:
- Contains Unicode characters (Spanish inverted punctuation: ¿ ¡)
Recommended Migration Order
Priority 1 (Week 3 - Sprint 1)
- ActuatorSettings.xml - Critical, single file, well-defined schema
- PanelConfigMap.xml (all 7 instances) - Simple routing tables, high usage
- UserControlConfigMap.xml - Simple routing table, high usage
Priority 2 (Week 4 - Sprint 2)
- Theme.xml - Moderate complexity, single file, important for UX
- PanelClassConfig.xml - Medium complexity, single file
Priority 3 (Week 5+ - Sprint 3)
- Panel Configuration Files (73 files) - Defer to Phase 2 due to complexity and animation handling
- SpellCheck.xml - Simple, low impact
- LanguageSettings.xml - Simple, language-specific
Generated POCO Classes (Top 5 Schemas)
1. ActuatorSettings.cs
using System;
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations;
using System.Text.Json.Serialization;
namespace ACAT.Lib.Core.ActuatorManagement
{
/// <summary>
/// Root configuration for all actuators (input devices)
/// </summary>
public class ActuatorConfig
{
[JsonPropertyName("actuatorSettings")]
public List<ActuatorSetting> ActuatorSettings { get; set; } = new();
}
/// <summary>
/// Configuration for a single actuator device
/// </summary>
public class ActuatorSetting
{
[JsonPropertyName("id")]
[Required]
public Guid Id { get; set; }
[JsonPropertyName("name")]
[Required]
public string Name { get; set; }
[JsonPropertyName("description")]
public string Description { get; set; }
[JsonPropertyName("enabled")]
public bool Enabled { get; set; } = false;
[JsonPropertyName("imageFileName")]
public string ImageFileName { get; set; }
[JsonPropertyName("switchSettings")]
public List<SwitchSetting> SwitchSettings { get; set; } = new();
}
/// <summary>
/// Configuration for a single switch/button on an actuator
/// </summary>
public class SwitchSetting
{
[JsonPropertyName("name")]
[Required]
public string Name { get; set; }
[JsonPropertyName("source")]
public string Source { get; set; }
[JsonPropertyName("command")]
public string Command { get; set; }
[JsonPropertyName("enabled")]
public bool Enabled { get; set; } = true;
[JsonPropertyName("actuate")]
public bool Actuate { get; set; } = true;
[JsonPropertyName("beepFile")]
public string BeepFile { get; set; }
[JsonPropertyName("description")]
public string Description { get; set; }
[JsonPropertyName("minHoldTime")]
public string MinHoldTime { get; set; }
}
}
2. ThemeSettings.cs
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations;
using System.Text.Json.Serialization;
namespace ACAT.Lib.Core.ThemeManagement
{
/// <summary>
/// Theme configuration root
/// </summary>
public class ThemeConfig
{
[JsonPropertyName("theme")]
[Required]
public Theme Theme { get; set; }
}
/// <summary>
/// Theme definition with description and color schemes
/// </summary>
public class Theme
{
[JsonPropertyName("description")]
public string Description { get; set; }
[JsonPropertyName("colorSchemes")]
[Required]
public List<ColorScheme> ColorSchemes { get; set; } = new();
}
/// <summary>
/// Color scheme for a specific UI element type
/// </summary>
public class ColorScheme
{
[JsonPropertyName("name")]
[Required]
public string Name { get; set; }
[JsonPropertyName("background")]
public string Background { get; set; }
[JsonPropertyName("foreground")]
public string Foreground { get; set; }
[JsonPropertyName("highlightBackground")]
public string HighlightBackground { get; set; }
[JsonPropertyName("highlightForeground")]
public string HighlightForeground { get; set; }
[JsonPropertyName("highlightSelectedBackground")]
public string HighlightSelectedBackground { get; set; }
[JsonPropertyName("highlightSelectedForeground")]
public string HighlightSelectedForeground { get; set; }
[JsonPropertyName("backgroundImage")]
public string BackgroundImage { get; set; }
[JsonPropertyName("highlightBackgroundImage")]
public string HighlightBackgroundImage { get; set; }
}
}
3. PanelConfigMap.cs
using System;
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations;
using System.Text.Json.Serialization;
namespace ACAT.Lib.Core.PanelManagement
{
/// <summary>
/// Root configuration for panel mappings
/// </summary>
public class PanelConfigMapConfig
{
[JsonPropertyName("configMapEntries")]
[Required]
public List<ConfigMapEntry> ConfigMapEntries { get; set; } = new();
}
/// <summary>
/// Maps a panel class to its configuration file and IDs
/// </summary>
public class ConfigMapEntry
{
[JsonPropertyName("panelClass")]
[Required]
public string PanelClass { get; set; }
[JsonPropertyName("configName")]
[Required]
public string ConfigName { get; set; }
[JsonPropertyName("configId")]
[Required]
public Guid ConfigId { get; set; }
[JsonPropertyName("formId")]
[Required]
public Guid FormId { get; set; }
[JsonPropertyName("configFile")]
[Required]
public string ConfigFile { get; set; }
[JsonPropertyName("userControls")]
public string UserControls { get; set; }
}
}
4. UserControlConfigMap.cs
using System;
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations;
using System.Text.Json.Serialization;
namespace ACAT.Lib.Core.PanelManagement
{
/// <summary>
/// Root configuration for user control mappings
/// </summary>
public class UserControlConfigMapConfig
{
[JsonPropertyName("userControlConfigMapEntries")]
[Required]
public List<UserControlConfigMapEntry> UserControlConfigMapEntries { get; set; } = new();
}
/// <summary>
/// Maps a user control to its configuration file and IDs
/// </summary>
public class UserControlConfigMapEntry
{
[JsonPropertyName("name")]
[Required]
public string Name { get; set; }
[JsonPropertyName("configName")]
[Required]
public string ConfigName { get; set; }
[JsonPropertyName("configId")]
[Required]
public Guid ConfigId { get; set; }
[JsonPropertyName("userControlId")]
[Required]
public Guid UserControlId { get; set; }
[JsonPropertyName("configFile")]
[Required]
public string ConfigFile { get; set; }
}
}
5. PanelClassConfig.cs
using System;
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations;
using System.Text.Json.Serialization;
namespace ACAT.Lib.Core.PanelManagement
{
/// <summary>
/// Root configuration for panel class definitions
/// </summary>
public class AppPanelClassConfig
{
[JsonPropertyName("panelClassConfigs")]
[Required]
public List<PanelClassConfig> PanelClassConfigs { get; set; } = new();
}
/// <summary>
/// Configuration for an application's panel classes
/// </summary>
public class PanelClassConfig
{
[JsonPropertyName("appId")]
[Required]
public string AppId { get; set; }
[JsonPropertyName("appName")]
[Required]
public string AppName { get; set; }
[JsonPropertyName("appDescription")]
public string AppDescription { get; set; }
[JsonPropertyName("panelClassConfigMaps")]
[Required]
public List<PanelClassConfigMap> PanelClassConfigMaps { get; set; } = new();
}
/// <summary>
/// Configuration map for a panel class
/// </summary>
public class PanelClassConfigMap
{
[JsonPropertyName("name")]
[Required]
public string Name { get; set; }
[JsonPropertyName("displayNameShort")]
public string DisplayNameShort { get; set; }
[JsonPropertyName("displayNameLong")]
public string DisplayNameLong { get; set; }
[JsonPropertyName("description")]
public string Description { get; set; }
[JsonPropertyName("default")]
public bool Default { get; set; } = false;
[JsonPropertyName("screenshotFileName")]
public string ScreenshotFileName { get; set; }
[JsonPropertyName("panelClassConfigMapEntries")]
[Required]
public List<PanelClassConfigMapEntry> PanelClassConfigMapEntries { get; set; } = new();
}
/// <summary>
/// Individual entry in a panel class config map
/// </summary>
public class PanelClassConfigMapEntry
{
[JsonPropertyName("panelClass")]
[Required]
public string PanelClass { get; set; }
[JsonPropertyName("configId")]
[Required]
public Guid ConfigId { get; set; }
}
}
Migration Complexity Assessment
Simple Schemas (1-2 hours each)
- ✅ SpellCheck.xml - Simple key-value list
- ✅ LanguageSettings.xml - Simple character lists
- ✅ PanelConfigMap.xml (7 files) - Simple routing tables
- ✅ UserControlConfigMap.xml - Simple routing table
Subtotal: ~15 hours
Medium Schemas (4-8 hours each)
- ⚠️ Theme.xml - Many color schemes, but flat structure
- ⚠️ PanelClassConfig.xml - Nested but predictable structure
- ⚠️ ActuatorSettings.xml - Nested, with special template variables
Subtotal: ~20 hours
Complex Schemas (40-60 hours total)
- ❌ Panel Configuration Files (73 files) - Defer to Phase 2
- Contains DTD entities requiring preprocessing
- Embedded animations (Phase 2 scope)
- Complex nested widget hierarchies
- High variation across files
Phase 1 Subtotal: ~35-40 hours
Phase 2 Estimate: ~40-60 hours (Panel configs)
Risk Assessment
Critical Risks
-
Template Variable Resolution
- Risk: Many XML files use template variables (e.g.,
@MinActuationHoldTime,@CmdGoBack) - Impact: High - variables must be resolved at runtime or preserved in JSON
- Mitigation: Preserve template syntax in JSON; update variable resolution logic
- Risk: Many XML files use template variables (e.g.,
-
DTD Entity Resolution
- Risk: Panel XMLs use DTD entities for constants (e.g.,
&buttonFontName;) - Impact: High - XML parser automatically resolves these; JSON won't
- Mitigation: Preprocess XML to resolve entities before JSON conversion, or move constants to separate config
- Risk: Panel XMLs use DTD entities for constants (e.g.,
-
GUID Preservation
- Risk: GUIDs in config files may be referenced by code or other configs
- Impact: High - breaking GUID references would break the application
- Mitigation: Ensure 100% fidelity in GUID migration; add validation
-
Encoding Issues
- Risk: PanelClassConfig.xml uses UTF-16 encoding
- Impact: Medium - requires special handling in migration tool
- Mitigation: Auto-detect encoding; ensure UTF-8 JSON output
Medium Risks
-
Animation Complexity
- Risk: 73 panel files contain animation definitions
- Impact: Medium - animations should be handled in Phase 2 per requirements
- Mitigation: Keep panel configs as XML in Phase 1; migrate in Phase 2
-
Backward Compatibility
- Risk: Users may have custom XML configurations
- Impact: Medium - need migration tool for users
- Mitigation: Create migration tool (Ticket #8); support both XML and JSON temporarily
-
Unicode and Special Characters
- Risk: XML files contain Unicode (¿, ¡, u)
- Impact: Low - JSON supports Unicode natively
- Mitigation: Test with non-ASCII characters; ensure UTF-8 encoding
Low Risks
-
Color Value Formats
- Risk: Theme.xml accepts both named colors ("White") and hex codes ("#232433")
- Impact: Low - both formats valid in JSON
- Mitigation: Validate both formats in JSON schema
-
Optional vs. Required Fields
- Risk: Not all fields documented; some may be optional
- Impact: Low - can be discovered during testing
- Mitigation: Code inspection + runtime testing
Migration Strategy Recommendations
Phase 1 (Weeks 3-4) - Foundation
Scope: 13 simple/medium files
Focus: Core routing configs and user settings
-
Create JSON schemas for top 5 types (Ticket #7)
-
Create migration tool (Ticket #8)
-
Migrate in order:
- ActuatorSettings.xml
- PanelConfigMap.xml (7 files)
- UserControlConfigMap.xml
- Theme.xml
- PanelClassConfig.xml
- SpellCheck.xml
- LanguageSettings.xml
-
Update ACAT loaders to support JSON (Ticket #9)
-
Test with real user configurations
Phase 2 (Later) - Panel Configurations
Scope: 73 panel configuration files
Focus: Complex UI definitions with animations
- Design panel JSON schema with animation support
- Build entity resolution preprocessor
- Migrate panel configs in batches by type:
- Main menus (2 files)
- Keyboard layouts (10 files)
- Context menus (20 files)
- User controls (25 files)
- Specialized panels (16 files)
Technical Notes
XML Parser Behavior to Replicate
-
Automatic Entity Resolution
- XML:
<!ENTITY buttonFontName "Arial">→fontname="&buttonFontName;"becomesfontname="Arial" - JSON: Must preprocess or store entity values separately
- XML:
-
Whitespace Handling
- XML parsers normalize whitespace in element content
- JSON preserves literal strings
- May need trimming logic
-
Type Coercion
- XML: Everything is a string by default
- JSON: Types are explicit (string, number, boolean, array, object)
- Migration must correctly infer types
-
Default Values
- XML: Missing elements may have defaults defined in code
- JSON: Explicitly set defaults or rely on POCO initializers
Tools Needed
-
XML → POCO Deserializer
- Use
System.Xml.Serialization.XmlSerializer - Test with all XML files to ensure POCOs match
- Use
-
POCO → JSON Serializer
- Use
System.Text.Json.JsonSerializer - Configure for readability (indented, camelCase)
- Use
-
JSON Schema Validator
- Use JSON Schema Draft 7
- Integrate with VS Code for IntelliSense
-
Migration Report Generator
- Track success/failure per file
- Log warnings for manual review
- Generate diff reports
Validation Checklist
Before considering migration complete:
- All XML files successfully parse
- All POCOs correctly deserialize XML
- All JSON files validate against schemas
- All JSON files correctly deserialize to POCOs
- No data loss in XML → JSON → POCO round trip
- GUIDs preserved exactly
- Template variables preserved
- Unicode characters preserved
- Application launches with JSON configs
- All features work (input, UI, themes)
- Performance: JSON load time ≤ XML load time
- User migration tool tested with real configs
Appendix: File Distribution
By Schema Type
| Schema Type | Count | Percentage |
|---|---|---|
| Panel Configurations | 73 | 84.9% |
| PanelConfigMap | 7 | 8.1% |
| ActuatorSettings | 1 | 1.2% |
| Theme | 1 | 1.2% |
| UserControlConfigMap | 1 | 1.2% |
| PanelClassConfig | 1 | 1.2% |
| SpellCheck | 1 | 1.2% |
| LanguageSettings | 1 | 1.2% |
| Total | 86 | 100% |
By Location
| Directory | Count |
|---|---|
/src/ACATResources/panelconfigs/common/ | 54 |
/src/ACATResources/panelconfigs/es/ | 7 |
/src/Extensions/Default/AppAgents/* | 4 |
/src/Extensions/Default/FunctionalAgents/* | 2 |
/src/Applications/Install/Users/DefaultUser/panelconfigs/ | 4 |
/src/Applications/Install/Users/DefaultUser/ | 1 |
/src/Applications/Install/Users/DefaultUser/en/ | 1 |
/src/ACATResources/panelconfigs/ | 3 |
/src/Assets/Themes/Default/ | 1 |
By Complexity Level
| Complexity | Count | Effort (hours) |
|---|---|---|
| Simple | 10 | 15 |
| Medium | 3 | 20 |
| Complex (Phase 2) | 73 | 40-60 |
| Phase 1 Total | 13 | 35-40 |
JSON Schema Examples
Example: actuator-settings.schema.json
{
"$schema": "http://json-schema.org/draft-07/schema#",
"$id": "https://acat.intel.com/schemas/actuator-settings.json",
"title": "ACAT Actuator Settings",
"description": "Configuration for input devices (switches) that control ACAT",
"type": "object",
"required": ["actuatorSettings"],
"properties": {
"actuatorSettings": {
"type": "array",
"description": "List of configured actuators",
"items": { "$ref": "#/definitions/actuatorSetting" },
"minItems": 1
}
},
"definitions": {
"actuatorSetting": {
"type": "object",
"required": ["id", "name"],
"properties": {
"id": { "type": "string", "format": "uuid" },
"name": { "type": "string", "minLength": 1 },
"description": { "type": "string" },
"enabled": { "type": "boolean", "default": false },
"imageFileName": { "type": "string" },
"switchSettings": {
"type": "array",
"items": { "$ref": "#/definitions/switchSetting" }
}
}
},
"switchSetting": {
"type": "object",
"required": ["name", "source"],
"properties": {
"name": { "type": "string", "minLength": 1 },
"source": { "type": "string", "minLength": 1 },
"command": { "type": "string" },
"enabled": { "type": "boolean", "default": true },
"actuate": { "type": "boolean", "default": true },
"beepFile": { "type": ["string", "null"] },
"description": { "type": "string" },
"minHoldTime": { "type": "string" }
}
}
}
}
Example: theme.schema.json
{
"$schema": "http://json-schema.org/draft-07/schema#",
"$id": "https://acat.intel.com/schemas/theme.json",
"title": "ACAT Theme Configuration",
"type": "object",
"required": ["theme"],
"properties": {
"theme": {
"type": "object",
"required": ["colorSchemes"],
"properties": {
"description": { "type": "string" },
"colorSchemes": {
"type": "array",
"items": { "$ref": "#/definitions/colorScheme" },
"minItems": 1
}
}
}
},
"definitions": {
"colorScheme": {
"type": "object",
"required": ["name"],
"properties": {
"name": {
"type": "string",
"enum": ["Scanner", "ScannerButton", "Dialog", "Menu", "MenuTitle",
"Button", "HighContrast", "TalkWindow", "BCIColorCodedRegionDefault"]
},
"background": { "type": "string", "pattern": "^(#[0-9A-Fa-f]{6}|[A-Za-z]+)$" },
"foreground": { "type": "string", "pattern": "^(#[0-9A-Fa-f]{6}|[A-Za-z]+)$" },
"highlightBackground": { "type": "string" },
"highlightForeground": { "type": "string" },
"highlightSelectedBackground": { "type": "string" },
"highlightSelectedForeground": { "type": "string" },
"backgroundImage": { "type": "string" },
"highlightBackgroundImage": { "type": "string" }
}
}
}
}
Example Migration Output
Before: ActuatorSettings.xml
<?xml version="1.0" encoding="utf-8"?>
<ActuatorConfig>
<ActuatorSettings>
<ActuatorSetting>
<Enabled>true</Enabled>
<Id>d91a1877-c92b-4d7e-9ab6-f01f30b12df9</Id>
<Name>Keyboard</Name>
<SwitchSettings>
<SwitchSetting>
<Command>@Trigger</Command>
<Name>Trigger</Name>
<Source>F12</Source>
</SwitchSetting>
</SwitchSettings>
</ActuatorSetting>
</ActuatorSettings>
</ActuatorConfig>
After: actuator-settings.json
{
"$schema": "https://acat.intel.com/schemas/actuator-settings.json",
"actuatorSettings": [
{
"enabled": true,
"id": "d91a1877-c92b-4d7e-9ab6-f01f30b12df9",
"name": "Keyboard",
"switchSettings": [
{
"command": "@Trigger",
"name": "Trigger",
"source": "F12"
}
]
}
]
}
Additional POCO Classes
SpellCheck.cs
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations;
using System.Text.Json.Serialization;
namespace ACAT.Lib.Core.SpellCheckManagement
{
public class SpellCheckConfig
{
[JsonPropertyName("spellings")]
[Required]
public List<SpellingRule> Spellings { get; set; } = new();
public static SpellCheckConfig CreateDefault()
{
return new SpellCheckConfig
{
Spellings = new List<SpellingRule>
{
new SpellingRule { Word = "i", ReplaceWith = "I" },
new SpellingRule { Word = "cant", ReplaceWith = "can't" },
new SpellingRule { Word = "dont", ReplaceWith = "don't" }
}
};
}
}
public class SpellingRule
{
[JsonPropertyName("word")]
[Required]
public string Word { get; set; }
[JsonPropertyName("replaceWith")]
[Required]
public string ReplaceWith { get; set; }
}
}
LanguageSettings.cs
using System.ComponentModel.DataAnnotations;
using System.Text.Json.Serialization;
namespace ACAT.Lib.Core.Utility
{
public class LanguageSettings
{
[JsonPropertyName("deletePrecedingSpacesChars")]
[Required]
public string DeletePrecedingSpacesChars { get; set; }
[JsonPropertyName("insertSpaceAfterChars")]
[Required]
public string InsertSpaceAfterChars { get; set; }
[JsonPropertyName("sentenceTerminatorChars")]
[Required]
public string SentenceTerminatorChars { get; set; }
[JsonPropertyName("terminatorChars")]
public string TerminatorChars { get; set; }
public static LanguageSettings CreateSpanishDefault()
{
return new LanguageSettings
{
DeletePrecedingSpacesChars = ".? !,:;@})]",
InsertSpaceAfterChars = ".?!,:;})]",
SentenceTerminatorChars = "¿¡?!.",
TerminatorChars = "¿¡.? !,:;"
};
}
}
}
Next Steps
- Review this report with team - validate findings
- Proceed to Ticket #7 - Generate JSON schemas and POCOs
- Create Ticket #8 - Build migration tool
- Create Ticket #9 - Update ACAT configuration loaders
- Begin Phase 1 migration following priority order
- Plan Phase 2 after Phase 1 completion and lessons learned
Conclusion
This comprehensive analysis has successfully:
- ✅ Inventoried all 86 XML configuration files
- ✅ Identified 8 distinct schema types
- ✅ Documented structure and complexity for each schema
- ✅ Generated POCO classes for top 5 schemas
- ✅ Created migration priority list (P1, P2, P3)
- ✅ Assessed risks and special handling requirements
- ✅ Provided JSON schema examples
- ✅ Estimated migration effort: 40-60 hours
The migration is feasible with a phased approach. Priority 1 configurations (ActuatorSettings, Theme, maps) can be migrated first to validate the approach, followed by the more complex panel configurations in Phase 2.
Key Success Factors:
- Strong typing with POCO classes and JSON Schema validation
- Automated migration tool to reduce errors
- Comprehensive testing to ensure no data loss
- Preserve GUIDs and variable references exactly
- Handle DTD entities through XML preprocessing
Report Generated: 2026-02-10 (Updated)
Author: GitHub Copilot
Ticket: intel/acat#6
Status: ✅ Complete - Ready for Review