本文為英文版的機器翻譯版本,如內容有任何歧義或不一致之處,概以英文版為準。
AWS AppSync JavaScript Amazon 的解析器函數參考 RDS
AWS AppSync RDS 函數和解析程式可讓開發人員傳送 SQL 使用 RDS 資料查詢 Amazon Aurora 叢集資料庫,API並傳回這些查詢的結果。您可以寫入 SQL 陳述式,這些陳述式API會使用 AWS AppSyncrds
的模組sql
標籤範本或使用rds
模組的 select
、update
、 insert
和 remove
協助程式函數傳送至資料。 AWS AppSync 會使用 RDS Data Service ExecuteStatement
的動作,針對資料庫執行SQL陳述式。
SQL 標記的範本
AWS AppSync的sql
標記範本可讓您建立靜態陳述式,該陳述式可以使用範本表達式在執行階段接收動態值。 從表達式值 AWS AppSync 建立變數映射,以建構傳送至 Amazon Aurora Serverless Data 的SqlParameterized
查詢API。使用此方法時,執行時傳遞的動態值無法修改原始陳述式,這可能會導致意外執行。所有動態值都會以參數形式傳遞,無法修改原始陳述式,也不會由資料庫執行。這使您的查詢較不容易受到 SQL 注入攻擊。
注意
在所有情況下,寫入時 SQL 陳述式,您應該遵循安全準則,以正確處理作為輸入接收的資料。
注意
sql
標記的範本僅支援傳遞變數值。您不能使用運算式動態指定資料欄或資料表名稱。不過,您可以使用公用程式函數來建置動態陳述式。
在下列範例中,我們會建立查詢,根據執行時間 GraphQL 查詢中動態設定的col
引數值進行篩選。該值只能使用標籤表達式新增至陳述式:
import { sql, createMySQLStatement } from '@aws-appsync/utils/rds'; export function request(ctx) { const query = sql` SELECT * FROM table WHERE column = ${ctx.args.col}` ; return createMySQLStatement(query); }
透過透過變數映射傳遞所有動態值,我們依賴資料庫引擎安全地處理和消毒值。
建立陳述式
函數和解析程式可以與 MySQL 和 PostgreSQL 資料庫互動。createPgStatement
分別使用 createMySQLStatement
和 來建置陳述式。例如, createMySQLStatement
可以建立我的SQL查詢。這些函數最多接受兩個陳述式,當請求應該立即擷取結果時很有用。使用我的 SQL,您可以執行下列動作:
import { sql, createMySQLStatement } from '@aws-appsync/utils/rds'; export function request(ctx) { const { id, text } = ctx.args; const s1 = sql`insert into Post(id, text) values(${id}, ${text})`; const s2 = sql`select * from Post where id = ${id}`; return createMySQLStatement(s1, s2); }
注意
createPgStatement
和 createMySQLStatement
不會逸出或使用sql
標記範本建置的陳述式。
擷取資料
已執行SQL陳述式的結果可在 context.result
物件的回應處理常式中使用。結果是具有來自 ExecuteStatement
動作之回應元素的JSON字串。剖析時,結果具有下列形狀:
type SQLStatementResults = { sqlStatementResults: { records: any[]; columnMetadata: any[]; numberOfRecordsUpdated: number; generatedFields?: any[] }[] }
您可以使用 toJsonObject
公用程式,將結果轉換為代表傳回資料列的JSON物件清單。例如:
import { toJsonObject } from '@aws-appsync/utils/rds'; export function response(ctx) { const { error, result } = ctx; if (error) { return util.appendError( error.message, error.type, result ) } return toJsonObject(result)[1][0] }
請注意, toJsonObject
會傳回陳述式結果的陣列。如果您提供了一個陳述式,則陣列長度為 1
。如果您提供兩個陳述式,則陣列長度為 2
。陣列中的每個結果都包含 0
列或更多列。null
如果結果值無效或非預期, 會toJsonObject
傳回 。
公用程式函數
您可以使用 AWS AppSync RDS模組的公用程式協助程式與資料庫互動。
select
公用程式會建立 SELECT
陳述式來查詢您的關聯式資料庫。
基本使用
以基本形式,您可以指定要查詢的資料表:
import { select, createPgStatement } from '@aws-appsync/utils/rds'; export function request(ctx) { // Generates statement: // "SELECT * FROM "persons" return createPgStatement(select({table: 'persons'})); }
請注意,您也可以在資料表識別碼中指定結構描述:
import { select, createPgStatement } from '@aws-appsync/utils/rds'; export function request(ctx) { // Generates statement: // SELECT * FROM "private"."persons" return createPgStatement(select({table: 'private.persons'})); }
指定資料欄
您可以使用 columns
屬性指定資料欄。如果未將此值設定為 值,則預設為 *
:
export function request(ctx) { // Generates statement: // SELECT "id", "name" // FROM "persons" return createPgStatement(select({ table: 'persons', columns: ['id', 'name'] })); }
您也可以指定資料欄的資料表:
export function request(ctx) { // Generates statement: // SELECT "id", "persons"."name" // FROM "persons" return createPgStatement(select({ table: 'persons', columns: ['id', 'persons.name'] })); }
限制和偏移
您可以套用 limit
和 offset
至查詢:
export function request(ctx) { // Generates statement: // SELECT "id", "name" // FROM "persons" // LIMIT :limit // OFFSET :offset return createPgStatement(select({ table: 'persons', columns: ['id', 'name'], limit: 10, offset: 40 })); }
訂購者
您可以使用 orderBy
屬性排序結果。提供指定資料欄的物件陣列和選用dir
屬性:
export function request(ctx) { // Generates statement: // SELECT "id", "name" FROM "persons" // ORDER BY "name", "id" DESC return createPgStatement(select({ table: 'persons', columns: ['id', 'name'], orderBy: [{column: 'name'}, {column: 'id', dir: 'DESC'}] })); }
篩選條件
您可以使用特殊條件物件建置篩選條件:
export function request(ctx) { // Generates statement: // SELECT "id", "name" // FROM "persons" // WHERE "name" = :NAME return createPgStatement(select({ table: 'persons', columns: ['id', 'name'], where: {name: {eq: 'Stephane'}} })); }
您也可以合併篩選條件:
export function request(ctx) { // Generates statement: // SELECT "id", "name" // FROM "persons" // WHERE "name" = :NAME and "id" > :ID return createPgStatement(select({ table: 'persons', columns: ['id', 'name'], where: {name: {eq: 'Stephane'}, id: {gt: 10}} })); }
您也可以建立OR
陳述式:
export function request(ctx) { // Generates statement: // SELECT "id", "name" // FROM "persons" // WHERE "name" = :NAME OR "id" > :ID return createPgStatement(select({ table: 'persons', columns: ['id', 'name'], where: { or: [ { name: { eq: 'Stephane'} }, { id: { gt: 10 } } ]} })); }
您也可以使用 否定條件not
:
export function request(ctx) { // Generates statement: // SELECT "id", "name" // FROM "persons" // WHERE NOT ("name" = :NAME AND "id" > :ID) return createPgStatement(select({ table: 'persons', columns: ['id', 'name'], where: { not: [ { name: { eq: 'Stephane'} }, { id: { gt: 10 } } ]} })); }
您也可以使用下列運算子來比較值:
運算子 | 描述 | 可能的值類型 |
---|---|---|
eq | 等於 | 數字、字串、布林值 |
ne | 不等於 | 數字、字串、布林值 |
le | 小於或等於 | 數字、字串 |
lt | 小於 | 數字、字串 |
ge | 大於或等於 | 數字、字串 |
gt | 大於 | 數字、字串 |
contains | 就像 | string |
notContains | 不喜歡 | string |
beginsWith | 以字首開頭 | string |
介於 | 在兩個值之間 | 數字、字串 |
attributeExists | 屬性不是 null | 數字、字串、布林值 |
size | 檢查元素的長度 | string |
insert
公用程式提供一種直接的方式,透過 INSERT
操作在資料庫中插入單列項目。
單一項目插入
若要插入項目,請指定資料表,然後傳遞至值的物件。物件索引鍵會映射到您的資料表資料欄。資料欄名稱會自動逸出,並使用變數映射將值傳送至資料庫:
import { insert, createMySQLStatement } from '@aws-appsync/utils/rds'; export function request(ctx) { const { input: values } = ctx.args; const insertStatement = insert({ table: 'persons', values }); // Generates statement: // INSERT INTO `persons`(`name`) // VALUES(:NAME) return createMySQLStatement(insertStatement) }
我的SQL使用案例
您可以結合 insert
後跟 select
來擷取插入的資料列:
import { insert, select, createMySQLStatement } from '@aws-appsync/utils/rds'; export function request(ctx) { const { input: values } = ctx.args; const insertStatement = insert({ table: 'persons', values }); const selectStatement = select({ table: 'persons', columns: '*', where: { id: { eq: values.id } }, limit: 1, }); // Generates statement: // INSERT INTO `persons`(`name`) // VALUES(:NAME) // and // SELECT * // FROM `persons` // WHERE `id` = :ID return createMySQLStatement(insertStatement, selectStatement) }
Postgres 使用案例
透過 Postgres,您可以使用 returning
*
或 欄名稱陣列:
import { insert, createPgStatement } from '@aws-appsync/utils/rds'; export function request(ctx) { const { input: values } = ctx.args; const insertStatement = insert({ table: 'persons', values, returning: '*' }); // Generates statement: // INSERT INTO "persons"("name") // VALUES(:NAME) // RETURNING * return createPgStatement(insertStatement) }
update
公用程式可讓您更新現有的資料列。您可以使用條件物件,將變更套用至滿足條件的所有資料列中的指定資料欄。例如,假設我們有一個結構描述,允許我們產生此突變。我們希望Person
使用 id
的值更新 name
的 ,3
但前提是我們從 開始已知道它們 (known_since
)2000
:
mutation Update { updatePerson( input: {id: 3, name: "Jon"}, condition: {known_since: {ge: "2000"}} ) { id name } }
我們的更新解析程式如下所示:
import { update, createPgStatement } from '@aws-appsync/utils/rds'; export function request(ctx) { const { input: { id, ...values }, condition } = ctx.args; const where = { ...condition, id: { eq: id }, }; const updateStatement = update({ table: 'persons', values, where, returning: ['id', 'name'], }); // Generates statement: // UPDATE "persons" // SET "name" = :NAME, "birthday" = :BDAY, "country" = :COUNTRY // WHERE "id" = :ID // RETURNING "id", "name" return createPgStatement(updateStatement) }
我們可以將檢查新增至我們的條件,以確保僅3
更新具有id
等於 主索引鍵的資料列。同樣地,對於 Postgres inserts
,您可以使用 returning
來傳回修改的資料。
remove
公用程式可讓您刪除現有的資料列。您可以在滿足條件的所有資料列上使用條件物件。請注意, delete
是 中預留的關鍵字 JavaScript。remove
應該改用:
import { remove, createPgStatement } from '@aws-appsync/utils/rds'; export function request(ctx) { const { input: { id }, condition } = ctx.args; const where = { ...condition, id: { eq: id } }; const deleteStatement = remove({ table: 'persons', where, returning: ['id', 'name'], }); // Generates statement: // DELETE "persons" // WHERE "id" = :ID // RETURNING "id", "name" return createPgStatement(updateStatement) }
轉換
在某些情況下,您可能希望在陳述式中使用有關正確物件類型的更具體性。您可以使用提供的類型提示來指定參數的類型。 AWS AppSync 支援與資料 相同的類型提示API。您可以使用模組的 typeHint
函數 AWS AppSync rds
來轉換參數。
下列範例可讓您將陣列傳送為轉換為JSON物件的值。我們使用->
運算子在JSON陣列index
2
中的 擷取 元素:
import { sql, createPgStatement, toJsonObject, typeHint } from '@aws-appsync/utils/rds'; export function request(ctx) { const arr = ctx.args.list_of_ids const statement = sql`select ${typeHint.JSON(arr)}->2 as value` return createPgStatement(statement) } export function response(ctx) { return toJsonObject(ctx.result)[0][0].value }
在處理和比較 DATE
、 和 時TIME
, Casting 也很有用TIMESTAMP
:
import { select, createPgStatement, typeHint } from '@aws-appsync/utils/rds'; export function request(ctx) { const when = ctx.args.when const statement = select({ table: 'persons', where: { createdAt : { gt: typeHint.DATETIME(when) } } }) return createPgStatement(statement) }
以下是另一個範例,示範如何傳送目前的日期和時間:
import { sql, createPgStatement, typeHint } from '@aws-appsync/utils/rds'; export function request(ctx) { const now = util.time.nowFormatted('YYYY-MM-dd HH:mm:ss') return createPgStatement(sql`select ${typeHint.TIMESTAMP(now)}`) }
可用的類型提示
-
typeHint.DATE
- 對應的參數會以DATE
類型的物件傳送至資料庫。接受的格式為YYYY-MM-DD
。 -
typeHint.DECIMAL
- 對應的參數會以DECIMAL
類型的物件形式傳送至資料庫。 -
typeHint.JSON
- 對應的參數會以JSON
類型的物件形式傳送至資料庫。 -
typeHint.TIME
- 對應的字串參數值會以TIME
類型的物件形式傳送至資料庫。接受的格式為HH:MM:SS[.FFF]
。 -
typeHint.TIMESTAMP
- 對應的字串參數值會以TIMESTAMP
類型的物件形式傳送至資料庫。接受的格式為YYYY-MM-DD HH:MM:SS[.FFF]
。 -
typeHint.UUID
- 對應的字串參數值會以UUID
類型的物件形式傳送至資料庫。