简体   繁体   English

如何将本地 JSON 文件中的数据显示到 HTML 表中?

[英]How to display data from local JSON file to HTML table?

I have a local JSON file prices.json that looks like this:我有一个本地 JSON 文件prices.json ,如下所示:

{
  "Company01": {
    "price": "R$600,50",
    "price2": "R$700,40"
  },
  "Company02": {
    "price": "R$800,45",
    "price2": "R$500,22"
  },
}

I need to display those prices in a Table, on my index.html page.我需要在我的 index.html 页面上的表格中显示这些价格。
The HTML code looks like this: HTML 代码如下所示:

<table id="prices-table">
  <tr>
    <th class="company-title">★</th>
    <th class="pagamento-title">PRICE 1</th>
    <th class="pagamento-2-title">PRICE 2</th>
  </tr>
  <tr>
    <td>Company 1</td>
    <td></td>
    <td></td>
  </tr>
  <tr>
    <td>Company 2</td>
    <td></td>
    <td></td>
  </tr>
</table>

I'm not sure how to do it either with JS or jQuery (Which, I guess, would be preferable)我不知道如何用 JS 或 jQuery 来做(我想这会更好)

EDIT: I would prefer to use the table already created using HTML.编辑:我更喜欢使用已经使用 HTML 创建的表。 Most responses focused on creating a table using JS and displaying the JSON values there.大多数响应都集中在使用 JS 创建一个表并在那里显示 JSON 值。 For my case, it would be better to just get those specific JSON values, and display them in the specific <td> .就我而言,最好只获取那些特定的 JSON 值,并将它们显示在特定的<td>中。 I believe I would need to give an id=" to each one of them, but that wouldn't be a problem. I just can't get to the point where I can take, for example, Company01-price2, and display it on the equivalent <td> .我相信我需要给他们每个人一个id=" ,但这不是问题。我只是无法达到我可以采取例如 Company01-price2 并显示它的地步在等效的<td>上。

In modern vanilla JS with comments...在带有评论的现代香草JS中......

The functions below will create an entire HTML table, using the first object to populate the table heading row.下面的函数将创建一个完整的 HTML 表格,使用第一个对象填充表格标题行。 In this way, it assumes that all objects will have the same keys.通过这种方式,它假定所有对象都将具有相同的键。 Once created, the table is appended to the DOM.创建后,该表将附加到 DOM。

The names of the object properties do not need to be known with this approach, and it will support an open-ended number of table rows.使用这种方法不需要知道对象属性的名称,它将支持不限数量的表行。

// fetch JSON - Returns a JS object
async function getPrices () {
    const http = await fetch("prices.json");
    const response = await http.json();
    return response;
};

// read JSON into var
const prices = await getPrices();

// create table - Returns table as DOM object
function createTable() {

    // create table element
    const table = document.createElement("table");
    
    // create the thead element and first row of table headers
    const tableHead = (() => {

        // create table head
        const thead = document.createElement("thead");

        // create header row from properties of first object
        const headerRow = (() => {
            
            // create the <tr> element
            const row = document.createElement("tr");
            
            // iterate through outer object properties
            for (const property in prices) {
                
                // simplify object notation by assigning named variable
                const nestedObj = prices[property];
        
                // iterate through inner object properties
                for (const key in nestedObj) {
                    
                    // simplify object notation by assigning named variable
                    const val = nestedObj[key];

                    // create <th> element
                    const th = document.createElement("th");

                    // set a scope attribute on <th> for better A11Y
                    th.setAttribute("scope", "col");
                    
                    // add text from object keys to <th> element
                    th.innerText = key;

                    // append <th> to <tr>
                    row.appendChild(th)
                    
                }

                // prevent subsequent iterations after the first
                break;
            }

            return row;
            
        })();

        // add the <tr> element to the <thead> element
        thead.appendChild(headerRow);

        return thead;

    })();
    

    // create <tbody> populated with rows
    const tableBody = (() => {
    
        // create <tbody> element
        const tbody = document.createElement("tbody");

        // iterate through outer object properties
        for (const property in prices) {
            
            // simplify object notation by assigning named variable
            const nestedObj = prices[property];

            // create <tr> element for each body row
            const row = document.createElement("tr");
    
            // iterate through inner object properties
            for (const key in nestedObj) {
                
                // simplify object notation by assigning named variable
                const val = nestedObj[key];

                // create <td> element
                const td = document.createElement("td");

                // add the object value to the <td> element
                td.innerText = val;

                // append the <td> element to the <tr>
                row.appendChild(td)
                
            }

            // append each row to the <tbody>
            tbody.appendChild(row)

        }

        return tbody;

    })();

    // append <thead> to <table>
    table.appendChild(tableHead);

    // append <tbody> to <table>
    table.appendChild(tableBody);

    return table
}

// add table to DOM - Returns nothing 
function drawTable() {

    // get the table
    const table = createTable();

    // specify output location
    const destination = document.getElementById("table-wrapper");

    // ouput to DOM
    destination.appendChild(table);
}


drawTable();

It's worth nothing that this task is heavily complicated by the structure of the JSON (which is missing a closing brace in the example).毫无价值的是,这项任务因 JSON 的结构而变得非常复杂(在示例中缺少右大括号)。 Had it been an array of objects, this would have been a much simpler solution.如果它是一个对象数组,这将是一个更简单的解决方案。

Given that this script uses async functions, you'll need to load it using <script type="module"> .鉴于此脚本使用异步函数,您需要使用<script type="module">加载它。

Use <thead> and <tbody> in your table.在表中使用<thead><tbody> PS: <tbody> will be created by the browser anyways, so if you create it it's easier to remove and add data rows without having to tackle with static table headings titles . PS: <tbody>无论如何都会由浏览器创建,因此如果您创建它,则可以更轻松地删除和添加数据行,而无需处理静态表标题标题

<table id="prices-table">
  <thead>
    <tr>
      <th>★</th>
      <th>PRICE 1</th>
      <th>PRICE 2</th>
      </tr>
    </thead>
  <tbody></tbody>
 </table>

You don't need jQuery.你不需要 jQuery。
Create some simple reusable functions to query the DOM and for the Fetch API创建一些简单的可重用函数来查询 DOM 和Fetch API

// DOM utility functions:

const el = (sel, par) => (par || document).querySelector(sel);
const els = (sel, par) => (par || document).querySelector(sel);
const elNew = (tag, prop) => Object.assign(document.createElement(tag), prop);


// Fetch handlers:

const handleError = (res) => { if (!res.ok) throw Error(res.statusText); return res; };
const handleCatch = (err) => { console.error(err); };
const get = (uri, type = "json") => fetch(uri).then(handleError).then(res => res[type]()).catch(handleCatch);


// Task: Company data:

// DOM query the tbody Element:
const elTbody = el("#prices-table tbody");

const populateCompanyData = async () => {

  // Fetch JSON Company data:
  const companyDataResponse = await get("./data.json");

  // If response is undefined — do nothing.
  if (!companyDataResponse) return;

  // create rows
  const elsRows = Object.entries(companyDataResponse).reduce((DF, [key, val]) => {
    const elTR = elNew("TR", {
      innerHTML: `
            <td>${key}</td>
            <td>${val.price}</td>
            <td>${val.price2}</td>
        `
    })
    DF.append(elTR);
    return DF;
  }, new DocumentFragment);

  // Remove old rows
  elTbody.innerHTML = "";

  // Insert new rows
  elTbody.append(elsRows);

};

// Init:
populateCompanyData();

will result in:将导致:

在此处输入图像描述


If you really need to populate already existing rows, then use the same markup with <thead> and <tbody> with your populated rows and cells and use:如果您确实需要填充已经存在的行,请使用与<thead><tbody>相同的标记以及填充的行和单元格并使用:

// ...

// Task: Company data:

// DOM query a NodeList of all the TR elements in tbody:
const elsTr = els("#prices-table tbody tr");

const populateCompanyData = async () => {

  // Fetch JSON Company data:
  const companyDataResponse = await get("./data.json");

  // If response is undefined — do nothing.
  if (!companyDataResponse) return;

  // Populate rows
  Object.entries(companyDataResponse).forEach(([key, val], i) => {
    const elsTd = els("td", elsTr[i]);
    elsTd[0].textContent = key;
    elsTd[1].textContent = val.price;
    elsTd[2].textContent = val.price2;
  });
};

// ...

First parse the JSON into a javascript object:首先将 JSON 解析为 javascript 对象:

const newObject = JSON.parse('{
  "Company01": {
    "price": "R$600,50",
    "price2": "R$700,40"
  },
  "Company02": {
    "price": "R$800,45",
    "price2": "R$500,22"  
}')

Then insert via class or id selector:然后通过类或 id 选择器插入:

$( ".exampleClass" ).append( "<p>"+newObject.Compnay01.price+"</p>" );

if you get some string issue you might need to do this:如果您遇到一些字符串问题,您可能需要这样做:

$( ".exampleClass" ).append( "<p>"+"+newObject.Compnay01.price+"+"</p>" );

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM