如何在JS中从多层嵌套JSON提取指定SKU属性值数组
问题
我有一个嵌套结构的JSON对象,需要提取其中shipping和downloads模块下line_items数组中的sku属性值,组成结果数组。尝试用JS的filter或map函数高效实现,但不清楚如何迭代多层嵌套数组。
原始JSON对象:
{"id": 103,"consignments": [{"pickups": [],"shipping": [{"id": 4,"first_name": "Sabareesh","line_items": [{"id": 5,"order_id": 103,"product_id": 86,"variant_id": 66,"order_pickup_method_id": 0,"order_address_id": 4,"name": "[Sample] Able Brewing System","name_customer": "[Sample] Able Brewing System","name_merchant": "[Sample] Able Brewing System","sku": "ABS","upc": "","type": "physical","base_price": "225.0000","price_ex_tax": "225.0000","price_inc_tax": "270.0000","price_tax": "45.0000","base_total": "225.0000","total_ex_tax": "225.0000","total_inc_tax": "270.0000","total_tax": "45.0000","weight": "1.0000","width": "10.0000","height": "10.0000","depth": "10.0000","quantity": 1,"base_cost_price": "0.0000","cost_price_inc_tax": "0.0000","cost_price_ex_tax": "0.0000","cost_price_tax": "0.0000","is_refunded": false,"quantity_refunded": 0,"refund_amount": "0.0000","return_id": 0,"wrapping_id": 0,"wrapping_name": "","base_wrapping_cost": "0.0000","wrapping_cost_ex_tax": "0.0000","wrapping_cost_inc_tax": "0.0000","wrapping_cost_tax": "0.0000","wrapping_message": "","quantity_shipped": 0,"event_name": null,"event_date": "","fixed_shipping_cost": "0.0000","ebay_item_id": "","ebay_transaction_id": "","option_set_id": null,"parent_order_product_id": null,"is_bundled_product": false,"bin_picking_number": "","external_id": null,"fulfillment_source": "","brand": "","gift_certificate_id": null,"applied_discounts": [],"product_options": [],"configurable_fields": [],"discounted_total_inc_tax": "270.0000"},{"id": 14,"order_id": 103,"product_id": 94,"variant_id": 68,"order_pickup_method_id": 0,"order_address_id": 4,"name": "[Sample] Oak Cheese Grater","name_customer": "[Sample] Oak Cheese Grater","name_merchant": "[Sample] Oak Cheese Grater","sku": "OCG","upc": "","type": "physical","base_price": "31.4600","price_ex_tax": "31.4600","price_inc_tax": "37.7500","price_tax": "6.2900","base_total": "31.4600","total_ex_tax": "31.4600","total_inc_tax": "37.7500","total_tax": "6.2900","weight": "1.0000","width": "0.0000","height": "0.0000","depth": "0.0000","quantity": 1,"base_cost_price": "0.0000","cost_price_inc_tax": "0.0000","cost_price_ex_tax": "0.0000","cost_price_tax": "0.0000","is_refunded": false,"quantity_refunded": 0,"refund_amount": "0.0000","return_id": 0,"wrapping_id": 0,"wrapping_name": "","base_wrapping_cost": "0.0000","wrapping_cost_ex_tax": "0.0000","wrapping_cost_inc_tax": "0.0000","wrapping_cost_tax": "0.0000","wrapping_message": "","quantity_shipped": 0,"event_name": null,"event_date": "","fixed_shipping_cost": "0.0000","ebay_item_id": "","ebay_transaction_id": "","option_set_id": null,"parent_order_product_id": null,"is_bundled_product": false,"bin_picking_number": "","external_id": null,"fulfillment_source": "","brand": "Sagaform","gift_certificate_id": null,"applied_discounts": [],"product_options": [],"configurable_fields": [],"discounted_total_inc_tax": "37.7500"}],"items_total": 2,"items_shipped": 0,"shipping_method": "Free Shipping","base_cost": 0,"cost_ex_tax": 0,"cost_inc_tax": 0,"cost_tax": 0,"cost_tax_class_id": 2,"base_handling_cost": 0,"handling_cost_ex_tax": 0,"handling_cost_inc_tax": 0,"handling_cost_tax": 0,"handling_cost_tax_class_id": 2,"shipping_zone_id": 2,"shipping_zone_name": "Qatar"}],"downloads": [{"line_items": [{"id": 15,"order_id": 103,"product_id": 104,"variant_id": 72,"order_pickup_method_id": 0,"order_address_id": 0,"name": "[Sample] Utility Caddy","name_customer": "[Sample] Utility Caddy","name_merchant": "[Sample] Utility Caddy","sku": "OFSUC","upc": "","type": "digital","base_price": "41.3600","price_ex_tax": "41.3600","price_inc_tax": "49.6300","price_tax": "8.2700","base_total": "41.3600","total_ex_tax": "41.3600","total_inc_tax": "49.6300","total_tax": "8.2700","weight": "0.0000","width": "0.0000","height": "0.0000","depth": "0.0000","quantity": 1,"base_cost_price": "0.0000","cost_price_inc_tax": "0.0000","cost_price_ex_tax": "0.0000","cost_price_tax": "0.0000","is_refunded": false,"quantity_refunded": 0,"refund_amount": "0.0000","return_id": 0,"wrapping_id": 0,"wrapping_name": "","base_wrapping_cost": "0.0000","wrapping_cost_ex_tax": "0.0000","wrapping_cost_inc_tax": "0.0000","wrapping_cost_tax": "0.0000","wrapping_message": "","quantity_shipped": 0,"event_name": null,"event_date": "","fixed_shipping_cost": "0.0000","ebay_item_id": "","ebay_transaction_id": "","option_set_id": null,"parent_order_product_id": null,"is_bundled_product": false,"bin_picking_number": "","external_id": null,"fulfillment_source": "","brand": "OFS","gift_certificate_id": null,"applied_discounts": [],"product_options": [],"configurable_fields": [],"discounted_total_inc_tax": "49.6300"}]}],"email": {"gift_certificates": []}}]}
解决方案
可以通过多层数组迭代结合属性提取的方式实现,以下是两种简洁高效的写法:
方法1:链式使用flatMap提取
flatMap能同时完成数组映射和扁平化操作,逐层遍历嵌套结构并提取sku:
// 假设JSON已解析为变量orderData const skus = [ // 提取shipping模块下的sku ...orderData.consignments.flatMap(cons => cons.shipping.flatMap(ship => ship.line_items.map(item => item.sku)) ), // 提取downloads模块下的sku ...orderData.consignments.flatMap(cons => cons.downloads.flatMap(down => down.line_items.map(item => item.sku)) ) ]; console.log(skus); // 输出: ["ABS", "OCG", "OFSUC"]
方法2:合并数据源后统一处理
先将shipping和downloads的line_items合并为一个数组,再批量提取sku:
// 合并所有line_items const allLineItems = orderData.consignments.flatMap(cons => [ ...cons.shipping.flatMap(ship => ship.line_items), ...cons.downloads.flatMap(down => down.line_items) ]); // 提取所有sku const skus = allLineItems.map(item => item.sku); console.log(skus); // 输出: ["ABS", "OCG", "OFSUC"]
兼容说明
如果需要兼容不支持flatMap的旧环境,可以用map配合数组展开实现扁平化:
// 替代flatMap的写法:map + 展开 const shippingSkus = [].concat(...orderData.consignments.map(cons => [].concat(...cons.shipping.map(ship => ship.line_items.map(item => item.sku))) ));
预期结果
["ABS", "OCG", "OFSUC"]
内容的提问来源于stack exchange,提问作者Sabareesh
相关产品推荐
相关产品推荐

