shade-sdk
O runtime e o framework dos robôs da ShadeOne. O robô gerado pela plataforma importa este
pacote, na versão fixada pelo requirements.lock da imagem do sandbox, e o robô escrito à mão
importa o mesmo pacote (ADR 019, D1). O import é shade_sdk.
from decimal import Decimal
from pydantic import BaseModel, Field
from shade_sdk import Alvo, Item, Pagina, Retentativa, Robo
class Pedido(BaseModel):
cliente: str = Field(min_length=1)
valor: Decimal = Field(gt=0)
class TelaDePedido(Pagina):
url = "/pedidos/novo" # relativa ao [config] base_url
pronta = Alvo(papel="heading", nome="Novo pedido") # abrir() espera por ela
cliente = Alvo(rotulo="Cliente")
salvar = Alvo(papel="button", nome="Salvar")
class CadastroDePedido(Robo):
chave = ("cliente", "pedido") # a chave de negócio do item
modelo = Pedido # o item inválido fica retido antes de abrir o navegador
retentativas = Retentativa(sistema=3) # erro de sistema repete; negócio nunca
def entrar(self, pagina) -> None: # opcional: ao abrir a sessão e se ela cair
...
def processar(self, item: Item[Pedido], pagina) -> None:
tela = TelaDePedido(pagina)
with item.etapa("preencher"): # tempo, resultado e erro no relatório
tela.abrir()
tela.cliente.fill(item.dados.cliente) # item.dados é o Pedido validado
with item.efetivar("salvar pedido"): # o ensaio para aqui; o real registra antes
tela.salvar.click()
main.py na raiz do projeto: CadastroDePedido.main(). Sem flag, roda em modo real, como o
robô gerado; --rehearsal é o ensaio. A entrada é --input <arquivo>, ou data/input.json
(onde a plataforma a deixa), ou [itens] exemplo do shade.toml: JSON, CSV (o delimitador é
detectado) ou XLSX ([itens] aba escolhe a aba). Planilha chega como texto, e o modelo
converte.
Com [itens] fonte = "fila", o run real pega cada item da fila hospedada pelo executor da
plataforma, um por vez, e o fecha com o desfecho (a chave do item é o id que o servidor
entregou). A queda no meio de um item o devolve pelo efeito: sem efeito, volta para a fila; com
o efeito em voo, fica retido para conferência. --input e o ensaio leem o arquivo (o ensaio
nunca pega item da fila do cliente), e o run real sem o executor e sem --input para com
ErroDeContrato.
Robo(uma lista de itens) eTarefa(uma execução única,executar(item, pagina)).Item:item.dados(a instância domodelo, ou a linha),item["campo"](a linha como veio),item.chave,with item.efetivar(nome),with item.etapa(nome),item.saida(**campos),item.reter(motivo),item.log(texto).modelo = <pydantic.BaseModel>: cada item é validado antes de abrir o navegador; o inválido fica retido com o campo e a regra (sem o valor), e sem item válido o navegador nem abre.Pagina(url,pronta,abrir(),esperar_pronta()) eAlvo(papel=, nome=),Alvo(rotulo=),Alvo(test_id=),Alvo(texto=)e, por último,Alvo(css=): oLocatordo Playwright (tela.salvar.click();tela.salvar.locatoré o cru). Quando a ação falha,ErroDoAlvodiz o alvo, a URL (sem a query), se não achou nada, se achou mais de um (e quais) ou em que elemento caiu, e os candidatos parecidos.diagnosticar(pagina, alvo)dá o mesmo texto sem agir.shade_sdk.entradas.ler_entrada(caminho, aba=None): os itens de um JSON, CSV ou XLSX.Retentativa(sistema=N, espera=Exponencial(base, teto), sessao_perdida="reentrar" | "falhar"): a política por classe de falha. Negócio nunca repete, e nada repete depois do__enter__deefetivar().- O item que falha deixa a tela e o trecho do trace do Playwright em
evidencias/<sha256 da chave>/, com teto por item e por run e os dados do item mascarados (SHADE_MASCARAR_PII=0desliga); o que passa não guarda nada. shade_sdk.http:http.geta qualquer momento;http.post,put,patchedeletesó dentro deefetivar()(fora,ErroDeContrato; no ensaio, nada sai), comIdempotency-Keyderivada da chave do item, do nome da efetivação e da ordem da escrita no bloco (numTarefa, comidempotencia=). Host fora de[hosts] permitidosé recusado antes de qualquer byte, timeout sempre finito, e só repete quando a rede recusou antes do envio.http.NadaSaiu(certamente sem efeito:desfazer_se=(http.NadaSaiu,)devolve o item à fila) ehttp.ResultadoIncerto(pode ter gravado: o item fica retido). É fidelidade, não segurança: na plataforma, quem barra o host é o proxy da allowlist.self.segredo(nome): só a credencial declarada em[credenciais] nomes;self.config: a tabela[config].- Erros:
ErroDeNegocio(não repete),SessaoPerdida(entra de novo e refaz),ErroDeContrato, e os sinaisParadaDoEnsaioeItemRetido(BaseException: umexcept Exceptionnão os engole). shade_sdk.testing:ExecutorLocal(o lado do executor do protocolo, com o robô em subprocesso, eex.fila, a fila hospedada do lado do servidor) epagina_local(um site local que conta os efeitos, do formulário e da API JSON, com aIdempotency-Keyde cada chamada).
O runtime:
shade_sdk.runtime.laco: o laço por item (ledger, retomada, política de retentativa,efetivar, etapas, resumo).shade_sdk.runtime.evidencia: o trace por item, a tela, a máscara e os tetos.shade_sdk.runtime.ledger: identidade do item por chave de negócio, oincertogravado antes de efetivar e o canal do registro com o executor.shade_sdk.runtime.fila: opegare ofecharda fila hospedada, pelo mesmo canal.shade_sdk.runtime.recovery: classificação da falha, sessão perdida e modal inesperado.shade_sdk.runtime.report: relatório HTML da execução e o histórico.shade_sdk.runtime.config:Settingse a carga do.env.shade_sdk.runtime.output: a planilha de saída, com ou sem mascaramento de PII.shade_sdk.runtime.protocolo: o número e o formato do contrato robô ↔ executor, inclusive a entrada (main.py, argv e ambiente).
Testes do pacote: cd sdk && uv run pytest (Chromium do Playwright instalado).
Licença: Apache-2.0.
Metadata
Release files for shade-sdk 0.8.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| shade_sdk-0.8.0-py3-none-any.whl | Python 3 | none | any | Details |
Release files / shade_sdk-0.8.0-py3-none-any.whl
| Download URL | shade_sdk-0.8.0-py3-none-any.whl |
|---|---|
| Size | 101.5 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
860d50b5b3cb892388492f890effc15f9c5ab2f0b841224300ab75e9ac9c8830
|
|
BLAKE2b-256 checksum How to use checksums |
b06ca8927c1eaf18e50c9cbd49688859815c8f67b386b4e0fa323d092f9a6271
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|