การลบ Field Response
การเพิ่ม directive @remove เข้าสู่ GraphQL schema เพื่อลบผลลัพธ์ของ field ออกจาก response
คำอธิบาย
ข้อกำหนดของ GraphQL ระบุว่า response ของ GraphQL ต้องตรงกับรูปร่างของ query อย่างแม่นยำ อย่างไรก็ตาม ในบางสถานการณ์เราอาจต้องการหลีกเลี่ยงการส่ง response ของ field กลับมา เนื่องจาก:
- เราทราบค่านั้นอยู่แล้ว และการไม่ส่งซ้ำสามารถเพิ่มประสิทธิภาพได้
- ค่านั้นมีข้อมูลที่ละเอียดอ่อน (เช่น ข้อมูลรับรองการเข้าสู่ระบบ)
- field ที่ว่างเปล่าสามารถแยกแยะออกจากค่า
nullได้
เมื่อเพิ่ม @remove ไปที่ field นั้นจะไม่ถูกแสดงใน response
ใน query ด้านล่าง (ที่ใช้ extension PHP Functions via Schema และ HTTP Client) เราสร้าง URL สำหรับส่ง HTTP request โดยการเชื่อมต่อ domain ของไซต์และ REST API endpoint เนื่องจากค่าของ "ส่วนประกอบ" เหล่านี้ไม่จำเป็นต้องแสดงใน response เราจึงสามารถ @remove ออกได้:
query {
siteURL: optionValue(name: "siteurl")
@remove
requestURL: _sprintf(
string: "%s/wp-json/wp/v2/comments/11/?_fields=id,content,date",
values: [$__siteURL]
)
@remove
_sendJSONObjectItemHTTPRequest(
input: {
url: $__requestURL
}
)
}...ผลลัพธ์ (สังเกตว่า field siteURL และ requestURL ไม่ปรากฏใน response):
{
"data": {
"_sendJSONObjectItemHTTPRequest": {
"id": 11,
"date": "2020-12-12T04:07:36",
"content": {
"rendered": "<p>Btw, I really like this stuff<\/p>\n"
}
}
}
}เราสามารถบอก directive @remove ให้ลบค่าแบบมีเงื่อนไขได้เช่นกัน หากเงื่อนไขที่กำหนดได้รับการตอบสนอง argument condition รับค่าได้ 3 แบบ:
ALWAYS(ค่าเริ่มต้น): ลบเสมอIS_NULL: ลบเมื่อค่าเป็นnullIS_EMPTY: ลบเมื่อค่าว่างเปล่า
ตัวอย่างเช่น ใน query ด้านล่าง เมื่อโพสต์ไม่มีรูปภาพเด่น field featuredImage จะมีค่าเป็น null โดยการเพิ่ม @remove(condition: IS_NULL) ค่านี้จะไม่ถูกเพิ่มเข้าใน response:
query {
posts {
title
featuredImage @remove(condition: IS_NULL) {
src
}
}
}...ผลลัพธ์:
{
"data": {
"posts": [
{
"title": "Hello world!"
},
{
"title": "Nested mutations are a must have",
"featuredImage": {
"src": "https:\/\/gato-graphql.lndo.site\/wp-content\/uploads\/2022\/05\/graphql-voyager-public.jpg"
}
},
{
"title": "Customize the schema for each client"
}
]
}
}ตัวอย่าง
ลบข้อมูลที่ไม่จำเป็นจาก API ภายนอก
สมมติว่าเราต้องการดึงข้อมูลเฉพาะบางส่วนจาก REST API endpoint ภายนอก และไม่ต้องการข้อมูลส่วนที่เหลือ เราสามารถใช้ @remove เพื่อทำให้ payload ของ response มีขนาดเล็กลง ซึ่งช่วยเพิ่มประสิทธิภาพได้:
- ใช้ field
_sendJSONObjectItemHTTPRequest(จาก extension HTTP Client) เพื่อเชื่อมต่อกับ REST API - ประมวลผลข้อมูลนี้เพื่อดึงข้อมูลที่ต้องการ (ผ่าน Field to Input และ field
_objectPropertyจาก PHP Function via Schema) @removeข้อมูลต้นฉบับจาก REST endpoint ออก
Query นี้รวมทุกอย่างเข้าด้วยกัน:
{
postData: _sendJSONObjectItemHTTPRequest(input: {
url: "https://newapi.getpop.org/wp-json/wp/v2/posts/1"
}) @remove
renderedTitle: _objectProperty(
object: $__postData,
by: {
path: "title.rendered"
}
)
}ใน response ของ query นี้ field postData ถูกลบออกแล้ว:
{
"data": {
"renderedTitle": "Hello world!"
}
}หลีกเลี่ยงการแสดงข้อมูลรับรองของผู้ใช้
ตัวอย่างนี้เชื่อมต่อกับ GitHub API เพื่อดึง artifacts ที่มีอยู่ใน private repository และหลีกเลี่ยงการแสดงข้อมูลรับรองของผู้ใช้ใน response:
query RetrieveGitHubActionArtifacts(
$repoOwner: String!
$repoProject: String!
) {
githubAccessToken: _env(name: "GITHUB_ACCESS_TOKEN")
@remove
# Create the authorization header to send to GitHub
authorizationHeader: _sprintf(
string: "Bearer %s"
# "Field to Input" feature to access value from the field above
values: [$__githubAccessToken]
)
@remove
# Create the authorization header to send to GitHub
githubRequestHeaders: _echo(
value: [
{ name: "Accept", value: "application/vnd.github+json" }
{ name: "Authorization", value: $__authorizationHeader }
]
)
@remove
githubAPIEndpoint: _sprintf(
string: "https://api.github.com/repos/%s/%s/actions/artifacts"
values: [$repoOwner, $repoProject]
)
# Use the field from "Send HTTP Request Fields" to connect to GitHub
gitHubArtifactData: _sendJSONObjectItemHTTPRequest(
input: {
url: $__githubAPIEndpoint
options: { headers: $__githubRequestHeaders }
}
)
}ข้อกำหนดของ GraphQL
ฟังก์ชันนี้ยังไม่ได้เป็นส่วนหนึ่งของข้อกำหนด GraphQL ในปัจจุบัน แต่มีการร้องขอไว้แล้ว: