As traduções são geradas por tradução automática. Em caso de conflito entre o conteúdo da tradução e da versão original em inglês, a versão em inglês prevalecerá.
AWS AppSync JavaScript referência da função de resolução para Amazon RDS
A AWS AppSync RDS função e o resolvedor permitem que os desenvolvedores enviem SQL consulta um banco de dados de cluster do Amazon Aurora usando RDS os API dados e recupera o resultado dessas consultas. Você pode escrever SQL declarações que são enviadas aos Dados API usando o modelo sql
marcado com o rds
módulo AWS AppSync do ou usando as funções remove
auxiliaresselect
, insert
update
, e do rds
módulo. AWS AppSync utiliza a ExecuteStatement
ação do Serviço de RDS Dados para executar SQL instruções no banco de dados.
Tópicos
SQLmodelo marcado
AWS AppSync O modelo sql
marcado permite que você crie uma declaração estática que pode receber valores dinâmicos em tempo de execução usando expressões de modelo. AWS AppSync cria um mapa variável a partir dos valores da expressão para criar uma SqlParameterized
consulta que é enviada aos dados sem servidor do Amazon Aurora. API Com esse método, não é possível que valores dinâmicos transmitidos em runtime modifiquem a declaração original, o que pode causar uma execução não intencional. Todos os valores dinâmicos são transmitidos como parâmetros, não podem modificar a declaração original e não são executados pelo banco de dados. Isso torna sua consulta menos vulnerável a SQL ataques de injeção.
nota
Em todos os casos, ao escrever SQL declarações, você deve seguir as diretrizes de segurança para lidar adequadamente com os dados que você recebe como entrada.
nota
O modelo marcado com sql
só aceita a transmissão de valores de variáveis. Não é possível usar uma expressão para especificar dinamicamente nomes de colunas ou de tabelas. No entanto, é possível usar funções de utilitário para criar declarações dinâmicas.
No exemplo a seguir, criamos uma consulta que filtra com base no valor do argumento col
definido dinamicamente na consulta do GraphQL em runtime. O valor só pode ser adicionado à declaração usando a expressão de tag:
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); }
Ao transmitir todos os valores dinâmicos pelo mapa de variáveis, contamos com o mecanismo de banco de dados para processar e higienizar os valores com segurança.
Criar declarações
Funções e resolvedores podem interagir com os bancos de dados My SQL e PostgreSQL. Use createMySQLStatement
e createPgStatement
, respectivamente, para criar declarações. Por exemplo, createMySQLStatement
pode criar uma Minha SQL consulta. Essas funções aceitam até duas declarações, o que é útil quando uma solicitação deve recuperar os resultados imediatamente. Com o MySQL, você pode fazer:
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); }
nota
createPgStatement
e createMySQLStatement
não inserem caracteres de escape nem citam declarações criadas com o modelo marcado com sql
.
Recuperação de dados
O resultado da SQL instrução executada está disponível em seu manipulador de respostas no context.result
objeto. O resultado é uma JSON string com os elementos de resposta da ExecuteStatement
ação. Quando analisado, o resultado tem o seguinte formato:
type SQLStatementResults = { sqlStatementResults: { records: any[]; columnMetadata: any[]; numberOfRecordsUpdated: number; generatedFields?: any[] }[] }
Você pode usar o toJsonObject
utilitário para transformar o resultado em uma lista de JSON objetos representando as linhas retornadas. Por exemplo:
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] }
Observe que o toJsonObject
exibe uma matriz de resultados das declarações. Se você forneceu uma declaração, o tamanho da matriz será 1
. Se você forneceu duas declarações, o tamanho da matriz será 2
. Cada resultado na matriz contém 0
ou mais linhas. toJsonObject
exibirá null
se o valor do resultado for inválido ou inesperado.
Funções do utilitário
Você pode usar os auxiliares utilitários do AWS AppSync RDS módulo para interagir com seu banco de dados.
O utilitário select
cria uma declaração SELECT
para consultar o banco de dados relacional.
Uso básico
Na forma básica, é possível especificar a tabela que deseja consultar:
import { select, createPgStatement } from '@aws-appsync/utils/rds'; export function request(ctx) { // Generates statement: // "SELECT * FROM "persons" return createPgStatement(select({table: 'persons'})); }
Observe também que é possível especificar o esquema no identificador da tabela:
import { select, createPgStatement } from '@aws-appsync/utils/rds'; export function request(ctx) { // Generates statement: // SELECT * FROM "private"."persons" return createPgStatement(select({table: 'private.persons'})); }
Especificar colunas
É possível especificar colunas com a propriedade columns
. Se isso não for definido como um valor, o padrão será *
:
export function request(ctx) { // Generates statement: // SELECT "id", "name" // FROM "persons" return createPgStatement(select({ table: 'persons', columns: ['id', 'name'] })); }
Também é possível especificar a tabela de uma coluna:
export function request(ctx) { // Generates statement: // SELECT "id", "persons"."name" // FROM "persons" return createPgStatement(select({ table: 'persons', columns: ['id', 'persons.name'] })); }
Limites e deslocamentos:
É possível aplicar limit
e offset
à consulta:
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 })); }
Ordenar por
É possível classificar os resultados com a propriedade orderBy
. Forneça uma matriz de objetos especificando a coluna e uma propriedade dir
opcional:
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'}] })); }
Filtros
É possível criar filtros usando o objeto de condição especial:
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'}} })); }
Também é possível combinar filtros:
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}} })); }
Também é possível criar declarações 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 } } ]} })); }
Também é possível negar uma condição com 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 } } ]} })); }
Também é possível usar os seguintes operadores para comparar valores:
Operador | Descrição | Tipos de valores possíveis |
---|---|---|
eq | Equal | número, string, booleano |
um | Not equal | número, string, booleano |
le | Menor ou igual a | número, seqüência |
lt | Menor que | número, seqüência |
idade | Maior ou igual a | número, seqüência |
gt | Maior que | número, seqüência |
contém | Como | string |
notContains | Não é como | string |
beginsWith | Começa com o prefixo | string |
entre | Entre dois valores | número, seqüência |
attributeExists | O atributo não é nulo | número, string, booleano |
tamanho | verifica o comprimento do elemento | string |
O utilitário insert
oferece uma maneira simples de inserir itens de linha única no banco de dados com a operação INSERT
.
Inserções de item único
Para inserir um item, especifique a tabela e, depois, transmita o objeto de valores. As chaves do objeto são associadas às colunas da tabela. São inseridos automaticamente caracteres de escape nos nomes das colunas e os valores são enviados ao banco de dados usando o mapa de variáveis:
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) }
Meu caso SQL de uso
É possível combinar um insert
seguido por um select
para recuperar a linha inserida:
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) }
Caso de uso do Postgres
Com o Postgres, é possível usar returning
*
ou uma matriz de nomes de colunas:
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) }
O utilitário update
permite atualizar as linhas existentes. É possível usar o objeto de condição para aplicar alterações às colunas especificadas em todas as linhas que atendam à condição. Por exemplo, digamos que temos um esquema que nos permita fazer essa mutação. Queremos atualizar o name
de Person
com o valor id
de 3
, mas somente se os conhecermos (known_since
) desde o ano 2000
:
mutation Update { updatePerson( input: {id: 3, name: "Jon"}, condition: {known_since: {ge: "2000"}} ) { id name } }
Nosso resolvedor de atualização é semelhante a:
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) }
Podemos adicionar uma verificação à nossa condição para garantir que somente a linha que tem a chave primária id
igual a 3
seja atualizada. Da mesma forma, para Postgres inserts
, é possível usar returning
para exibir os dados modificados.
O utilitário remove
permite excluir as linhas existentes. É possível usar o objeto de condição em todas as linhas que atendam à condição. Observe que delete
é uma palavra-chave reservada em JavaScript. remove
deve ser usado em vez disso:
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) }
Conversão
Em alguns casos, convém ter maior especificidade sobre o tipo de objeto correto a ser usado na declaração. Você pode usar as dicas de tipo fornecidas para especificar o tipo dos seus parâmetros. AWS AppSync suporta o mesmo tipo de dicas que o DataAPI. Você pode converter seus parâmetros usando as typeHint
funções do AWS AppSync rds
módulo.
O exemplo a seguir permite que você envie uma matriz como um valor que é convertido como um JSON objeto. Usamos o ->
operador para recuperar o elemento index
2
na JSON matriz:
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 }
A conversão também é útil ao processar e comparar DATE
, TIME
e 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) }
Veja outro exemplo de como enviar a data e a hora atuais:
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)}`) }
Dicas de tipo disponíveis
-
typeHint.DATE
: o parâmetro correspondente é enviado como objeto do tipoDATE
ao banco de dados. O formato aceito éYYYY-MM-DD
. -
typeHint.DECIMAL
: o parâmetro correspondente é enviado como objeto do tipoDECIMAL
ao banco de dados. -
typeHint.JSON
: o parâmetro correspondente é enviado como objeto do tipoJSON
ao banco de dados. -
typeHint.TIME
: o valor de parâmetro de string correspondente é enviado como objeto do tipoTIME
ao banco de dados. O formato aceito éHH:MM:SS[.FFF]
. -
typeHint.TIMESTAMP
: o valor de parâmetro de string correspondente é enviado como objeto do tipoTIMESTAMP
ao banco de dados. O formato aceito éYYYY-MM-DD HH:MM:SS[.FFF]
. -
typeHint.UUID
: o valor de parâmetro de string correspondente é enviado como objeto do tipoUUID
ao banco de dados.