Connectors¶
Um connector representa a integracao com um servico externo: gateways de pagamento, APIs de terceiros, plataformas de analytics, bridges com outros LMS. O MIDDAG fornece um modelo padronizado para credenciais, health check e registro de tipos.
O sistema de connectors e a Core Capability CC-02 (core.connectors) do framework (ADR-607).
Conceito¶
Connectors resolvem tres problemas:
- Catalogo padronizado -- a plataforma sabe quais servicos externos estao disponiveis e em que estado.
- Credenciais declarativas -- cada connector declara os campos necessarios para configuracao, sem hardcoding.
- Health check uniforme -- monitoramento de conectividade integrado ao framework.
Quick example¶
Implementar um connector para enviar SMS via Twilio:
namespace local_meuplugin\extensions\notifications\connector;
use local_middag\framework\contract\connector_interface;
final class twilio_connector implements connector_interface
{
public function __construct(
private readonly string $account_sid,
private readonly string $auth_token,
private readonly string $from_number,
) {}
public function get_type(): string
{
return 'twilio';
}
public function get_name(): string
{
return 'Twilio SMS';
}
public function get_extension(): string
{
return 'notifications';
}
public function health_check(): bool
{
try {
// Tenta autenticar na API do Twilio.
$response = $this->call_api('/2010-04-01/Accounts/' . $this->account_sid . '.json');
return $response->status === 'active';
} catch (\Throwable) {
return false;
}
}
public function get_credential_fields(): array
{
return [
['key' => 'account_sid', 'label' => 'Account SID', 'type' => 'text'],
['key' => 'auth_token', 'label' => 'Auth Token', 'type' => 'password'],
['key' => 'from_number', 'label' => 'From Number', 'type' => 'text'],
];
}
}
API reference¶
connector_interface¶
Contract que todo connector deve implementar:
| Metodo | Retorno | Descricao |
|---|---|---|
get_type() |
string |
Slug unico do tipo (ex: 'twilio', 'woocommerce', 'bigquery') |
get_name() |
string |
Nome legivel para exibicao na UI |
get_extension() |
string |
Slug da extension que possui este connector |
health_check() |
bool |
Testa conectividade com as credenciais configuradas |
get_credential_fields() |
list<array{key, label, type}> |
Campos de credencial necessarios para configuracao |
Os campos de credencial suportam os tipos 'text', 'password', 'url' e 'select'.
connector_registry_interface¶
Registry central que gerencia todos os connectors registrados:
| Metodo | Retorno | Descricao |
|---|---|---|
register($connector) |
void |
Registra um connector type |
get($type) |
?connector_interface |
Retorna connector pelo slug, ou null se inexistente |
all() |
array<string, connector_interface> |
Todos os connectors registrados, indexados por slug |
for_extension($extension) |
list<connector_interface> |
Connectors de uma extension especifica |
Registro no boot()¶
Extensions registram seus connectors durante o boot():
namespace local_meuplugin\extensions\notifications;
use local_middag\base\extension;
use local_middag\framework\contract\connector_registry_interface;
class notifications_extension extends extension
{
public function boot(): void
{
$registry = $this->container->get(connector_registry_interface::class);
$registry->register(new connector\twilio_connector(
account_sid: $this->config('twilio_account_sid'),
auth_token: $this->config('twilio_auth_token'),
from_number: $this->config('twilio_from_number'),
));
}
}
O registry e obtido do container DI. O register() e chamado uma vez por tipo.
Consultar connectors¶
use local_middag\facade\connector_registry;
// Obter um connector especifico.
$twilio = connector_registry::get('twilio');
if ($twilio !== null && $twilio->health_check()) {
// Connector disponivel e saudavel.
}
// Listar todos os connectors de uma extension.
$connectors = connector_registry::for_extension('notifications');
// Listar todos os connectors registrados.
$all = connector_registry::all();
Patterns¶
Credenciais via settings¶
Armazene credenciais nas settings tipadas do MIDDAG, nunca no codigo. Use get_credential_fields() para declarar quais campos o admin precisa preencher na UI de configuracao:
public function get_credential_fields(): array
{
return [
['key' => 'api_key', 'label' => 'API Key', 'type' => 'password'],
['key' => 'webhook_url', 'label' => 'Webhook URL', 'type' => 'url'],
];
}
Health check com timeout¶
Sempre proteja o health check contra timeouts e excecoes. O metodo deve retornar false em caso de falha, nunca lancar excecao:
public function health_check(): bool
{
try {
$response = $this->http->get($this->base_url . '/health', [
'timeout' => 5,
]);
return $response->is_ok();
} catch (\Throwable) {
return false;
}
}
Graceful degradation¶
Verifique disponibilidade antes de usar. Se o servico externo estiver fora, a extension deve degradar sem derrubar o sistema:
$connector = connector_registry::get('bigquery');
if ($connector === null || !$connector->health_check()) {
// Servico indisponivel -- fallback ou skip.
return;
}
// Prosseguir com a integracao.
Um tipo por servico¶
Cada servico externo distinto deve ter seu proprio connector type. Nao misture credenciais ou endpoints de servicos diferentes no mesmo connector.
Anti-patterns¶
Credenciais hardcoded¶
// ERRADO: credenciais no codigo.
public function __construct()
{
$this->api_key = 'sk-1234567890abcdef';
}
Credenciais devem vir de settings tipadas, injetadas via construtor.
Health check ausente¶
O health check deve testar conectividade real. Um return true incondicional mascara falhas e inutiliza o monitoramento.
Health check que lanca excecao¶
// ERRADO: excecao escapa do health check.
public function health_check(): bool
{
$response = $this->http->get('/ping'); // pode lancar
return $response->is_ok();
}
Sempre envolva em try/catch. O contrato exige retorno bool.
Connector generico multi-servico¶
// ERRADO: um connector para multiplos servicos.
public function get_type(): string
{
return 'payment'; // Qual? Stripe? PayPal? PagSeguro?
}
Cada servico externo e um tipo distinto: 'stripe', 'paypal', 'pagseguro'.
Referencias¶
- Core Capability CC-02 (ADR-607)
- Settings tipadas
- Modos de Integracao