Принятие имен и значений полей формы при создании схемы JSON

1

У меня есть форма, которая генерируется ответ JSON, и каждое имя поля (Shopping_Orders_OrderInfo_ContactID) содержит структуру вложенных объектов

так, например, эта часть JSON

 "Shopping": {
  "Orders": {
   "OrderInfo": {
     "OrderNumber": "",

будет построено следующее имя поля

<input type="text" name="Shopping_Orders_OrderInfo_OrderNumber" value="D0102864">

Вот другие поля

 <input type="text" name="Shopping_Orders_OrderInfo_ContactID" value="AS76372">
 <input type="text" name="Shopping_Orders_OrderInfo_OrderDate" value="01/01/2018">
 <input type="text" name="Shopping_Orders_OrderInfo_Billing_BillingID" value="B673472">
 <input type="text" name="Shopping_Orders_OrderInfo_Billing_Name" value="Fred Smith">
 <input type="text" name="Shopping_Orders_OrderInfo_Delivery_DeliveryID" value="D769397">
 <input type="text" name="Shopping_Orders_OrderInfo_Delivery_Name" value="Joe Blogg">
 <input type="text" name="Shopping_Orders_OrderInfo_Discount_DiscountValue" value="10">
 <input type="text" name="Shopping_Orders_OrderInfo_OrderProduct_NumberofItems" value="1">
 <input type="text" name="Shopping_Orders_OrderInfo_OrderProduct_Items_Item_0_ProductID" value="P5763868">
 <input type="text" name="Shopping_Orders_OrderInfo_OrderProduct_Items_Item_0_ItemName" value="Big Blue Box">
 <input type="text" name="Shopping_Orders_OrderInfo_OrderProduct_Items_Item_0_Price" value="10">
 <input type="text" name="Shopping_Orders_OrderInfo_OrderProduct_Items_Item_1_ProductID" value="P57638262">
 <input type="text" name="Shopping_Orders_OrderInfo_OrderProduct_Items_Item_1_ItemName" value="Big Red Box">
 <input type="text" name="Shopping_Orders_OrderInfo_OrderProduct_Items_Item_1_Price" value="20">

Мне нужна функция Javascript, которая будет захватывать вышеуказанные имена полей и их значения и восстанавливать схему JSON, как показано ниже. В основном он смотрит на имя поля и выдает вложенные объекты/массивы и ключи со значениями.

 {
  "Shopping": {
  "Orders": {
   "OrderInfo": {
    "OrderNumber": "D0102864",
    "ContactID": "AS76372",
    "OrderDate": "01/01/2018",
    "Billing": {
     "BillingID": "B673472",
     "Name": "Fred Smith"
     },
    "Delivery": {
    "DeliveryID": "D769397",
     "Name": "Joe Blogg"
     },
     "Discount": {
      "DiscountValue": "10"
      },
     "OrderProduct": {
      "NumberofItems": "2",
       "Items": {
        "Item": [
        {
         "ProductID": "P5763868",
         "ItemName": "Big Blue Box",
         "Price": "10",
         },
        {
         "ProductID": "P57638262",
         "ItemName": "Big Red Box",
         "Price": "20",
        }
      ]
     }
    }
   }
  }
 }
} 

Ниже приведена функция, которая пытается отразить вышеуказанный процесс

function setValue(object, path, value) {
var last = path.pop();

path.reduce((o, k, i, kk) => o[k] = o[k] || (isFinite(i + 1 in kk ? 
kk[i + 1] : last) ? [] : {}), object)[last] = value;
}

function getValues(object) {
function iter(o, p) {
    if (o && typeof o === 'object') {
        Object.keys(o).forEach(k => iter(o[k], p.concat(k)));
    } else {
        result.push([p, o]);
    }
}

var result = [];
iter(object, []);
return result;
 }

//// here im not sure how to grab the fields and values from above 
var object = data['shopping'],
values = getValues(object),
objectFromValues = {};


 values.forEach(([keys, value]) => setValue(objectFromValues, keys, value));

  console.log(objectFromValues);
  console.log(values)
Теги:
forms

1 ответ

0
Лучший ответ

Вы можете взять все элементы ввода и взять имя и разделить его подчеркиванием для пути нового объекта и значения и построить новый объект с данной информацией.

allInputs - это массив, подобный объекту, который итерабелен, заимствуя метод массива.

В setValue обратный вызов уменьшения проверяет, является ли следующий ключ setValue числовым значением и принимает массив как объект по умолчанию вместо объекта.

function setValue(object, path, value) {
    var last = path.pop();

    path.reduce((o, k, i, kk) => o[k] = o[k] || (isFinite(i + 1 in kk ? kk[i + 1] : last) ? [] : {}), object)[last] = value;
}

var object = {},
    allInputs = document.getElementsByTagName('input');

Array.prototype.forEach.call(allInputs, ({ name, value }) => setValue(object, name.split('_'), value));

console.log(object);
<input type="text" name="Shopping_Orders_OrderInfo_OrderNumber" value="D0102864">
<input type="text" name="Shopping_Orders_OrderInfo_ContactID" value="AS76372">
<input type="text" name="Shopping_Orders_OrderInfo_OrderDate" value="01/01/2018">
<input type="text" name="Shopping_Orders_OrderInfo_Billing_BillingID" value="B673472">
<input type="text" name="Shopping_Orders_OrderInfo_Billing_Name" value="Fred Smith">
<input type="text" name="Shopping_Orders_OrderInfo_Delivery_DeliveryID" value="D769397">
<input type="text" name="Shopping_Orders_OrderInfo_Delivery_Name" value="Joe Blogg">
<input type="text" name="Shopping_Orders_OrderInfo_Discount_DiscountValue" value="10">
<input type="text" name="Shopping_Orders_OrderInfo_OrderProduct_NumberofItems" value="1">
<input type="text" name="Shopping_Orders_OrderInfo_OrderProduct_Items_Item_0_ProductID" value="P5763868">
<input type="text" name="Shopping_Orders_OrderInfo_OrderProduct_Items_Item_0_ItemName" value="Big Blue Box">
<input type="text" name="Shopping_Orders_OrderInfo_OrderProduct_Items_Item_0_Price" value="10">
<input type="text" name="Shopping_Orders_OrderInfo_OrderProduct_Items_Item_1_ProductID" value="P57638262">
<input type="text" name="Shopping_Orders_OrderInfo_OrderProduct_Items_Item_1_ItemName" value="Big Red Box">
<input type="text" name="Shopping_Orders_OrderInfo_OrderProduct_Items_Item_1_Price" value="20">
  • 0
    Brilliant! Большое спасибо, Нина. Несколько часов пытались заставить его работать правильно. Я собираюсь выбрать это как лучший ответ прямо сейчас! Одна крошечная мысль, Shopping_Orders_OrderInfo_OrderProduct_NumberofItems на самом деле не будет полем, она просто увеличивается в зависимости от количества элементов в массиве Item ": [{

Ещё вопросы

Сообщество Overcoder
Наверх
Меню