{
    "request_json": "{\"model\":\"gpt-oss:20b\",\"messages\":[{\"role\":\"system\",\"content\":\"# Reglas flat para IR semántico\\n\\nInterpreta INSTRUCCION_USUARIO sobre el estado literal recibido. Devuelve únicamente operaciones soportadas, conserva lo no solicitado y no inventes tipos, propiedades, IDs, campos, fórmulas, relaciones u operaciones.\\n\\n## Entidades\\n\\nCada bloque bajo # Objetos visuales es un objeto independiente. Un objeto raíz y uno con Ubicación: tabla/... se modifican igual cuando la propiedad pertenece al objeto. La ubicación solo limita el ámbito.\\n\\nTTable es una entidad estructural. Sus líneas se identifican por tableId + section + line; sus celdas por tableId + section + line + cell. Los objetos de celda ya aparecen como objetos visuales independientes.\\n\\n## Contrato de modificación\\n\\n`changes` solo admite `{\\\"targetId\\\":\\\"id_real\\\",\\\"path\\\":\\\"/propiedad\\\",\\\"value\\\":valor}` y se usa para un cambio escalar cuando el ID real ya es conocido inequívocamente. Nunca contiene `target`, `type`, `location`, `where`, `set` ni `transform`.\\n\\n`intents` expresa una operación declarativa cuando PHP debe resolver el objetivo o calcularla. Usa `target` y la operación soportada; sus propiedades no llevan `/`.\\n\\nRegla: ID conocido → `changes`; ID o conjunto por resolver → `intents`. La decisión no depende de singular o plural.\\n\\nEjemplos: `{\\\"changes\\\":[{\\\"targetId\\\":\\\"id_123\\\",\\\"path\\\":\\\"/lFontBold\\\",\\\"value\\\":true}],\\\"intents\\\":[]}` · `{\\\"changes\\\":[],\\\"intents\\\":[{\\\"intent\\\":\\\"change\\\",\\\"target\\\":{\\\"type\\\":\\\"TText\\\"},\\\"where\\\":{\\\"property\\\":\\\"cTextColor\\\",\\\"equals\\\":\\\"#rrggbb\\\"},\\\"set\\\":{\\\"property\\\":\\\"cTextColor\\\",\\\"value\\\":\\\"#rrggbb\\\"}}]}`.\\n\\n## Target de intents CORE\\n\\nPara cálculos sobre objetos seleccionados usa `target.ids`. Para resolver un conjunto sencillo usa `target.type`, `target.location` y, si hay filtro literal, `where`. No construyas consultas complejas.\\n\\n## Selección\\n\\n- El ámbito indicado limita los objetos participantes.\\n- Comprueba tipo, ubicación, propiedad y valor literal actual.\\n- En peticiones plurales modifica todos los compatibles.\\n- Un filtro por valor exige coincidencia literal y excluye el resto.\\n- Una petición singular ambigua no produce operaciones.\\n- No uses defaults o apariencia para sustituir un valor ausente.\\n- Copia IDs y nombres de propiedades exactamente como aparecen.\\n\\n## Propietario y operación\\n\\n- Un intent puede usar set como lista para varias propiedades del mismo conjunto; where es opcional cuando no hay filtro por valor.\\n- Una transformación relativa usa `transform:[{property,op,value}]` sobre propiedades numéricas; `op` admite `multiply`, `add` y `subtract`. `target.ids` limita explícitamente el conjunto a esos IDs reales seleccionados; no se buscan otros.\\n- `set` y `transform` pueden coexistir solo si afectan a propiedades distintas. Una misma propiedad en ambos, una transformación duplicada o un ID inexistente hace que la intención sea inválida.\\n- Propiedad escalar de TTable: changes.\\n- Propiedad de línea: structure con setTableLine.\\n- Propiedad de sección, grupo, columna o línea estructural: operación declarada.\\n- No conviertas una propiedad de un nivel en otra de nivel distinto.\\n\\n## Creación y eliminación\\n\\ncreate requiere tipo real, parentId (null para raíz o ID de tabla para celda), propiedades requeridas y ubicación exacta cuando sea anidado. En una celda usa cTableSectionKey, nTableLineIndex y nTableCellIndex en properties según el contrato. No crea implícitamente líneas o celdas. delete usa el cId real, único y no bloqueado.\\n\\n## Seguridad\\n\\nNo cambies cId, cType ni referencias protegidas. No reemplaces arrays, objetos o relaciones mediante changes. Conserva tipos JSON, dominios, fórmulas y propiedades no solicitadas. Si la capacidad, campo, propiedad o path no existe, devuelve las cuatro listas vacías.\\n\\n## Respuesta\\n\\nDevuelve solo JSON válido con exactamente:\\n\\n{\\\"create\\\":[],\\\"changes\\\":[],\\\"delete\\\":[{\\\"targetId\\\":\\\"id_real\\\"}],\\\"structure\\\":[],\\\"intents\\\":[]}\\n\\n# Operaciones estructurales reales\\n\\nCuando existe OBJETOS_SELECCIONADOS y no se pide explicitamente todo el documento, limita la operación a esos IDs: cambios absolutos escalares usan `changes`; cálculos declarativos usan `target.ids`. No busques objetos adicionales.\\n\\nCada entrada de structure usa exactamente las claves declaradas. No inventes operaciones.\\n\\n`\\\"structure\\\":[{\\\"op\\\":\\\"setTableLine\\\",\\\"tableId\\\":\\\"id_tabla\\\",\\\"section\\\":\\\"header\\\",\\\"lineIndex\\\":0,\\\"path\\\":\\\"/hBackground/cColor\\\",\\\"value\\\":\\\"#rrggbb\\\"}]`\\n\\n`\\\"structure\\\":[{\\\"op\\\":\\\"moveTableColumn\\\",\\\"tableId\\\":\\\"id_tabla\\\",\\\"fromIndex\\\":2,\\\"toIndex\\\":0}]`\\n\\nLas intenciones pueden expresar transformaciones deterministas antes de generar `changes`: `{\\\"intent\\\":\\\"change\\\",\\\"target\\\":{\\\"ids\\\":[\\\"id_real\\\"]},\\\"transform\\\":[{\\\"property\\\":\\\"nFontSize\\\",\\\"op\\\":\\\"multiply\\\",\\\"value\\\":2}]}`. Solo se admiten propiedades numéricas y las operaciones `multiply`, `add` y `subtract`; PHP calcula el valor absoluto.\\n\\n| op | claves | uso |\\n|---|---|---|\\n| setDocument | op,path,value | propiedades reales del documento |\\n| setLabelLayout | op,path,value | propiedades reales de layout de etiqueta |\\n| setTableSection | op,tableId,section,path,value | lConcatNextDataLine, lAlsoOnEmptyGroup |\\n| setTableGroup | op,tableId,path,value | cBreakExpression, aBreakExpressions, lSkipEmptyValues |\\n| clearTableGroup | op,tableId | limpia grupo y líneas de grupo |\\n| addTableColumn | op,tableId,index,width | añade celda vacía; width>0 |\\n| deleteTableColumn | op,tableId,index | no elimina la única columna |\\n| duplicateTableColumn | op,tableId,index,toIndex | clona columna |\\n| insertTableLine | op,tableId,section,index,height,columnWidths | altura y anchos positivos |\\n| deleteTableLine | op,tableId,section,index | línea existente |\\n| moveTableLine | op,tableId,section,fromIndex,toIndex | mueve dentro de sección |\\n| upsertAccumulator | op,name,definition | definición con tipo y formula |\\n| deleteAccumulator | op,name | elimina acumulador existente |\\n\\nSecciones válidas: header, groupHeader, detail, groupFooter, footer. setTableLine admite los paths reales de línea: cName, nHeight, cConditionFormula, hBackground/*, hBorder/*, hZebraPattern/*, flags y paths declarados por el contrato PHP. Las columnas se identifican por contenido y posición lógica.\\n\\n# Propiedades comunes reales\\n\\nTodos los objetos visuales usan unidades milimétricas y comparten estas propiedades cuando aparecen:\\n\\n## Interpretación visual\\n\\n| Orden visual | Propiedad real | Valor o efecto |\\n|---|---|---|\\n| alineación horizontal del texto | cTextAlign | left, center, right o justify; no mueve nLeft |\\n| alineación vertical del texto | cTextVerticalAlign | top, middle o bottom; no mueve nTop |\\n| redondeo | nRounded | porcentaje numérico literal solicitado |\\n| relleno degradado | cFillStyle | gradient |\\n| tamaño relativo de un objeto | nWidth y nHeight | a la mitad divide ambas; al doble multiplica ambas; no cambia nLeft ni nTop |\\n\\n## Colores canónicos\\n\\nCuando el usuario use uno de estos nombres de color, usa su HEX canónico: `rojo:#ff0000` · `verde:#008000` · `verde oscuro:#006400` · `azul:#0000ff` · `azul oscuro:#00008b` · `amarillo:#ffff00` · `gris claro:#d3d3d3`.\\n\\n| Propiedad | Tipo | Restricción |\\n|---|---|---|\\n| cId | S | identidad literal; protegida |\\n| cType | S | tipo literal; protegido |\\n| cName | S | nombre descriptivo |\\n| nLeft, nTop | N | posición no negativa |\\n| nWidth, nHeight | N | tamaño positivo |\\n| lVisible, lLocked | B | visibilidad y bloqueo |\\n| nLayerId, nZIndex | N | capa y orden |\\n| nRotation, nOpacity | N | rotación; opacidad 0..1 |\\n| cCondition | S | fórmula de aparición, no evaluada |\\n| cBorderColor, cBorderColorFormula | S | borde fijo y fórmula |\\n| nBorderWidth | N | grosor no negativo |\\n| lBorderTop, lBorderRight, lBorderBottom, lBorderLeft | B | lados del borde |\\n| cBackgroundColor, cBackgroundColorFormula | S | fondo propio y fórmula |\\n| cFillStyle, cFillColor2, cFillColor3 | S | relleno |\\n| nFillOpacity, nRounded, nShadowSize, nShadowTransparency | N | valores visuales |\\n| cShadowColor, cShadowColorFormula | S | sombra fija y fórmula |\\n| nPaddingTop, nPaddingRight, nPaddingBottom, nPaddingLeft | N | padding propio no negativo |\\n\\nAl crear son obligatorias nLeft, nTop, nWidth, nHeight y las propiedades requeridas por el tipo. cId, cType y referencias de tabla no se crean ni se cambian mediante changes. Las fórmulas permanecen literales.\\n\\nDefaults comunes relevantes: lVisible=true, lLocked=false, nLayerId=0, nZIndex=1, nRotation=0, nOpacity=1, nBorderWidth=0.1, nPaddingTop/Right/Bottom/Left=0. El tipo puede sustituir estos defaults.\\n\\n# TBarcode\\n\\nObjeto visual de código, raíz o contenido de celda. Propiedades: cContent, cBarcodeType, lShowText, lTrimSpaces, cColor, cColorFormula, fuente y estilos del texto legible. Crear requiere cContent y geometría. Cambios usan paths reales con changes.\\n\\nDefaults de creación: cName=Código de barras, cBarcodeType=EAN13, lShowText=true, lTrimSpaces=false, cColor=#000000, cFontFamily=Arial, nFontSize=12.\\n\\n# TChart\\n\\nObjeto visual de gráfico raíz. Propiedades propias: cChartKind y hChartSpec; usa COMMON para geometría y apariencia. Crear requiere geometría y especificación compatible.\\n\\n# TDocument\\n\\nDocumento raíz. Propiedades reales: cType, cFormatVersion, cTemplateId, cTemplateName, cDocumentKind, cPaperFormat, cPaperOrientation, nPaperWidth, nPaperHeight, nDesignHeight, cPaperHeightMode y nContinuousBottomMargin. Los cambios documentales usan setDocument; el layout de etiqueta usa setLabelLayout.\\n\\n# TEllipse\\n\\nForma elíptica raíz. Usa COMMON y nRounded cuando aparezca. No contiene objetos ni adquiere relaciones por solapamiento. Crear usa parentId:null.\\n\\n# TFormattedText\\n\\nObjeto visual con aRichTextRuns. Puede ser raíz o contenido de celda. Crear requiere aRichTextRuns y geometría. Sus propiedades escalares se modifican con changes.\\n\\n# TImage\\n\\nObjeto visual de imagen, raíz o contenido de celda. Propiedades: cSource, cSourceType, lKeepRatio y cFit. cSource y geometría son obligatorios al crear. El origen y sus fórmulas se conservan literalmente. Cambios escalares usan changes; eliminación usa delete.\\n\\nDefaults de creación: cName=Imagen, cSourceType=auto, lKeepRatio=true, cFit=contain.\\n\\n# TLine\\n\\nLínea gráfica raíz, distinta de una línea estructural de TTable. Propiedades propias: cOrientation y cLineStyle. Nunca usa setTableLine.\\n\\n# TRectangle\\n\\nForma rectangular raíz. No contiene objetos. Usa COMMON para geometría, fondo, relleno, borde, redondeo, sombra y opacidad. Crear usa parentId:null.\\n\\n# TTable\\n\\nEntidad estructural raíz. Propiedades propias: cName, geometría, cBackgroundColor, cPageBreakCondition, lFixedSeparators, lFooterOnBottom, cHeightMode y hGroup cuando aparezcan.\\n\\nDefaults relevantes: cName=Tabla, cPageBreakCondition=\\\"\\\", lFixedSeparators=false, lFooterOnBottom=true, cHeightMode=fixed.\\n\\nLíneas se identifican por tableId + section + line; sus propiedades reales se modifican con setTableLine. Celdas se identifican por tableId + section + line + cell, tienen nWidth y objectId o están vacías. Los objetos contenidos ya aparecen una sola vez en Objetos visuales con ubicación directa y se modifican como cualquier objeto visual.\\n\\nOperaciones estructurales disponibles: líneas, secciones, grupo, columnas y acumuladores según OPERATIONS. No es necesario conocer la representación interna de almacenamiento.\\n\\n# TText\\n\\n`nLeft` y `nTop` son obligatorios al crear; si el usuario no indica posicion, usa los defaults reales `nLeft: 0` y `nTop: 0`, sin omitirlos.\\n\\nAl crear, cada elemento de `create` solo tiene `type`, `parentId` y `properties`; `properties` debe contener siempre `cText`, `nLeft`, `nTop`, `nWidth` y `nHeight`, además de las propiedades solicitadas. Para un objeto raiz se usa `parentId: null`.\\n\\nRegla de `cText`: es una expresión; en JSON un texto fijo se envía como `{\\\"cText\\\":\\\"\\\\\\\"HOLA\\\\\\\"\\\"}` para que el valor real conserve las comillas. Las referencias y fórmulas van sin comillas artificiales, y las expresiones mixtas se conservan completas.\\n\\nObjeto visual de texto. Puede estar en documento o en una celda; Ubicación expresa el ámbito y no cambia sus paths.\\n\\nPropiedades propias: cText, cTextColor, cTextColorFormula, nTextOpacity, cTextAlign, cTextVerticalAlign, cFontFamily, nFontSize, lFontBold, lFontItalic, lFontUnderline, lFontStrikeout, lTextWrap, lAllowPageBreak, nLineSpacing, nParagraphSpacing, lKeepEmptyParagraphs, lTextAdjusted, lTrimSpaces, cTextFlowGroup, nTextFlowOrder, nTextFlowLineHeight, nTextDecimalPosition y fórmulas de estilo.\\n\\ncText y fórmulas se conservan literalmente. Crear requiere cText y geometría. Cambiar usa changes; eliminar usa delete.\\n\\nDefaults de creación relevantes: cName=Texto, cText=\\\"\\\", cFontFamily=Arial, nFontSize=12, lTextWrap=true, lKeepEmptyParagraphs=true, cTextColor=#000000, nTextOpacity=1, cTextAlign=left, cTextVerticalAlign=top.\\n\\n# richText\\n\\nObjeto de contenido HTML enriquecido, raíz o contenido de celda. Propiedades: cContent, cVerticalAlign y cOverflow. Crear requiere cContent y geometría. Conservar HTML y fórmulas; cambios escalares usan changes.\\n\\nDefaults de creación: cName=Texto enriquecido, cVerticalAlign=top, cOverflow=hidden.\\n\\n# Contrato experimental de intención\\n\\nUna intención expresa una modificación declarativa sin enumerar IDs:\\n\\n```json\\n{\\\"intent\\\":\\\"change\\\",\\\"target\\\":{\\\"type\\\":\\\"TText\\\",\\\"location\\\":{\\\"kind\\\":\\\"table\\\",\\\"tableId\\\":\\\"id_tabla\\\",\\\"sections\\\":[\\\"header\\\",\\\"footer\\\"]}},\\\"where\\\":{\\\"property\\\":\\\"cBackgroundColor\\\",\\\"equals\\\":\\\"#rrggbb\\\"},\\\"set\\\":{\\\"property\\\":\\\"cBackgroundColor\\\",\\\"value\\\":\\\"#rrggbb\\\"}}\\n```\\n\\n- `target` limita tipo, ID o ubicación plana (`kind`, `tableId`, `sections`, `lines`, `cells`).\\n- `where` es opcional; si existe, contiene condiciones literales `equals` o `notEquals` que deben cumplirse.\\n- Las claves opcionales no utilizadas se omiten; nunca se envían como `null`.\\n- `set` usa una propiedad o una lista de propiedades reales con valores absolutos sobre el mismo conjunto.\\n- La propiedad es semántica y no usa JSON Pointer; PHP genera el path técnico con `/`.\\n- El resolver devuelve el contrato actual `{create,changes,delete,structure}` y no interpreta lenguaje natural.\\n\"},{\"role\":\"user\",\"content\":\"CAMPOS_Y_VARIABLES_MARKDOWN\\n# Campos, variables y acumuladores disponibles\\n\\nTipos: `C`=texto, `N`=número, `D`=fecha, `I`=imagen, `M`=memo, `L`=booleano.\\n\\n## UserVar — Variables de usuario\\n\\n| Nombre | Referencia exacta | Tipo | Definición actual |\\n|---|---|---|---|\\n| — | — | — | Sin definiciones disponibles |\\n\\n## AcumVar — Acumuladores\\n\\n| Nombre | Referencia exacta | Tipo | Definición actual |\\n|---|---|---|---|\\n| — | — | — | Sin definiciones disponibles |\\nFIN_CAMPOS_Y_VARIABLES_MARKDOWN\\n\\nDOCUMENTO_IR_V5\\n# Documento\\n\\ncType: TDocument\\n\\n# Tablas\\n\\n# Objetos visuales\\n\\nFIN_DOCUMENTO_IR_V5\\n\\nINSTRUCCION_USUARIO\\náéíóú ÁÉÍÓÚ ñÑ º € ¿? semántico únicamente raíz líneas ubicación\\nFIN_INSTRUCCION_USUARIO\\n\\nVERIFICACION_FINAL_FLAT\\nDevuelve solo {\\\"create\\\":[],\\\"changes\\\":[],\\\"delete\\\":[],\\\"structure\\\":[],\\\"intents\\\":[]}. Respeta la separación contractual de changes e intents definida en las reglas. En intents, omite las claves opcionales no usadas; no uses null. Respeta el ámbito y modifica solo coincidencias literales. No inventes IDs, propiedades, campos, valores ni operaciones. Aplica el cambio mínimo.\\nFIN_VERIFICACION_FINAL_FLAT\\n\"}],\"stream\":false,\"format\":\"json\",\"keep_alive\":-1,\"options\":{\"temperature\":0,\"top_p\":1,\"top_k\":0,\"repeat_penalty\":1.1,\"frequency_penalty\":0,\"presence_penalty\":0,\"num_ctx\":65536,\"num_batch\":4096,\"num_thread\":10,\"num_gpu\":99,\"num_predict\":4096},\"think\":\"low\"}",
    "http_status": 200,
    "body_raw": "{\"model\":\"gpt-oss:20b\",\"message\":{\"role\":\"assistant\",\"content\":\"{\\\"create\\\":[],\\\"changes\\\":[],\\\"delete\\\":[],\\\"structure\\\":[],\\\"intents\\\":[]}\",\"thinking\":\"\"},\"done\":true,\"total_duration\":1,\"prompt_eval_count\":1,\"prompt_eval_duration\":1,\"eval_count\":1,\"eval_duration\":1}",
    "message_content": "{\"create\":[],\"changes\":[],\"delete\":[],\"structure\":[],\"intents\":[]}",
    "message_thinking": "",
    "done": true,
    "done_reason": null,
    "total_duration": 1,
    "prompt_eval_count": 1,
    "eval_count": 1
}