From b13ae88475f3f68abc62d6dd669189e759a663ff Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Lu=C3=ADs=20Jesus?= Date: Tue, 25 Mar 2025 19:07:26 +0000 Subject: [PATCH] Added conversion from json to xml --- src/pages/tools/json/json-to-xml/index.tsx | 6 +- src/pages/tools/json/json-to-xml/service.ts | 81 +++++++++++++++++++++ 2 files changed, 84 insertions(+), 3 deletions(-) diff --git a/src/pages/tools/json/json-to-xml/index.tsx b/src/pages/tools/json/json-to-xml/index.tsx index 17be45b..68da35b 100644 --- a/src/pages/tools/json/json-to-xml/index.tsx +++ b/src/pages/tools/json/json-to-xml/index.tsx @@ -2,7 +2,7 @@ import React, { useState } from 'react'; import ToolContent from '@components/ToolContent'; import ToolTextInput from '@components/input/ToolTextInput'; import ToolTextResult from '@components/result/ToolTextResult'; -// import { convertJsonToXml } from './service'; +import { convertJsonToXml } from './service'; import { CardExampleType } from '@components/examples/ToolExamples'; import { ToolComponentProps } from '@tools/defineTool'; import { Box, Radio } from '@mui/material'; @@ -65,8 +65,8 @@ export default function JsonToXml({ title }: ToolComponentProps) { const compute = (values: InitialValuesType, input: string) => { if (input) { try { - //const xmlResult = convertJsonToXml(input, values); - //setResult(xmlResult); + const xmlResult = convertJsonToXml(input, values); + setResult(xmlResult); } catch (error) { setResult( `Error: ${ diff --git a/src/pages/tools/json/json-to-xml/service.ts b/src/pages/tools/json/json-to-xml/service.ts index e69de29..ae9671e 100644 --- a/src/pages/tools/json/json-to-xml/service.ts +++ b/src/pages/tools/json/json-to-xml/service.ts @@ -0,0 +1,81 @@ +type JsonToXmlOptions = { + indentationType: 'space' | 'tab' | 'none'; + addMetaTag: boolean; +}; + +export const convertJsonToXml = ( + json: string, + options: JsonToXmlOptions +): string => { + const obj = JSON.parse(json); + return convertObjectToXml(obj, options); +}; + +const getIndentation = (options: JsonToXmlOptions, depth: number): string => { + switch (options.indentationType) { + case 'space': + return ' '.repeat(depth + 1); + case 'tab': + return '\t'.repeat(depth + 1); + case 'none': + default: + return ''; + } +}; + +const convertObjectToXml = ( + obj: any, + options: JsonToXmlOptions, + depth: number = 0 +): string => { + let xml = ''; + + const newline = options.indentationType === 'none' ? '' : '\n'; + + if (depth === 0) { + if (options.addMetaTag) { + xml += '' + newline; + } + xml += '' + newline; + } + + for (const key in obj) { + const value = obj[key]; + + const keyString = isNaN(Number(key)) ? key : `row-${key}`; + + if (Array.isArray(value)) { + value.forEach((item) => { + xml += `${getIndentation(options, depth)}<${keyString}>`; + xml += + typeof item === 'object' && item !== null + ? `${newline}${convertObjectToXml( + item, + options, + depth + 1 + )}${getIndentation(options, depth)}` + : `${escapeXml(String(item))}`; + xml += `${newline}`; + }); + } else if (typeof value === 'object' && value !== null) { + xml += `${getIndentation(options, depth)}<${keyString}>${newline}`; + xml += convertObjectToXml(value, options, depth + 1); + xml += `${getIndentation(options, depth)}${newline}`; + } else { + xml += `${getIndentation(options, depth)}<${keyString}>${escapeXml( + String(value) + )}${newline}`; + } + } + + return depth === 0 ? `${xml}` : xml; +}; + +const escapeXml = (str: string): string => { + return str + .replace(/&/g, '&') + .replace(//g, '>') + .replace(/"/g, '"') + .replace(/'/g, '''); +};