การทำงานกับ JSON ใน Power Fx
Power Fx ให้ผู้สร้างสามารถอ่าน JSON ใน ออบเจ็กต์ไม่ระบุชนิด โดยใช้ฟังก์ชัน ParseJSON
การอ่านและการแปลงค่า
ParseJSON จะแปลง JSON สตริงบันทึกต่อไปนี้เป็น ออบเจ็กต์ที่ไม่ได้ระบุชนิด ด้วยฟิลด์ ItemName
, Quantity
, ReleaseDate
และ AvailableForPreOrder
.
{
"ItemName" : "Widget 1",
"Quantity" : 46,
"ReleaseDate" : "2022-09-01",
"AvailableForPreOrder" : true
}
แต่ละฟิลด์สามารถเข้าถึงได้โดยใช้เครื่องหมายจุดในค่า ออบเจ็กต์ไม่ระบุชนิด ที่ส่งคืนจาก ParseJSON
Set( untyped, ParseJSON( jsonStringVariable ) );
Set( item, Text ( untyped.ItemName ) );
Set( quantity, Value ( untyped.Quantity ) );
Set( release, DateValue ( untyped.ReleaseDate ) );
Set( preorder, Boolean ( untyped.AvailableForPreOrder ) );
โดยทั่วไปเป็นความคิดที่ดีที่จะแปลงค่าของออบเจกต์ที่ไม่ได้ระบุชนิดเป็นชนิดเฉพาะอย่างชัดเจน การตั้งค่าออบเจ็กต์ที่ไม่ได้ระบุชนิดเป็นค่าตัวแปรทำให้ตัวแปรเป็น ออบเจ็กต์ที่ไม่ได้ระบุชนิด อีกด้วย ดังนั้น การแปลงค่าดังกล่าวอย่างชัดเจนเมื่อตั้งค่าเป็นตัวแปรจึงมีความจำเป็น แต่ในกรณีส่วนใหญ่ค่าออบเจ็กต์ที่ไม่ได้ระบุชนิดจะแปลงเป็นชนิดเฉพาะโดยอัตโนมัติ ("บังคับ") เมื่อใช้เป็นพารามิเตอร์ของฟังก์ชัน โดยที่ชนิดเป็นชนิดง่ายๆ เช่น บูลีน ตัวเลข หรือข้อความ และโปรไฟล์พารามิเตอร์ของฟังก์ชันไม่มีโอเวอร์โหลดที่ขัดแย้งกัน
Left( untyped.ItemName, 1 ); // "W"
Radians( untyped.Quantity ); // 0.80285146
If (untyped.AvailableForPreOrder, "Available", "Not Available" ); // "Available"
นอกจากการแปลงชนิดโดยอัตโนมัติในการเรียกใช้ฟังก์ชันแล้ว ออบเจ็กต์ที่ไม่ได้ระบุชนิดจะถูกแปลงเมื่อกำหนดให้กับคุณสมบัติการควบคุมด้วย หากเป็นไปได้
Label1.Text: untyped.Quantity
InputText1.Default: untyped.ItemName
และสุดท้าย เมื่อ ใช้ตัวดำเนินการ เช่น & หรือ + จะทำให้ ออบเจ็กต์ที่ไม่ได้ระบุชนิด จะถูกบังคับหากไม่มีความคลุมเครือในชนิดที่คาดหวัง
untyped.Quantity + 1 // result is a number
untyped.ItemName & " (preorder)" // result is text
untyped.Quantity + untyped.Quantity // result is a number
untyped.Quantity & untyped.ItemName // result is text
หมายเหตุ
JSON ไม่มี GUID, สี, เวลา หรือ วันที่และเวลา ประเภท ค่าเหล่านี้แสดงเป็นสตริง หากคุณกำหนดค่าออบเจ็กต์ที่ไม่ได้ระบุชนิด JSON ซึ่งมีวันที่ไปยังคุณสมบัติข้อความโดยตรง ข้อความต้นฉบับของ JSON จะถูกนำไปใช้ สิ่งนี่อาจมีความสำคัญเมื่อต้องจัดการกับโซนเวลา รูปแบบวันที่ เป็นต้น ในกรณีเช่นนี้คุณควรแปลงค่าอย่างชัดเจนโดยใช้ GUID() ColorValue() DateValue() DateTimeValue() เป็นต้น
ในกรณีที่ชื่อฟิลด์ประกอบด้วยชื่อตัวระบุที่ไม่ถูกต้อง ตัวอย่างเช่น เมื่อชื่อฟิลด์เริ่มต้นด้วยตัวเลขหรือมีอักขระที่ไม่ถูกต้อง เช่น ยัติภังค์ คุณสามารถใส่ชื่อฟิลด์ในเครื่องหมายคำพูดเดี่ยว:
untyped.'01'
untyped.'my-field'
Power Fx จะไม่ประเมินการมีอยู่ของฟิลด์จนกว่าสูตรจะทำงาน ซึ่งช่วยให้มีความยืดหยุ่นใน JSON ขาเข้า ตัวอย่างเช่น บางครั้ง JSON ก่อนหน้าอาจมีฟิลด์พิเศษที่ชื่อ Discount
แต่ในตัวอย่างก่อนหน้า ไม่มีฟิลด์นี้ การเขียนสูตรที่ใช้ฟิลด์ Discount
จะไม่ทำให้เกิดข้อผิดพลาดใดๆ ระหว่างขั้นตอนการสร้างแอปหรือเมื่อผู้ใช้ใช้แอป หากฟิลด์หายไปเมื่อสูตรทำงาน ค่าดังกล่าวจะส่งผลในค่า Blank()
หมายเหตุ
JSON รองรับ null
ค่าสำหรับฟิลด์ ค่าเหล่านี้ยังเป็นผลลัพธ์ในค่า Blank() ด้วย ปัจจุบันไม่มีความแตกต่างใน Power Fx ระหว่างฟิลด์ที่หายไปหรือฟิลด์ที่มีค่า null
เมื่อการเข้าถึงฟิลด์ใน ออบเจ็กต์ไม่ระบุชนิด ไม่ได้รับการประเมินเมื่อเขียนสูตร จะไม่มี Intellisense ด้วย ทั้ง JSON และ Power Fx ต้องตรงตามตัวพิมพ์ใหญ่-เล็ก ดังนั้น โปรดระมัดระวังเป็นพิเศษในการเขียนชื่อฟิลด์
ค่า JSON ไม่จำเป็นต้องอยู่ในรูปแบบบันทึก JSON ที่ถูกต้องสามารถเป็นเพียงค่า เช่น "text value"
, true
หรือ 123.456
ในกรณีเช่นนี้ ออบเจ็กต์ไม่ระบุชนิด ที่ ParseJSON ส่งคืนคือค่าของตัวเองและไม่ได้ใช้เครื่องหมายจุด
Set( myText, Boolean( ParseJSON( "true" ) ) );
Set( myNumber, Value( ParseJSON( "123.456" ) ) );
ในที่สุด JSON รองรับเรกคอร์ดที่ซ้อนกัน การแปลง JSON เป็น ออบเจ็กต์ไม่ระบุชนิด ส่งผลให้ออบเจ็กต์ซ้อนกันและสามารถใช้เครื่องหมายจุดเพื่อส่งผ่านลำดับชั้น
{
"Version" : 1,
"RootElement" : {
"Parent" : {
"Name" : "This is the parent",
"Child" : {
"Name" : "This is the child"
}
}
}
}
เมื่อแปลงสตริง JSON นี้เป็นตัวแปร ออบเจ็กต์ไม่ระบุชนิด ที่ชื่อ jsonObject
ฟิลด์สามารถเข้าถึงได้โดยใช้เครื่องหมายจุด
Set( jsonObject, ParseJSON( jsonStringVariable ) );
Set( parentName, Text( jsonObject.RootElement.Parent.Name ) ); // "This is the parent"
Set( childName, Text( jsonObject.RootElement.Parent.Child.Name ) ); // "This is the child"
หากไม่มีฟิลด์ใดในนิพจน์เครื่องหมายจุด จะมีการส่งคืน Blank()
อาร์เรย์และตาราง
JSON สามารถมีอาร์เรย์ของค่าหรือระเบียนได้ อาร์เรย์เหล่านี้สามารถเข้าถึงได้โดยตรงหรือแปลงเป็นตาราง Power Fx
{
"OrderNumber" : "SO000010",
"CustomerID" : "CUST0126",
"OrderLines" : [
{
"Item" : "Widget 1",
"Quantity" : 3
},
{
"Item" : "Widget 2",
"Quantity" : 5
}
]
}
JSON นี้มีเรกคอร์ดที่มีฟิลด์ชื่อ OrderLines
ซึ่งมีอาร์เรย์ของเรกคอร์ด แต่ละเรกคอร์ดมีสองฟิลด์: Item
และ Quantity
ถ้า JSON ถูกแปลงเป็น ออบเจ็กต์ไม่ระบุชนิด โดยใช้ฟังก์ชัน ParseJSON และตั้งค่าเป็นตัวแปรที่ชื่อ jsonOrder
เราสามารถเข้าถึงรายการใบสั่งแต่ละรายการได้หลายวิธี
Set( jsonOrder, ParseJSON( jsonStringVariable ) );
คุณสามารถดึงข้อมูลเรกคอร์ดและค่าแต่ละรายการโดยใช้ฟังก์ชัน Index() ตัวอย่างเช่น ในการรับเรกคอร์ดที่สองในฟิลด์ OrderLines
แล้วเข้าถึงฟิลด์ Quantity
และแปลงเป็นค่า
Set( line2Quantity, Value( Index( jsonOrder.OrderLines, 2 ).Quantity ); // 5
คุณสามารถแปลงอาร์เรย์ของรายการใบสั่งเป็นตารางได้โดยตรง การดำเนินการนี้จะสร้างตารางแบบคอลัมน์เดียวด้วย ออบเจ็กต์ไม่ระบุชนิด ที่แสดงเรกคอร์ด
Set( orderLines, Table( jsonOrder.OrderLines ) );
ตารางแบบคอลัมน์เดียว 'orderLines' มีคอลัมน์ 'Value' ที่แสดง ออบเจ็กต์ไม่ระบุชนิด ในการใช้ฟิลด์ใดๆ จากเรกคอร์ดในตารางนี้ ให้ใช้เครื่องหมายจุดเพื่อเข้าถึงฟิลด์ JSON เฉพาะบน ออบเจ็กต์ไม่ระบุชนิด ในคอลัมน์ Value
Set( jsonRecord, Index( orderLines, 2 ) ); // Get the second record in the table
Set( line2Item, Text( jsonRecord.Value.Item ) ); // "Widget 2"
เพื่อให้การใช้รายการใบสั่งง่ายขึ้นและไม่ยุ่งยากในส่วนอื่นๆ ของแอป คุณสามารถแปลง ออบเจ็กต์ไม่ระบุชนิด ทั้งหมดเป็นชนิดเรกคอร์ดทั้งหมดโดยใช้ฟังก์ชัน ForAll() ให้ ออบเจ็กต์ไม่ระบุชนิด โดยตรงกับ ForAll() หมายความว่าคุณสามารถเข้าถึงฟิลด์ออบเจ็กได้โดยตรง แทนที่จะใช้ฟิลด์ Value
คอลัมน์เดียว
Set( typedOrderLines, ForAll( jsonOrder.OrderLines, { Item : Text( ThisRecord.Item ), Quantity : Value( ThisRecord.Quantity ) } ) );
ตัวแปร typedOrderLines
ใหม่เป็นชนิดสำหรับตาราง Power Fx ที่มีคอลัมน์และค่าต่อไปนี้ทั้งหมด:
Item | ปริมาณ |
---|---|
"วิดเจ็ต 1" | 3 |
"วิดเจ็ต 2" | 5 |
ตัวอย่างก่อนหน้าใช้อาร์เรย์ของเรกคอร์ด แต่ JSON ยังสามารถมีอาร์เรย์ของค่าเพียงอย่างเดียวได้ พิจารณาตัวอย่างต่อไปนี้ซึ่งเป็นสตริง JSON ที่ถูกต้องที่มีอาร์เรย์สามสตริง
[ "First Item", "Second Item", "Third Item"]
เราสามารถดึงข้อมูลหนึ่งในรายการจากอาร์เรย์โดยใช้ฟังก์ชัน Index() และแปลงเป็นข้อความได้
Text( Index( ParseJSON( jsonStringVariable ), 2 ) ) // "Second Item"