วิธีแปลง JSON เป็นรูปแบบ CSV และจัดเก็บในตัวแปร


110

ฉันมีลิงค์ที่เปิดข้อมูล JSON ในเบราว์เซอร์ แต่น่าเสียดายที่ฉันไม่รู้วิธีอ่าน มีวิธีแปลงข้อมูลนี้โดยใช้ JavaScript ในรูปแบบ CSV และบันทึกเป็นไฟล์ JavaScript หรือไม่

ข้อมูลดูเหมือนว่า:

{
  "count": 2,
  "items": [{
    "title": "Apple iPhone 4S Sale Cancelled in Beijing Amid Chaos (Design You Trust)",
    "description": "Advertise here with BSA Apple cancelled its scheduled sale of iPhone 4S in one of its stores in China\u2019s capital Beijing on January 13. Crowds outside the store in the Sanlitun district were waiting on queues overnight. There were incidents of scuffle between shoppers and the store\u2019s security staff when shoppers, hundreds of them, were told that the sales [...]Source : Design You TrustExplore : iPhone, iPhone 4, Phone",
    "link": "http:\/\/wik.io\/info\/US\/309201303",
    "timestamp": 1326439500,
    "image": null,
    "embed": null,
    "language": null,
    "user": null,
    "user_image": null,
    "user_link": null,
    "user_id": null,
    "geo": null,
    "source": "wikio",
    "favicon": "http:\/\/wikio.com\/favicon.ico",
    "type": "blogs",
    "domain": "wik.io",
    "id": "2388575404943858468"
  }, {
    "title": "Apple to halt sales of iPhone 4S in China (Fame Dubai Blog)",
    "description": "SHANGHAI \u2013 Apple Inc said on Friday it will stop selling its latest iPhone in its retail stores in Beijing and Shanghai to ensure the safety of its customers and employees. Go to SourceSource : Fame Dubai BlogExplore : iPhone, iPhone 4, Phone",
    "link": "http:\/\/wik.io\/info\/US\/309198933",
    "timestamp": 1326439320,
    "image": null,
    "embed": null,
    "language": null,
    "user": null,
    "user_image": null,
    "user_link": null,
    "user_id": null,
    "geo": null,
    "source": "wikio",
    "favicon": "http:\/\/wikio.com\/favicon.ico",
    "type": "blogs",
    "domain": "wik.io",
    "id": "16209851193593872066"
  }]
}

สิ่งที่ใกล้เคียงที่สุดที่ฉันสามารถหาได้คือ: แปลงรูปแบบ JSON เป็นรูปแบบ CSV สำหรับ MS Excel

แต่มันดาวน์โหลดในไฟล์ CSV ฉันเก็บไว้ในตัวแปรซึ่งเป็นข้อมูลที่แปลงทั้งหมด

นอกจากนี้ยังต้องการทราบวิธีการเปลี่ยนอักขระ Escape: '\u2019'กลับสู่สภาวะปกติ


ฉันลองใช้รหัสนี้:

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">

<head>
  <title>JSON to CSV</title>
  <script src="http://code.jquery.com/jquery-1.7.1.js" type="text/javascript"></script>
  <script type="text/javascript">
    var json3 = {
      "count": 2,
      "items": [{
          "title": "Apple iPhone 4S Sale Cancelled in Beijing Amid Chaos (Design You Trust)",
          "description": "Advertise here with BSA Apple cancelled its scheduled sale of iPhone 4S in one of its stores in China’s capital Beijing on January 13. Crowds outside the store in the Sanlitun district were waiting on queues overnight. There were incidents of scuffle between shoppers and the store’s security staff when shoppers, hundreds of them, were told that the sales [...]Source : Design You TrustExplore : iPhone, iPhone 4, Phone",
          "link": "http://wik.io/info/US/309201303",
          "timestamp": 1326439500,
          "image": null,
          "embed": null,
          "language": null,
          "user": null,
          "user_image": null,
          "user_link": null,
          "user_id": null,
          "geo": null,
          "source": "wikio",
          "favicon": "http://wikio.com/favicon.ico",
          "type": "blogs",
          "domain": "wik.io",
          "id": "2388575404943858468"
        },
        {
          "title": "Apple to halt sales of iPhone 4S in China (Fame Dubai Blog)",
          "description": "SHANGHAI – Apple Inc said on Friday it will stop selling its latest iPhone in its retail stores in Beijing and Shanghai to ensure the safety of its customers and employees. Go to SourceSource : Fame Dubai BlogExplore : iPhone, iPhone 4, Phone",
          "link": "http://wik.io/info/US/309198933",
          "timestamp": 1326439320,
          "image": null,
          "embed": null,
          "language": null,
          "user": null,
          "user_image": null,
          "user_link": null,
          "user_id": null,
          "geo": null,
          "source": "wikio",
          "favicon": "http://wikio.com/favicon.ico",
          "type": "blogs",
          "domain": "wik.io",
          "id": "16209851193593872066"
        }
      ]
    }
    //var objJson = JSON.parse(json3.items);

    DownloadJSON2CSV(json3.items);

    function DownloadJSON2CSV(objArray) {
      var array = typeof objArray != 'object' ? JSON.parse(objArray) : objArray;

      var str = '';

      for (var i = 0; i < array.length; i++) {
        var line = '';

        for (var index in array[i]) {
          line += array[i][index] + ',';
        }

        line.slice(0, line.Length - 1);

        str += line + '\r\n';
      }
      $('div').html(str);
    }
  </script>

</head>

<body>
  <div></div>
</body>

</html>

แต่ดูเหมือนจะไม่ได้ผล ใครช่วยหน่อยได้ไหม



คุณมีรหัสที่ดีที่นั่น บรรทัดที่ดาวน์โหลดคือ window.open ("data: text / csv; charset = utf-8," + escape (str)) .. เพียงข้ามไปหากไม่ต้องการ และสตริง csv จะถูกเก็บไว้ในตัวแปรนี้: str
zdrsh

1
CSV ไม่สามารถจัดการข้อมูลหลายระดับ (เช่นกัน) เป็น JSON คุณคาดหวังให้ JSON ของคุณมีลักษณะเป็น CSV อย่างไร 2,Apple iPhone 4S Sale Cancelled in Beijing Amid Chaos (Design You Trust), ...เหรอ?
Stefan

ฉันต้องการให้ข้อมูลของฉันมีลักษณะดังนี้: การขาย Apple iPhone 4S ถูกยกเลิกในปักกิ่งท่ามกลางความโกลาหล (Design You Trust) โฆษณาที่นี่กับ BSA Apple ยกเลิกการขาย iPhone 4S ตามกำหนดเวลาในร้านค้าแห่งใดแห่งหนึ่ง .. ,,,,,, ฯลฯ ฉันสามารถลบอักขระเริ่มต้นนี้ได้อย่างง่ายดาย: "{" count ": 2," items ": [:"
praneybehl

@zdrsh ใช่ แต่ด้วยเหตุผลบางอย่างฉันไม่สามารถทำให้มันใช้งานได้
praneybehl

คำตอบ:


165

วิธีที่สวยงามกว่าในการแปลง json เป็น csv คือการใช้ฟังก์ชันแผนที่โดยไม่มีกรอบใด ๆ :

var json = json3.items
var fields = Object.keys(json[0])
var replacer = function(key, value) { return value === null ? '' : value } 
var csv = json.map(function(row){
  return fields.map(function(fieldName){
    return JSON.stringify(row[fieldName], replacer)
  }).join(',')
})
csv.unshift(fields.join(',')) // add header column
 csv = csv.join('\r\n');
console.log(csv)

เอาท์พุต:

title,description,link,timestamp,image,embed,language,user,user_image,user_link,user_id,geo,source,favicon,type,domain,id
"Apple iPhone 4S Sale Cancelled in Beijing Amid Chaos (Design You Trust)","Advertise here with BSA Apple cancelled its scheduled sale of iPhone 4S in one of its stores in China’s capital Beijing on January 13. Crowds outside the store in the Sanlitun district were waiting on queues overnight. There were incidents of scuffle between shoppers and the store’s security staff when shoppers, hundreds of them, were told that the sales [...]Source : Design You TrustExplore : iPhone, iPhone 4, Phone","http://wik.io/info/US/309201303","1326439500","","","","","","","","","wikio","http://wikio.com/favicon.ico","blogs","wik.io","2388575404943858468"
"Apple to halt sales of iPhone 4S in China (Fame Dubai Blog)","SHANGHAI – Apple Inc said on Friday it will stop selling its latest iPhone in its retail stores in Beijing and Shanghai to ensure the safety of its customers and employees. Go to SourceSource : Fame Dubai BlogExplore : iPhone, iPhone 4, Phone","http://wik.io/info/US/309198933","1326439320","","","","","","","","","wikio","http://wikio.com/favicon.ico","blogs","wik.io","16209851193593872066"

อัปเดต ES6 (2016)

ใช้ไวยากรณ์ที่มีความหนาแน่นน้อยกว่านี้และ JSON.stringify เพื่อเพิ่มเครื่องหมายคำพูดให้กับสตริงในขณะที่ไม่ต้องใส่เครื่องหมายตัวเลข:

const items = json3.items
const replacer = (key, value) => value === null ? '' : value // specify how you want to handle null values here
const header = Object.keys(items[0])
const csv = [
  header.join(','), // header row first
  ...items.map(row => header.map(fieldName => JSON.stringify(row[fieldName], replacer)).join(','))
].join('\r\n')

console.log(csv)

3
ฉันชอบความสั้นของสิ่งนี้ แต่ควรสังเกตว่ามันไม่ได้จัดการกับบางสิ่งที่บางคนอาจคิดว่าเหมาะ เช่นแต่ละระเบียนในบรรทัดของตัวเองตัวเลขและบูลีนที่ไม่ได้ใส่
เครื่องหมายคำพูด

2
คุณสามารถเพิ่ม + "\ r \ n" หลัง fields.map () เพื่อรับหนึ่งระเบียนต่อแถว หากต้องการรับตัวเลขที่ไม่มีเครื่องหมายคำพูดคุณสามารถใช้ JSON.stringify (row [fieldName]) แทนซึ่งจะอ้างอิงเฉพาะสตริงและปล่อยให้ตัวเลขไม่ต้องใส่เครื่องหมาย
Christian Landgren

1
@scunliffe: ฉันอัปเดตตัวอย่างใหม่ด้วย JSON.stringify - ควรจัดการกรณีที่คุณอธิบายไว้
Christian Landgren

1
@marathon, Good catch อัปเดตตัวอย่างด้วยตัวเปลี่ยนเพื่อจัดการกรณีว่างแยกต่างหาก หากไม่มีการใช้ตัวแทนที่ null จะถูกส่งออกเป็นnull- ตอนนี้ตัวอย่างควรจัดการทั้ง null, ไม่ได้กำหนดและตัวเลขอย่างถูกต้อง
Christian Landgren

5
เป็นที่น่าสังเกตว่าสิ่งนี้\"จะ""หลีกเลี่ยงสตริงในเครื่องหมายคำพูดโดยใช้ซึ่งทำให้บางฟิลด์สามารถ "โผล่ออกมา" ของคอลัมน์ได้เมื่อดูใน Excel (ซึ่งดูเหมือนว่าจะเป็นอักขระหลีกสำหรับเครื่องหมายคำพูด) สิ่งนี้สามารถแก้ไขได้โดยเพิ่ม.replace(/\\"/g, '""')ต่อท้ายJSON.stringify(row[fieldName], replacer)ตามที่ฉันระบุไว้ในคำตอบด้านบน
user1274820

56

ตกลงในที่สุดฉันก็ได้รหัสนี้ใช้งานได้:

<html>
<head>
    <title>Demo - Covnert JSON to CSV</title>
    <script type="text/javascript" src="http://code.jquery.com/jquery-latest.js"></script>
    <script type="text/javascript" src="https://github.com/douglascrockford/JSON-js/raw/master/json2.js"></script>

    <script type="text/javascript">
        // JSON to CSV Converter
        function ConvertToCSV(objArray) {
            var array = typeof objArray != 'object' ? JSON.parse(objArray) : objArray;
            var str = '';

            for (var i = 0; i < array.length; i++) {
                var line = '';
                for (var index in array[i]) {
                    if (line != '') line += ','

                    line += array[i][index];
                }

                str += line + '\r\n';
            }

            return str;
        }

        // Example
        $(document).ready(function () {

            // Create Object
            var items = [
                  { name: "Item 1", color: "Green", size: "X-Large" },
                  { name: "Item 2", color: "Green", size: "X-Large" },
                  { name: "Item 3", color: "Green", size: "X-Large" }];

            // Convert Object to JSON
            var jsonObject = JSON.stringify(items);

            // Display JSON
            $('#json').text(jsonObject);

            // Convert JSON to CSV & Display CSV
            $('#csv').text(ConvertToCSV(jsonObject));
        });
    </script>
</head>
<body>
    <h1>
        JSON</h1>
    <pre id="json"></pre>
    <h1>
        CSV</h1>
    <pre id="csv"></pre>
</body>
</html>

ขอบคุณมากสำหรับการสนับสนุนทั้งหมดให้กับผู้มีส่วนร่วมทั้งหมด

ปราณี


1
ฉันลองสิ่งนี้แล้ว ฉันมีสามคอลัมน์ แต่ใน excel ทุกสิ่งจะมาในคอลัมน์เดียว
Nithesh Narayanan

1
Nithesh คุณควรระบุ "," เป็นตัวคั่น
Jacer Omri

ขอบคุณสำหรับการแบ่งปันที่นี่ เพียงแค่ใช้มันและทำงานได้อย่างสมบูรณ์แบบ
Ramin Arabbagheri

ขอบคุณสำหรับสิ่งนี้! ฉันเพิ่มสิ่งต่อไปนี้เพื่อหลีกเลี่ยงการมี "[object Object]" ในบรรทัดหากเซลล์มีวัตถุ ถ้า (_.isObject (อาร์เรย์ [i] [ดัชนี])) {อาร์เรย์ [i] [ดัชนี] = JSON.stringify (อาร์เรย์ [i] [ดัชนี]); }. (ใช้ขีดล่าง แต่คุณสามารถเปลี่ยนเป็นวานิลลาได้)
claytronicon

1
@Sunil ฉันพบว่าถ้าค่ามีเครื่องหมายจุลภาคมันจะแตก สำหรับความต้องการของฉันฉันเพิ่งทำสิ่งนี้: var re = new RegExp (',', 'g'); array [i] [index] = array [i] [index] .toString (). replace (re, ';')
claytronicon

18

ทางออกที่ดีมากโดย praneybehl แต่ถ้ามีคนต้องการบันทึกข้อมูลเป็นcsvไฟล์และใช้blobวิธีการพวกเขาสามารถอ้างถึงสิ่งนี้:

function JSONToCSVConvertor(JSONData, ReportTitle, ShowLabel) {     

//If JSONData is not an object then JSON.parse will parse the JSON string in an Object
var arrData = typeof JSONData != 'object' ? JSON.parse(JSONData) : JSONData;
var CSV = '';    
//This condition will generate the Label/Header
if (ShowLabel) {
    var row = "";

    //This loop will extract the label from 1st index of on array
    for (var index in arrData[0]) {
        //Now convert each value to string and comma-seprated
        row += index + ',';
    }
    row = row.slice(0, -1);
    //append Label row with line break
    CSV += row + '\r\n';
}

//1st loop is to extract each row
for (var i = 0; i < arrData.length; i++) {
    var row = "";
    //2nd loop will extract each column and convert it in string comma-seprated
    for (var index in arrData[i]) {
        row += '"' + arrData[i][index] + '",';
    }
    row.slice(0, row.length - 1);
    //add a line break after each row
    CSV += row + '\r\n';
}

if (CSV == '') {        
    alert("Invalid data");
    return;
}   

//this trick will generate a temp "a" tag
var link = document.createElement("a");    
link.id="lnkDwnldLnk";

//this part will append the anchor tag and remove it after automatic click
document.body.appendChild(link);

var csv = CSV;  
blob = new Blob([csv], { type: 'text/csv' }); 
var csvUrl = window.webkitURL.createObjectURL(blob);
var filename = 'UserExport.csv';
$("#lnkDwnldLnk")
.attr({
    'download': filename,
    'href': csvUrl
}); 

$('#lnkDwnldLnk')[0].click();    
document.body.removeChild(link);
}

วิธีนี้ใช้งานได้ แต่มีจุดแปลก ๆ - คุณกำหนดvar rowสองครั้ง (ถ้าคำสั่งและสำหรับลูปไม่สร้างการปิด) นอกจากนี้แถบป้าย / ส่วนหัวอาจลดลงเหลือหนึ่งบรรทัด:Object.keys(arrData[0]).join(',')
ccnokes

คำตอบของคุณใช้งานได้ แต่สำหรับกรณีเช่นถ้าบางคอลัมน์ไม่พร้อมใช้งานสำหรับบางแถวจะไม่พิจารณาคอลัมน์ที่ขาดหายไปและจะไม่จัดเรียงข้อมูลคอลัมน์สำหรับข้อมูลแถวนั้น
sms

ฉันสามารถทำให้วิธีนี้ใช้งานได้ แต่ฉันต้องแก้ไขโค้ดบางส่วนเพื่อ: 1. ทำงานโดยไม่ใช้ JQuery: document.getElementById("lnkDwnldLnk").download = filename; document.getElementById("lnkDwnldLnk").href = csvUrl;2. ทำงานใน IE11: if (window.navigator && window.navigator.msSaveOrOpenBlob) { window.navigator.msSaveOrOpenBlob(blob, filename); } else { document.getElementById('lnkDwnldLnk').click(); }
Jason

17

ฉันแค่อยากจะเพิ่มโค้ดให้กับผู้คนในอนาคตเนื่องจากฉันพยายามส่งออก JSON ไปยังเอกสาร CSV และดาวน์โหลด

ฉันใช้$.getJSONเพื่อดึงข้อมูล json จากเพจภายนอก แต่ถ้าคุณมีอาร์เรย์พื้นฐานคุณสามารถใช้สิ่งนั้นได้

สิ่งนี้ใช้รหัสของ Christian Landgren เพื่อสร้างข้อมูล csv

$(document).ready(function() {
    var JSONData = $.getJSON("GetJsonData.php", function(data) {
        var items = data;
        const replacer = (key, value) => value === null ? '' : value; // specify how you want to handle null values here
        const header = Object.keys(items[0]);
        let csv = items.map(row => header.map(fieldName => JSON.stringify(row[fieldName], replacer)).join(','));
        csv.unshift(header.join(','));
        csv = csv.join('\r\n');

        //Download the file as CSV
        var downloadLink = document.createElement("a");
        var blob = new Blob(["\ufeff", csv]);
        var url = URL.createObjectURL(blob);
        downloadLink.href = url;
        downloadLink.download = "DataDump.csv";  //Name the file here
        document.body.appendChild(downloadLink);
        downloadLink.click();
        document.body.removeChild(downloadLink);
    });
});

แก้ไข: มันน่าสังเกตว่าจะหนีคำพูดในเครื่องหมายคำพูดโดยการเพิ่มJSON.stringify \"หากคุณดู CSV ใน excel จะไม่ชอบให้เป็นอักขระหลีก

คุณสามารถเพิ่ม.replace(/\\"/g, '""')ต่อท้ายJSON.stringify(row[fieldName], replacer)เพื่อแสดงสิ่งนี้อย่างถูกต้องใน excel (สิ่งนี้จะแทนที่\"ด้วย""สิ่งที่ excel ต้องการ)

เต็มบรรทัด: let csv = items.map(row => header.map(fieldName => (JSON.stringify(row[fieldName], replacer).replace(/\\"/g, '""'))).join(','));


12

หากใครต้องการดาวน์โหลดมาใช้งานได้เช่นกัน
นี่คือฟังก์ชั่นเล็ก ๆ ที่ยอดเยี่ยมที่จะแปลงอาร์เรย์ของวัตถุ JSON เป็น csv จากนั้นดาวน์โหลด

downloadCSVFromJson = (filename, arrayOfJson) => {
  // convert JSON to CSV
  const replacer = (key, value) => value === null ? '' : value // specify how you want to handle null values here
  const header = Object.keys(arrayOfJson[0])
  let csv = arrayOfJson.map(row => header.map(fieldName => 
  JSON.stringify(row[fieldName], replacer)).join(','))
  csv.unshift(header.join(','))
  csv = csv.join('\r\n')

  // Create link and download
  var link = document.createElement('a');
  link.setAttribute('href', 'data:text/csv;charset=utf-8,%EF%BB%BF' + encodeURIComponent(csv));
  link.setAttribute('download', filename);
  link.style.visibility = 'hidden';
  document.body.appendChild(link);
  link.click();
  document.body.removeChild(link);
};

แล้วเรียกแบบนี้ว่า

this.downloadCSVFromJson(`myCustomName.csv`, this.state.csvArrayOfJson)

สิ่งนี้ดูเหมือนจะใช้ไม่ได้กับสิ่งต่างๆเมื่อมีคำพูดเดียวในองค์ประกอบใดองค์ประกอบหนึ่งเช่นCap D'antibes
MidnightDataGeek

10

มีหลายทางเลือกในการนำไลบรารีที่มีประสิทธิภาพที่มีอยู่ซึ่งเป็นมาตรฐานมาใช้ซ้ำ

หากคุณใช้ D3 ในโครงการของคุณคุณสามารถเรียกใช้:

    d3.csv.formatหรือd3.csv.formatRowsฟังก์ชันในการแปลงอาร์เรย์ของวัตถุเป็นสตริง csv

    d3.csv.formatRows ช่วยให้คุณสามารถควบคุมคุณสมบัติที่จะแปลงเป็น csv ได้มากขึ้น

    โปรดดูd3.csv.formatและd3.csv.formatRows wiki หน้า

มีห้องสมุดอื่น ๆ ที่มีมากเกินไปเหมือนjQuery-CSV , PapaParse Papa Parse ไม่มีการอ้างอิง - แม้แต่ jQuery

สำหรับ jQuery ปลั๊กอินตามโปรดตรวจสอบเรื่องนี้


1
สิ่งนี้ได้ผลดีสำหรับฉัน โปรดทราบว่า D3 API มีการเปลี่ยนแปลงตั้งแต่ปี 2017 v3 (ปัจจุบันคือ v4): github.com/d3/d3-dsv/blob/v1.2.0/README.md#csvFormat
aljabear

ขอบคุณ! ฉันใช้ Papa.unparse (data) ของPapaParse ( papaparse.com/docs#json-to-csv ) แก้ไขปัญหาของฉันอย่างรวดเร็ว!
Daniel Valenzuela

8

ลองใช้ตัวอย่างเหล่านี้

ตัวอย่างที่ 1:

JsonArray = [{
    "AccountNumber": "123",
    "AccountName": "abc",
    "port": "All",
    "source": "sg-a78c04f8"

}, {
    "Account Number": "123",
    "Account Name": "abc",
    "port": 22,
    "source": "0.0.0.0/0",
}]

JsonFields = ["Account Number","Account Name","port","source"]

function JsonToCSV(){
    var csvStr = JsonFields.join(",") + "\n";

    JsonArray.forEach(element => {
        AccountNumber = element.AccountNumber;
        AccountName   = element.AccountName;
        port          = element.port
        source        = element.source

        csvStr += AccountNumber + ',' + AccountName + ','  + port + ',' + source + "\n";
        })
        return csvStr;
}

ตัวอย่าง 2:

JsonArray = [{
    "AccountNumber": "1234",
    "AccountName": "abc",
    "inbound": [{
        "port": "All",
        "source": "sg-a78c04f8"
    },
    {
        "port": 22,
        "source": "0.0.0.0/0",
    }]
}]

JsonFields = ["Account Number", "Account Name", "port", "source"]

function JsonToCSV() {
    var csvStr = JsonFields.join(",") + "\n";

    JsonArray.forEach(element => {
        AccountNumber = element.AccountNumber;
        AccountName = element.AccountName;
        
        element.inbound.forEach(inboundELe => {
            port = inboundELe.port
            source = inboundELe.source
            csvStr += AccountNumber + ',' + AccountName + ',' + port + ',' + source + "\n";
        })
    })
    return csvStr;
}

คุณสามารถดาวน์โหลดไฟล์ csv โดยใช้รหัสต่อไปนี้:

function downloadCSV(csvStr) {

    var hiddenElement = document.createElement('a');
    hiddenElement.href = 'data:text/csv;charset=utf-8,' + encodeURI(csvStr);
    hiddenElement.target = '_blank';
    hiddenElement.download = 'output.csv';
    hiddenElement.click();
}

4
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
    <title>JSON to CSV</title>
    <script src="http://code.jquery.com/jquery-1.7.1.js" type="text/javascript"></script>
</head>
<body>
    <h1>This page does nothing....</h1>

    <script type="text/javascript">
        var json3 = {
          "count": 2,
          "items": [{
              "title": "Apple iPhone 4S Sale Cancelled in Beijing Amid Chaos (Design You Trust)",
              "description": "Advertise here with BSA Apple cancelled its scheduled sale of iPhone 4S in one of its stores in China’s capital Beijing on January 13. Crowds outside the store in the Sanlitun district were waiting on queues overnight. There were incidents of scuffle between shoppers and the store’s security staff when shoppers, hundreds of them, were told that the sales [...]Source : Design You TrustExplore : iPhone, iPhone 4, Phone",
              "link": "http://wik.io/info/US/309201303",
              "timestamp": 1326439500,
              "image": null,
              "embed": null,
              "language": null,
              "user": null,
              "user_image": null,
              "user_link": null,
              "user_id": null,
              "geo": null,
              "source": "wikio",
              "favicon": "http://wikio.com/favicon.ico",
              "type": "blogs",
              "domain": "wik.io",
              "id": "2388575404943858468"
            },
            {
              "title": "Apple to halt sales of iPhone 4S in China (Fame Dubai Blog)",
              "description": "SHANGHAI – Apple Inc said on Friday it will stop selling its latest iPhone in its retail stores in Beijing and Shanghai to ensure the safety of its customers and employees. Go to SourceSource : Fame Dubai BlogExplore : iPhone, iPhone 4, Phone",
              "link": "http://wik.io/info/US/309198933",
              "timestamp": 1326439320,
              "image": null,
              "embed": null,
              "language": null,
              "user": null,
              "user_image": null,
              "user_link": null,
              "user_id": null,
              "geo": null,
              "source": "wikio",
              "favicon": "http://wikio.com/favicon.ico",
              "type": "blogs",
              "domain": "wik.io",
              "id": "16209851193593872066"
            }
          ]
        };

        const items = json3.items
        const replacer = (key, value) => value === null ? '' : value // specify how you want to handle null values here
        const header = Object.keys(items[0])
        let csv = items.map(row => header.map(fieldName => JSON.stringify(row[fieldName], replacer)).join(','))
        csv.unshift(header.join(','))
        csv = csv.join('\r\n')

        var link = document.createElement("a");    
        link.id="lnkDwnldLnk";
        document.body.appendChild(link);
        blob = new Blob([csv], { type: 'text/csv' }); 
        var csvUrl = window.webkitURL.createObjectURL(blob);
        var filename = 'UserExport.csv';
        jQuery("#lnkDwnldLnk")
        .attr({
            'download': filename,
            'href': csvUrl
        });
        jQuery('#lnkDwnldLnk')[0].click();
        document.body.removeChild(link);
    </script>
</body>
</html>

2

การดัดแปลงจากคำตอบของpraneybehl เพื่อทำงานกับวัตถุที่ซ้อนกันและตัวคั่นแท็บ

function ConvertToCSV(objArray) {
  let array = typeof objArray != 'object' ? JSON.parse(objArray) : objArray;
  if(!Array.isArray(array))
      array = [array];

  let str = '';

  for (let i = 0; i < array.length; i++) {
    let line = '';
    for (let index in array[i]) {
      if (line != '') line += ','

      const item = array[i][index];
      line += (typeof item === 'object' && item !== null ? ConvertToCSV(item) : item);
    }
    str += line + '\r\n';
  }

  do{
      str = str.replace(',','\t').replace('\t\t', '\t');
  }while(str.includes(',') || str.includes('\t\t'));

  return str.replace(/(\r\n|\n|\r)/gm, ""); //removing line breaks: https://stackoverflow.com/a/10805198/4508758
}

1
เหมาะสำหรับการคัดลอกและวางลงใน Excel / ชีตโดยตรง! ขอบคุณ!
UP3

1

นี่เป็นวิธีที่ทำได้สำหรับวัตถุที่มีความลึกแบบไดนามิกในลักษณะเชิงวัตถุสำหรับ js เวอร์ชันที่ใหม่กว่า คุณอาจต้องเปลี่ยนประเภทการแยกตามภูมิภาค

private ConvertToCSV(objArray) {
    let rows = typeof objArray !== "object" ? JSON.parse(objArray) : objArray;
    let  header = "";
    Object.keys(rows[0]).map(pr => (header += pr + ";"));

    let str = "";
    rows.forEach(row => {
        let line = "";
        let columns =
            typeof row !== "object" ? JSON.parse(row) : Object.values(row);
        columns.forEach(column => {
            if (line !== "") {
                line += ";";
            }
            if (typeof column === "object") {
                line += JSON.stringify(column);
            }  else {
                line += column;
            }
        });
        str += line + "\r\n";
    });
    return header + "\r\n" + str;
}

1

บางครั้งวัตถุมีความยาวต่างกัน ดังนั้นฉันจึงพบปัญหาเดียวกับ Kyle Pennell แต่แทนที่จะเรียงลำดับอาร์เรย์เราเพียงแค่สำรวจมันและเลือกที่ยาวที่สุด ความซับซ้อนของเวลาจะลดลงเหลือ O (n) เมื่อเทียบกับ O (n log (n)) เมื่อเรียงลำดับก่อน

ฉันเริ่มต้นด้วยรหัสจากเวอร์ชันES6 (2016) ที่อัปเดตของ Christian Landgren

json2csv(json) {
    // you can skip this step if your input is a proper array anyways:
    const simpleArray = JSON.parse(json)
    // in array look for the object with most keys to use as header
    const header = simpleArray.map((x) => Object.keys(x))
      .reduce((acc, cur) => (acc.length > cur.length ? acc : cur), []);

    // specify how you want to handle null values here
    const replacer = (key, value) => (
      value === undefined || value === null ? '' : value);
    let csv = simpleArray.map((row) => header.map(
      (fieldName) => JSON.stringify(row[fieldName], replacer)).join(','));
    csv = [header.join(','), ...csv];
    return csv.join('\r\n');
}

1

ฉันต้องการปิดคำตอบของ @Christian Landgren ข้างต้น ฉันสับสนว่าทำไมไฟล์ CSV ของฉันมีเพียง 3 คอลัมน์ / ส่วนหัว นี่เป็นเพราะองค์ประกอบแรกใน json ของฉันมีเพียง 3 คีย์เท่านั้น ดังนั้นคุณต้องระมัดระวังกับconst header = Object.keys(json[0])เส้น สมมติว่าองค์ประกอบแรกในอาร์เรย์เป็นตัวแทน ฉันมี JSON ที่ยุ่งเหยิงกับวัตถุบางอย่างที่มีมากหรือน้อย

ดังนั้นฉันจึงเพิ่มสิ่งarray.sortนี้ซึ่งจะเรียงลำดับ JSON ตามจำนวนคีย์ ดังนั้นวิธีนี้ไฟล์ CSV ของคุณจะมีจำนวนคอลัมน์สูงสุด

นอกจากนี้ยังเป็นฟังก์ชันที่คุณสามารถใช้ในรหัสของคุณ เพียงแค่ป้อน JSON!

function convertJSONtocsv(json) {
    if (json.length === 0) {
        return;
    }

    json.sort(function(a,b){ 
       return Object.keys(b).length - Object.keys(a).length;
    });

    const replacer = (key, value) => value === null ? '' : value // specify how you want to handle null values here
    const header = Object.keys(json[0])
    let csv = json.map(row => header.map(fieldName => JSON.stringify(row[fieldName], replacer)).join(','))
    csv.unshift(header.join(','))
    csv = csv.join('\r\n')

    fs.writeFileSync('awesome.csv', csv)
}

1

นี่คือเวอร์ชันง่ายๆของฉันในการแปลงอาร์เรย์ของอ็อบเจ็กต์ ito CSV (สมมติว่าอ็อบเจ็กต์เหล่านั้นแชร์แอตทริบิวต์เดียวกันทั้งหมด):

var csv = []
if (items.length) {
  var keys = Object.keys(items[0])
  csv.push(keys.join(','))
  items.forEach(item => {
    let vals = keys.map(key => item[key] || '')
    csv.push(vals.join(','))
  })
}

csv = csv.join('\n') 

0

เขียน Csv

function writeToCsv(dataToWrite, callback) {
    var dataToWrite;
    var fs = require('fs');
    dataToWrite = convertToCSV(dataToWrite);
    fs.writeFile('assets/distanceInfo.csv', dataToWrite, 'utf8', function (err) {
      if (err) {
        console.log('Some error occured - file either not saved or corrupted file saved.');
      } else{
        console.log('It\'s saved!');
      }
      callback("data_saved | assets/distanceInfo.csv")
    });
}

function convertToCSV(objArray) {
    var array = typeof objArray != 'object' ? JSON.parse(objArray) : objArray;
    var str = '';
    for (var i = 0; i < array.length; i++) {
        var line = '';
        for (var index in array[i]) {
            if (line != '') line += ','

            line += array[i][index];
        }
        str += line + '\r\n';
    }
    return str;
}

2
ฉันไม่คิดว่าสิ่งนี้มีค่ามาก โปรดแก้ไขเพื่อเพิ่มคำอธิบายว่าสิ่งนี้ช่วยตอบคำถามได้อย่างไร
fedorqui 'SO หยุดทำร้าย'

0

ตลกดีไม่มีอะไรสมบูรณ์หรือทำงานที่นี่ (IE หรือ node.js) คำตอบสำหรับคำถามที่คล้ายกัน JSON ที่มีโครงสร้างเล็กน้อย (สมมติว่าไม่จำเป็นต้องคัดลอกอีกครั้ง) รวมถึงตัวอย่างข้อมูลสาธิตด้วย การแปลง JSON เป็น CSV (JavaScript): วิธีจัดรูปแบบการแปลง CSV อย่างถูกต้อง หวังว่าจะไม่ใช่แค่ตัวแปลงประเภทเดียวเท่านั้น แต่ใน Github ของฉัน (ที่กล่าวถึงในโปรไฟล์) จะคล้ายกับที่ใช้ในการวิเคราะห์โครงสร้าง JSON ที่ไม่รู้ ฉันเป็นผู้เขียนโค้ดในคำตอบนี้และโค้ดทั้งหมดบน Github ของฉัน (ยกเว้นบางโปรเจ็กต์ที่เริ่มต้นด้วยการแปล fork / +)


0

โดยส่วนตัวฉันจะใช้ห้องสมุดd3-dsvเพื่อทำสิ่งนี้ ทำไมต้องreinvent the wheel?


import { csvFormat } from 'd3-dsv';
/**
 * Based on input data convert it to csv formatted string
 * @param (Array) columnsToBeIncluded array of column names (strings)
 *                which needs to be included in the formated csv
 * @param {Array} input array of object which need to be transformed to string
 */
export function convertDataToCSVFormatString(input, columnsToBeIncluded = []) {
  if (columnsToBeIncluded.length === 0) {
    return csvFormat(input);
  }
  return csvFormat(input, columnsToBeIncluded);
}

ด้วยการเขย่าต้นไม้คุณสามารถนำเข้าฟังก์ชันเฉพาะนั้นจากd3-dsvไลบรารี

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.