FastAPI para Banco de Dados Relacional
O gerador connection conecta um FastAPI a um projeto de Banco de Dados Relacional Python, injetando uma sessão SQLModel tipada em seus manipuladores de rota via uma dependência FastAPI.
Pré-requisitos
Seção intitulada “Pré-requisitos”Antes de usar este gerador, certifique-se de ter:
Executar o Gerador
Seção intitulada “Executar o Gerador”Execute este gerador@aws/nx-plugin:connection
pnpm nx g @aws/nx-plugin:connection yarn nx g @aws/nx-plugin:connection npx nx g @aws/nx-plugin:connection bunx nx g @aws/nx-plugin:connection- Instale o Nx Console VSCode Plugin se ainda não o fez
- Abra o console Nx no VSCode
- Clique em
Generate (UI)na seção "Common Nx Commands" - Procure por
@aws/nx-plugin - connection - Preencha os parâmetros obrigatórios
- Clique em
Generate
Monte seu comando5
Obrigatório
Obrigatório
Selecione seu projeto FastAPI como origem e seu projeto de banco de dados relacional como destino.
sourceProjectObrigatóriostringO projeto de origem
targetProjectObrigatóriostringO projeto de destino para conectar
sourceComponentstringO componente de origem a partir do qual conectar (nome do componente, caminho relativo à raiz do projeto de origem, ou id do gerador). Use '.' para selecionar explicitamente o projeto como origem.
targetComponentstringO componente de destino ao qual conectar (nome do componente, caminho relativo à raiz do projeto de destino, ou id do gerador). Use '.' para selecionar explicitamente o projeto como destino.
preferInstallDependenciesbooleanPadrão:trueSe deve preferir instalar dependências após a execução do gerador. Defina como false para adiar a instalação ao executar múltiplos geradores em lote (uma instalação ainda é executada se necessário para que os geradores subsequentes possam calcular o grafo de projetos Nx); instale uma vez no final.
Saída do Gerador
Seção intitulada “Saída do Gerador”O gerador modifica seu projeto FastAPI:
Directorypackages/my_api
- project.json Adiciona uma dependência de
devno targetdevdo banco de dados - pyproject.toml Adiciona o pacote do banco de dados como uma dependência de workspace
Directorymy_api
Directorydependencies
- my_db.py Dependência FastAPI
MyDbSessionpara a sessão do banco de dados
- my_db.py Dependência FastAPI
- project.json Adiciona uma dependência de
Usando o Banco de Dados em Manipuladores de Rota
Seção intitulada “Usando o Banco de Dados em Manipuladores de Rota”Este gerador configura uma Dependência FastAPI injetável que você pode usar em seus manipuladores de rota:
from sqlmodel import selectfrom my_api.dependencies.my_db import MyDbSessionfrom my_scope_my_db.models.example import ExampleModel
@app.get("/examples")async def list_examples(my_db: MyDbSession): return (await my_db.execute(select(ExampleModel))).scalars().all()
@app.post("/examples")async def create_example(name: str, my_db: MyDbSession): item = ExampleModel(name=name) my_db.add(item) await my_db.commit() await my_db.refresh(item) return itemO FastAPI abre automaticamente uma nova sessão por requisição e a fecha quando o manipulador retorna.
Infraestrutura
Seção intitulada “Infraestrutura”Para permitir que a função Lambda FastAPI se conecte ao banco de dados em tempo de execução, ela deve ser implantada na mesma VPC que o banco de dados e receber acesso de rede e IAM.
Em sua pilha de aplicação, implante a API na mesma VPC que o banco de dados, depois chame allowDefaultPortFrom e grantConnect para abrir o caminho de rede e conceder permissão IAM rds-db:connect ao manipulador Lambda:
import { MyDatabase } from '@my-scope/common-constructs';
const db = new MyDatabase(this, 'Db', { vpc, ... });
const api = new MyApi(this, 'Api', { integrations: MyApi.defaultIntegrations(this) .withDefaultOptions({ vpc, vpcSubnets: { subnetType: SubnetType.PRIVATE_WITH_EGRESS }, }) .build(),});
Object.entries(api.integrations).forEach(([operation, integration]) => { db.allowDefaultPortFrom(integration.handler, `Allow ${operation} to connect to the database`); db.grantConnect(integration.handler);});Implante as funções Lambda da API em uma sub-rede privada com saída, não em uma sub-rede privada isolada. Em tempo de execução, session_context() recupera a configuração do banco de dados do AWS AppConfig, que é um endpoint de serviço AWS público que requer acesso à internet de saída.
Implante a API na mesma VPC que o banco de dados, conceda a ela rds-db:connect via additional_iam_policy_statements, e abra o caminho de rede com um par de regras de grupo de segurança:
O exemplo abaixo referencia os recursos VPC do guia de implantação do Banco de Dados Relacional Python: as sub-redes aws_subnet.database não têm rota de internet, enquanto as sub-redes aws_subnet.private têm saída NAT.
module "my_database" { source = "../../common/terraform/src/app/dbs/my-database" vpc_id = aws_vpc.main.id database_subnet_ids = aws_subnet.database[*].id lambda_subnet_ids = aws_subnet.private[*].id}
module "api" { source = "../../common/terraform/src/app/apis/my-api" enable_vpc = true vpc_id = aws_vpc.main.id subnet_ids = aws_subnet.private[*].id
appconfig_application_id = module.runtime_config_appconfig.application_id appconfig_application_arn = module.runtime_config_appconfig.application_arn
additional_iam_policy_statements = [ { Effect = "Allow" Action = ["rds-db:connect"] Resource = [ "arn:aws:rds-db:${data.aws_region.current.region}:${data.aws_caller_identity.current.account_id}:dbuser:${module.my_database.connect_resource_id}/${module.my_database.database_runtime_user}" ] } ]}
resource "aws_vpc_security_group_ingress_rule" "api_to_database" { description = "Allow the API Lambda functions to connect to the database" security_group_id = module.my_database.security_group_id referenced_security_group_id = module.api.security_group_id from_port = module.my_database.cluster_port to_port = module.my_database.cluster_port ip_protocol = "tcp"}
resource "aws_vpc_security_group_egress_rule" "api_to_database" { description = "Allow outbound traffic from the API Lambda functions to the database" security_group_id = module.api.security_group_id referenced_security_group_id = module.my_database.security_group_id from_port = module.my_database.cluster_port to_port = module.my_database.cluster_port ip_protocol = "tcp"}Implante as funções Lambda da API em sub-redes privadas com saída, não em sub-redes privadas isoladas. appconfig_application_id/appconfig_application_arn vêm da aplicação AppConfig de configuração de tempo de execução compartilhada declarada uma vez em seu módulo raiz, não do módulo do banco de dados — passá-los define RUNTIME_CONFIG_APP_ID nas funções Lambda e concede a elas acesso de leitura à aplicação.
A aplicação AppConfig expõe o namespace database por padrão, então a entrada de configuração de tempo de execução do módulo do banco de dados é implantada sem configuração adicional.
Requisitos SSL ao Conectar Sem RDS Proxy
Seção intitulada “Requisitos SSL ao Conectar Sem RDS Proxy”O armazenamento de confiança de CA integrado do ambiente de execução Lambda do Amazon Linux 2023 inclui os Amazon Root CAs usados pelo RDS, portanto nenhuma configuração adicional é necessária.
Ao usar RDS Proxy, você não precisa configurar o pacote de CA do RDS em sua função Lambda.
Desenvolvimento Local
Seção intitulada “Desenvolvimento Local”pnpm nx dev <project-name>yarn nx dev <project-name>npx nx dev <project-name>bunx nx dev <project-name>Isso inicia o FastAPI e todos os bancos de dados conectados. A variável de ambiente LOCAL_DEV=true faz com que o cliente do banco de dados se conecte ao seu banco de dados Docker local em vez do Aurora.