Excel到嵌套结构的JSON转换

ryevplcw  于 2023-05-02  发布在  其他
关注(0)|答案(2)|浏览(184)

我想使用自动化(使用任何Python或JS库)将以下Excel转换为JSON模板。

我的Excel格式如下:https://docs.google.com/spreadsheets/d/1-vwP_R77dSQsAngfAHQJojd-SR6ncjLYWSpJrxpKbL4/edit?usp=sharing

JSON输出如下:

[
  {
    "Old Field Name": "PRIORITY",
    "Old Field Label": "Priority",
    "New Field Label": "Priority",
    "New Field Name": "Priority",
    "Conversion": [
      {
        "Method": "Mapping",
        "Mapping": [
          "1-high : High",
          "2-medium : Medium",
          "3-low : Low"
        ]
      }
    ]
  },
  {
    "Old Field Name": "REVIEWER",
    "Old Field Label": "Reviewer",
    "New Field Label": "Author",
    "New Field Name": "Author",
    "Conversion": [
      {
        "Method": "CONCAT",
        "Conversion": "Reviewer + <REVIEWER>"
      }
    ]
  },
  {
    "Old Field Name": "NAME",
    "Old Field Label": "Name",
    "New Field Label": "Head",
    "New Field Name": "Head"   
  }
]

有人可以建议任何步骤来实现以下到嵌套JSON的转换,如上面所示,或任何工作来自动化以下场景。

**注意:**我期待JS或Python解决方案,但我也很喜欢C#库或任何JAVA库。

exdqitrt

exdqitrt1#

我已经提出了以下作为一个独立的脚本:

const file = process.argv[2];

const fs = require('fs');
const Papa = require('papaparse');

const rawCsv = fs.readFileSync(file, 'utf8');

const fileContents = Papa.parse(rawCsv, {
    delimiter: '', // auto-detect
    newline: '', // auto-detect
    quoteChar: '"',
    escapeChar: '"',
    header: true,
    transformHeader: true,
    dynamicTyping: false,
    preview: 0,
    encoding: '',
    worker: false,
    comments: false,
    step: undefined,
    complete: undefined,
    error: undefined,
    download: false,
    downloadRequestHeaders: undefined,
    downloadRequestBody: undefined,
    skipEmptyLines: true,
    chunk: undefined,
    chunkSize: undefined,
    fastMode: undefined,
    beforeFirstChunk: undefined,
    withCredentials: undefined,
    transform: true,
    delimitersToGuess: [';', '\t', '|', ',', Papa.RECORD_SEP, Papa.UNIT_SEP],
}).data.map((details) => {
    let row = {...details};

    if (row['Conversion Type'] === 'Mapping') {
        row.Conversion = [
            {
                Method: 'Mapping',
                Mapping: row.Mapping.split('\n'),
            }
        ];
    } else if (row['Conversion Type'] === 'CONCAT') {
        row.Conversion = [{
            Method: 'CONCAT',
            Conversion: row.Mapping,
        }];
    }
    
    delete row.Mapping;
    delete row['Conversion Type'];
    return row;
});

console.log(fileContents);

fs.writeFileSync(file.replace('.csv', '.json'), JSON.stringify(fileContents, null, 2));
  • 快速注意,你真的不需要包括所有这些选项与爸爸。解析。我这样做是为了让它对每个人都完全一样 *

为了使用它,你需要NodeJS并使用npm i papaparse安装papaparse。
如果可能的话,为了更好的可扩展性,你可以考虑使用CONCATconcat作为键,而不是Conversion,在适当的情况下,我们可以应用一个通用规则“以转换方法为键”,这样写:

if (row['Conversion Type'] === 'Mapping') {
        row.Conversion = [
            {
                Method: 'Mapping',
                Mapping: row.Mapping.split('\n'),
            }
        ];
    } else {
        row.Conversion = [{
            Method: row['Conversion Type'],
            [row['Conversion Type'].toLowerCase()]: row.Mapping,
        }];
    }

如果你有任何问题,请告诉我!:)

nnsrf1az

nnsrf1az2#

这里有一个JS/Node的解决方案。js。
第一次从Google Spreadsheet导出为csv。(注意:如果你在Excel中这样做,导出可能会略有不同,所以我从谷歌电子表格导出)。
这是我得到的CSV,保存为MigrationTool。csv

Old Field Name,Old Field Label,New Field Name,New Field Label,Conversion Type,Mapping
PRIORITY,Priority,Priority,Priority,Mapping,"""1-high : High"",
""2-medium : Medium"",
""3-low : Low"""
REVIEWER,Reviewer,Author,Author,CONCAT,"""Reviewer + <REVIEWER>"
NAME,Name,Head,Head,,

接下来编写JavaScript代码进行转换,这实际上相当棘手,但这里是:

const { readFileSync, writeFileSync } = require('fs');

function convertToJson(filePath) {
  let csv = readFileSync(filePath, 'utf-8').split('\n');
  const headings = csv.shift().split(',');
  // handle special last column
  let lastNormal = 0;
  csv.forEach((x, i) => x[0] === '"' ? csv[lastNormal] += x : lastNormal = i);
  csv = csv.filter(x => x[0] !== '"');
  csv = csv.map(x => x.replace(/"",""/g, '|').replace(/"/g, ''));
  // loop through csv rows and create data for json
  let data = [];
  for (let row of csv) {
    let obj = {};
    colCount = -1;
    for (let col of row.split(',')) {
      colCount++;
      if (!headings[colCount]) { continue; }
      if (headings[colCount] === 'Conversion Type') {
        if (!col) { continue; }
        obj.Conversion = { Method: col };
        continue;
      }
      if (headings[colCount] === 'Mapping') {
        if (!col) { continue; }
        obj.Conversion[col.split('|').length > 1
          ? 'Mapping' : 'Conversion'] =
          col.split('|').length > 1 ? col.split('|') : col;
        continue;
      }
      obj[headings[colCount]] = col;
    }
    data.push(obj);
  }
  writeFileSync(
    filePath.replace(/.csv/g, '.json'),
    JSON.stringify(data, null, '  '),
    'utf-8'
  )
}

convertToJson('./MigrationTool.csv');

运行该程序,您将在名为MigrationTool的文件中获得此JSON。json

[
  {
    "Old Field Name": "PRIORITY",
    "Old Field Label": "Priority",
    "New Field Name": "Priority",
    "New Field Label": "Priority",
    "Conversion": {
      "Method": "Mapping",
      "Mapping": [
        "1-high : High",
        "2-medium : Medium",
        "3-low : Low"
      ]
    }
  },
  {
    "Old Field Name": "REVIEWER",
    "Old Field Label": "Reviewer",
    "New Field Name": "Author",
    "New Field Label": "Author",
    "Conversion": {
      "Method": "CONCAT",
      "Conversion": "Reviewer + <REVIEWER>"
    }
  },
  {
    "Old Field Name": "NAME",
    "Old Field Label": "Name",
    "New Field Name": "Head",
    "New Field Label": "Head"
  }
]

最后,得到报酬?:D不,这很好,这是一个有趣的代码挑战。:)

相关问题