Cada exportación de figmascope incluye tokens.json. Es el puente entre los valores visuales de Figma y las constantes tipadas que necesita tu código. Este artículo cubre el esquema, cómo se nombran las claves, qué ocurre cuando un archivo de Figma no tiene Variables y dónde falla honestamente el sistema de tokens.
El esquema
La estructura de nivel superior tiene cuatro secciones:
{
"spacing": {
"spacing.4": { "$value": 4, "$type": "dimension" },
"spacing.8": { "$value": 8, "$type": "dimension" },
"spacing.12": { "$value": 12, "$type": "dimension" },
"spacing.16": { "$value": 16, "$type": "dimension" },
"spacing.24": { "$value": 24, "$type": "dimension" }
},
"radius": {
"radius.4": { "$value": 4, "$type": "dimension" },
"radius.8": { "$value": 8, "$type": "dimension" },
"radius.12": { "$value": 12, "$type": "dimension" }
},
"color": {
"color.7f5cfe": { "$value": "#7f5cfe", "$type": "color" },
"color.ffffff": { "$value": "#ffffff", "$type": "color" },
"color.1a1a2e": { "$value": "#1a1a2e", "$type": "color" }
},
"typography": {}
}
El formato se asemeja al W3C Design Tokens Community Group: cada token es un objeto con $value y $type. No es una implementación estricta del DTCG del W3C — figmascope es anterior a la publicación final de la especificación y no implementa tipos compuestos como fontFamily — pero se acerca lo suficiente como para que las herramientas compatibles con DTCG puedan parsearlo con adaptaciones mínimas.
El objeto typography vacío no es un error. Se explica a continuación.
Nomenclatura de claves derivada del valor
Cuando un archivo de Figma tiene Variables, las claves de token provienen de los nombres de Variable que asignó el diseñador. spacing.md, color.brand.primary, lo que use el sistema de diseño.
Cuando un archivo de Figma no tiene Variables — lo que ocurre en la mayoría de archivos reales — figmascope recurre a nomenclatura derivada del valor. Un valor de espaciado de 16 se convierte en spacing.16. Un color #7f5cfe se convierte en color.7f5cfe. Un radio de esquina de 4 se convierte en radius.4.
Esto es una concesión deliberada. Los nombres derivados del valor son poco elegantes pero estables. Se derivan del valor real, así que dos ejecuciones del mismo archivo Figma producen la misma clave. spacing.16 siempre significa 16dp. El agente puede confiar en ello.
La alternativa serían nombres posicionales como spacing.1, spacing.2, etc. Esos son frágiles — añade un valor de espaciado menor y todo se desplaza. Los nombres derivados del valor no se desplazan.
Los nombres derivados del valor son un fallback para archivos que deberían tener Variables pero no las tienen. Si tu sistema de diseño tiene 40 valores de espaciado que necesitan nombres semánticos, convence al diseñador de configurar Variables. El fallback de inferencia existe para archivos del mundo real, no como sustituto de un sistema de tokens real. Puedes ejecutar figmascope en tu propio archivo para ver qué ruta de obtención sigue.
El campo tokensSource y su significado
_meta.json incluye un campo tokensSource que indica cómo se derivaron los tokens:
| Valor | Significado |
|---|---|
"figma-variables" |
El archivo Figma tiene Variables y se usaron directamente. Los nombres de token los asignó el diseñador. Cobertura completa. |
"inferred-from-frequency" |
Sin Variables. figmascope analizó todos los nodos, encontró valores que se repiten con frecuencia y los promovió a tokens. La cobertura depende de la consistencia del diseño. |
"none" |
Sin Variables y la inferencia no produjo nada útil. tokens.json tendrá secciones vacías o casi vacías. |
La advertencia "tokens-inferred-from-frequency" en _meta.json refleja esto. Si la ves, la cobertura de tokens es de mejor esfuerzo.
Cuando tokensSource es "inferred-from-frequency", el algoritmo de inferencia es: encontrar todos los valores de dimensión que aparecen en tres o más nodos en los campos padding, gap o cornerRadius. Promover esos a tokens de espaciado o radio respectivamente. Hacer lo mismo con los colores de relleno. Los valores que aparecen solo una o dos veces se tratan como excepciones y no se promueven.
Esto funciona bien para diseños que son internamente consistentes. Funciona mal para diseños exploratorios donde el espaciado varía libremente. Las advertencias en _meta.json existen precisamente para que el agente sepa en qué situación se encuentra.
Por qué la tipografía suele estar vacía
Los tokens de tipografía requieren Figma Variables de tipo FLOAT o STRING para extraerse de forma fiable. Los estilos de texto existen en Figma como estilos compartidos, no como Variables, y la superficie de API para estilos es diferente a la de Variables.
figmascope v0.4 extrae tipografía cuando las Variables la cubren. No intenta la inferencia por frecuencia para tipografía porque los tokens de tipografía útiles — familia tipográfica, altura de línea, espaciado entre letras, combinaciones de peso — no tienen nombres obvios derivados del valor como spacing.16. Una clave fontSize.14 es mucho menos útil que typography.body.small, y generar un nombre malo es peor que no generar ninguno.
El resultado es honesto: si tu archivo Figma tiene Variables de tipografía, obtienes tokens de tipografía. Si no, obtienes un objeto vacío y el agente recibe el aviso a través de CONTEXT.md de que la cobertura tipográfica puede ser parcial.
// _meta.json
{
"tokensSource": "inferred-from-frequency",
"warnings": [
"tokens-inferred-from-frequency"
]
}
El agente lo ve y sabe ser conservador con las referencias a tokens de tipografía. Genera código de fallback con valores explícitos y un comentario TODO en lugar de inventar un nombre de token.
Cómo el agente usa tokens.json
La restricción en CONTEXT.md dice: "Nunca codifiques directamente valores dp si existe un token dentro de ±2dp." La tolerancia de ±2dp maneja el redondeo. Si un nodo tiene paddingLeft: 15 y existe spacing.16, el agente usa spacing.16. Si el token más cercano es spacing.24, no hay coincidencia — el agente usa el valor literal.
Para los colores, la coincidencia es exacta sobre el valor hexadecimal tras normalización a minúsculas de 6 dígitos. #7F5CFE coincide con color.7f5cfe.
Para el radio de esquina, la misma regla ±2dp que para el espaciado.
La salida práctica para un objetivo Jetpack Compose tiene este aspecto:
// With figma-variables tokensSource
Surface(
shape = RoundedCornerShape(Radius.radius8),
color = Color.Brand.Primary
) {
Column(
verticalArrangement = Arrangement.spacedBy(Spacing.spacing16),
modifier = Modifier.padding(horizontal = Spacing.spacing24)
) { ... }
}
// With inferred-from-frequency tokensSource (same visual output, same token refs)
Surface(
shape = RoundedCornerShape(Radius.radius8),
color = Color.color7f5cfe
) { ... }
Los nombres derivados del valor son menos legibles. Siguen siendo mejores que los valores codificados directamente.
Comparación con otros enfoques de extracción de tokens
El panel nativo "Inspect" de Figma muestra valores por nodo. No hay archivo de token exportado. Tendrías que crear uno manualmente o usar un plugin como Tokens Studio. Ambos requieren esfuerzo del diseñador y mantenimiento continuo.
figmascope extrae tokens automáticamente en cada exportación. Si el archivo cambia, vuelve a exportar y los tokens reflejan el estado actual. La contrapartida es que sin Variables los nombres son derivados del valor en lugar de semánticos — pero obtienes un archivo de tokens cada vez, sin plugin ni paso de flujo de trabajo adicional.
Tokens Studio (antes integración de Style Dictionary) requiere que el diseñador configure el plugin, mantenga un archivo JSON en el archivo Figma y lo sincronice. Esa es la solución correcta para un sistema de diseño maduro. El enfoque de figmascope es la solución correcta para archivos que aún no han llegado ahí, que son la mayoría.
La extracción de tokens es una instantánea de mejor esfuerzo de lo que existe en el archivo. No es un sustituto de un sistema de diseño que prioriza los tokens. Es lo que usas mientras construyes hacia uno.
Conectar tokens.json a tu base de código
La estructura JSON es lo suficientemente plana como para que generar un objeto Kotlin o un módulo TypeScript a partir de ella sea sencillo. Un script simple:
// tokens.json → Kotlin object (simplified)
const tokens = JSON.parse(fs.readFileSync('tokens.json', 'utf-8'));
let output = 'object Spacing {\n';
for (const [key, token] of Object.entries(tokens.spacing)) {
const name = key.replace('spacing.', 'spacing').replace('.', '_');
output += ` val ${name} = ${token.$value}.dp\n`;
}
output += '}';
// → val spacing16 = 16.dp
Si ya usas un pipeline de design tokens, el formato W3C-ish es suficientemente cercano para integrarlo en Style Dictionary con un transformador personalizado para las claves $value/$type.
El resto de cómo los tokens interactúan con el IR se cubre en IR por Pantalla. Para ver cómo los tokens interactúan con el contexto del agente más amplio, consulta Anatomía de CONTEXT.md. Para el flujo de exportación de design tokens de extremo a extremo, consulta Exportación de Design Tokens. Para exportar tokens de tu propio archivo Figma, dirígete a figmascope.dev.