AWS AppSync JavaScript Amazon 的解析器函數參考 RDS - AWS AppSync

本文為英文版的機器翻譯版本,如內容有任何歧義或不一致之處,概以英文版為準。

AWS AppSync JavaScript Amazon 的解析器函數參考 RDS

AWS AppSync RDS 函數和解析程式可讓開發人員傳送 SQL 使用 RDS 資料查詢 Amazon Aurora 叢集資料庫,API並傳回這些查詢的結果。您可以寫入 SQL 陳述式,這些陳述式API會使用 AWS AppSyncrds的模組sql標籤範本或使用rds模組的 selectupdateinsertremove 協助程式函數傳送至資料。 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); }
注意

createPgStatementcreateMySQLStatement不會逸出或使用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'] })); }

限制和偏移

您可以套用 limitoffset至查詢:

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_since2000

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陣列index2中的 擷取 元素:

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類型的物件形式傳送至資料庫。