This document provides detailed examples of the challenges in mapping ODS button tokens to Abyss button tokens, serving as a reference for the token conversion strategy outlined in adr-021-ods-to-abyss-token-conversion.
1. Compound Values vs. Split Values
Example:
- ODS compound value example:
{ "component": "button", "group": "options", "category": "size", "subcategory": "small", "section": "container", "property": "padding", "value": "7px 16px" // Compound CSS value that needs splitting}- Abyss: Requires mapping to two separate tokens:
button.spacing.padding.horizontal.container.sm:"{web.semantic.spacing.scale.lg}"button.spacing.padding.vertical.container.sm:"{web.semantic.spacing.scale.xs}"
Challenge: The automation would need to:
- Recognize that "7px 16px" is a compound CSS shorthand
- Split it into vertical (7px) and horizontal (16px) values
- Map each to the corresponding Abyss token path
2. State Representation Differences
Example:
- ODS uses explicit state and variant fields:
{ "component": "button", "group": "themes", "category": "light", "variant": "primary", // Explicit variant field "state": "hover", // Explicit state field "section": "container", "property": "background-color", "value": "{ds.btnColors.themes.light.primary.hover.background.color.value}"}- Abyss uses state as path segment:
button.color.surface.container.filled-brand.rest - Abyss state values:
rest(instead of "default"),hover,active,disabled
Challenge: The automation would need to:
- Map the state field values from ODS to the corresponding Abyss state path segments ("default" → "rest")
- Transform ODS variant field values to the Abyss variant-color combinations (e.g., ODS "primary" maps to Abyss "filled-brand")
3. Property and Section Organization
Example:
- ODS property and section organization:
{ "component": "button", "group": "themes", "category": "light", "variant": "primary", "state": "default", "section": "label", // Section field "property": "font-color", // Property field "value": "{ds.btnColors.themes.light.primary.default.font.color.value}"}- Abyss:
button.color.text.label.filled-brand.rest: "{web.semantic.color.text.on-container.neutral.default}"
Challenge: The automation would need to:
- Recognize that the "section" + "property" combination in ODS maps to different path structures in Abyss
- Understand that "section: label, property: font-color" corresponds to "text.label" category in Abyss
- Map the ODS variant field value ("primary") to the Abyss variant-color combination ("filled-brand")
4. Icon-Specific Properties
Example:
- ODS has granular icon sections with specific properties for leading, trailing, and loading icons:
// ODS uses specific section types for different icon positions{ "component": "button", "group": "options", "category": "size", "subcategory": "large", "section": "icon-leading", // Specific icon position "property": "margin-right", "value": "8px"},// Additional properties for the same icon section{ "section": "icon-leading", "property": "min-height", "value": "24px"}- Abyss groups icon properties differently:
"button.sizing.all.icon": "{web.semantic.sizing.icon.utility.xs}""button.sizing.all.icon-only.icon": "{web.semantic.sizing.icon.utility.md}"
Challenge: The automation would need to:
- Identify related icon properties across specific section types ("icon-leading", "icon-trailing", "icon-loading")
- Map between different organizational structures
- Handle cases where multiple ODS tokens map to a single Abyss token
- Distinguish between standard icon properties and icon-only button properties
5. Size Mapping Complexity
Example:
- ODS defines size tokens with size information in the
subcategoryfield:
// Small, medium, and large button heights{ "component": "button", "group": "options", "category": "size", "subcategory": "small", // Size in subcategory field "section": "container", "property": "min-height", "value": "32px"},{ "subcategory": "medium", "property": "min-height", "value": "40px" },{ "subcategory": "large", "property": "min-height", "value": "48px" }- Abyss:
"button.sizing.height.min.container.sm": "{web.semantic.sizing.height.min.sm}""button.sizing.height.min.container.md": "{web.semantic.sizing.height.min.md}""button.sizing.height.min.container.lg": "{web.semantic.sizing.height.min.lg}"
Challenge: The automation would need to:
- Extract the size value from the
subcategoryfield - Map between different size naming patterns ("small"/"medium"/"large" to "sm"/"md"/"lg")
- Handle the reorganized structure with "container" at a different level
6. Complex Variant System and Missing Counterparts
Example 1: Variant-Color Combinations
- The Abyss button tokens combine variants with colors, requiring complex mapping:
// Filled variant with brand color"button.color.text.label.filled-brand": "{web.semantic.color.text.label.cta.primary-alt}"// Outline variant with destructive color"button.color.text.label.outline-destructive": "{web.semantic.color.text.status.error}"
- ODS uses separate paths for variants and colors
Example 2: Different Focus State Implementation
- Abyss implements focus states through a utility function in the styling system:
'&:focus-visible': {focusRing:'boundingBorder'}
- ODS implements focus as explicit component tokens with multiple properties:
// Structure tokens for focus properties{"component": "button","group": "structure","category": "focus","section": "outline","property": "offset","value": "2px"},// Additional tokens for style and color{ "property": "style", "value": "solid" },{"group": "themes","category": "light","variant": "focus","section": "outline","property": "color","value": "#0C55B8"}
Example 3: Icon-Only Button Specifics
- Abyss has specialized tokens for icon-only buttons with per-size values:
"button.sizing.all.icon-only.container.sm": "{web.semantic.sizing.all.sm}""button.sizing.all.icon-only.container.md": "{web.semantic.sizing.all.md}""button.sizing.all.icon-only.container.lg": "{web.semantic.sizing.all.lg}"
- ODS has icon tokens but organizes them differently with leading/trailing distinctions
Example 4: Loading State Support
- Abyss button has specific loading spinner colors for different variants:
"button.color.surface.loading-spinner.text-brand": "{web.semantic.color.surface.container.status.info.saturated}"
- ODS has a general loading icon configuration
Challenge: The mapping process would need to:
- Identify missing token counterparts in ODS
- Map ODS variants to Abyss's combined variant-color system
- Create appropriate mappings for specialized token categories like loading states
- Document these gaps for future consideration in ODS token development
Conclusion
These examples from just the Button component illustrate the complexity of token mapping. These challenges reinforce why a purely automated approach would be insufficient. The mapping process requires value transformation, structural reorganization, and edge case handling that necessitates a hybrid approach with manual configuration of specialized transformers.