Transacional — Nó de Automação¶
Os nós são os passos de uma automação. Cada nó tem um type, um
child (o nó seguinte, ou null quando o contacto sai do fluxo) e, nos nós ifElse e
externalEvent, um child2 (o segundo ramo). As definições de um nó ficam em payload e são
alteradas com um PUT próprio de cada tipo.
Endpoints¶
| Método | URL |
|---|---|
POST |
/transactional/<transactional>/automation/<automation>/node |
PUT |
/transactional/<transactional>/automation/<automation>/node/<node>/<type> |
DELETE |
/transactional/<transactional>/automation/<automation>/node/<node> |
Os nós são lidos com GET /transactional/<transactional>/automation/<automation>.
Envie os parâmetros form-encoded ou na query string.
Tipos de nó¶
| Tipo | Categoria | O que faz | Ramos |
|---|---|---|---|
contactSignup |
Entrada | Um contacto é acrescentado à lista (API, carregamento de CSV, formulário ou contacto criado por um evento) | child |
contactAnniversary |
Entrada | A data de um campo personalizado do contacto volta a ocorrer (verificado de hora a hora) | child |
externalEventEntry |
Entrada | Chama o URL do evento para o contacto | child |
smsReceivedEntry |
Entrada | O contacto envia um SMS para um dos seus números de receção | child |
existingContact |
Entrada | Não é processado de momento. Não use. | child |
loopingContact |
Entrada | Não é processado de momento. Não use. | child |
sendMessage |
Ação | Envia uma mensagem transacional (email e/ou SMS) | child |
setField |
Ação | Altera campos personalizados do contacto | child |
httpCallback |
Ação | Envia um POST HTTP para o seu serviço |
child |
wait |
Espera | Espera um período fixo | child |
externalEvent |
Espera | Espera por um evento para o contacto, com um tempo limite opcional | child = evento, child2 = tempo limite |
smsReceived |
Espera | Espera por um SMS do contacto, com um tempo limite opcional | child (SMS ou tempo limite) |
ifElse |
Condição | Testa campos do contacto | child = verdadeiro, child2 = falso |
POST /transactional/<transactional>/automation/<automation>/node¶
Cria um nó e liga-o ao fluxo.
| Parâmetro | Tipo | Descrição |
|---|---|---|
type |
string | Obrigatório. Um dos tipos de nó acima |
connectFrom |
string | Obrigatório. Onde ligar o nó: null para um nó de entrada; o ID do nó anterior (o novo nó passa a ser o seu child); <id>[1] para o segundo ramo (child2) de um nó ifElse ou externalEvent; ou start para o primeiro passo depois dos nós de entrada |
connectTo |
string | Obrigatório. null para acrescentar o nó no fim de um ramo, ou o ID de um nó existente para inserir o novo nó antes dele. Nesse caso, todos os nós que apontavam para ele passam a apontar para o novo nó. |
title |
string | Opcional. Por defeito, um título para o tipo |
comment |
string | Opcional. Por defeito, uma descrição para o tipo |
- Os tipos de entrada (
contactSignup,contactAnniversary,externalEventEntry,smsReceivedEntry) têm de ser criados comconnectFrom=null&connectTo=null, e os outros tipos não. Caso contrário, o pedido falha comIncompatible type and position. - Um novo nó de entrada leva ao mesmo primeiro passo dos nós de entrada existentes.
- Para acrescentar um nó entre dois nós, indique em
connectToo nó seguinte. ComconnectTo=null, ligue apenas a um nó ou ramo que ainda não tenha nó seguinte.
Devolve: O novo nó (transactionalAutomationNode) e a automação.
Exemplo — acrescentar um nó sendMessage depois do nó 31:
curl -u "username:api_key" -H "Accept: application/json" \
-d "type=sendMessage&connectFrom=31&connectTo=null" \
https://app.duo.pt/transactional/{transactional_id}/automation/{automation_id}/node
Resposta:
{
"success": true,
"data": {
"transactionalAutomation": {
"id": 7,
"name": "Payment follow-up",
"enabled": false,
"send_transactional": 1
},
"transactionalAutomationNode": {
"id": 32,
"send_transactional_automation": 7,
"type": "sendMessage",
"title": "Receives a message",
"comment": "Click to select message",
"child": null,
"child2": null,
"payload": null
}
}
}
PUT /transactional/<transactional>/automation/<automation>/node/<node>/<type>¶
Altera as definições do nó. <type> tem de ser o tipo do nó. Envie um POST com
x-verb=PUT. Cada pedido substitui o payload inteiro.
Devolve: transactional, transactionalAutomation e o transactionalAutomationNode
atualizado, com o seu payload e um novo comment.
contactSignup¶
| Parâmetro | Tipo | Descrição |
|---|---|---|
segment |
int | Opcional. ID de um segmento da lista. É guardado, mas não é aplicado de momento: todos os novos contactos entram. |
Payload: {"segment": 5}
contactAnniversary¶
| Parâmetro | Tipo | Descrição |
|---|---|---|
anniversary_field |
int | ID do campo personalizado da lista com a data |
anniversary_period |
string | Opcional. year (por defeito), month, week, day ou hour |
Payload: {"field_to_check": 42, "check_period": "year"}
externalEventEntry¶
| Parâmetro | Tipo | Descrição |
|---|---|---|
event |
string | Obrigatório. Nome do evento. É uma etiqueta: o URL do evento identifica o nó. |
fields_to_set[argument][] |
array de string | Obrigatório, pode ser vazio. Reservado: é guardado, mas não é aplicado de momento. |
fields_to_set[custom_field][] |
array de string | Obrigatório, pode ser vazio. Reservado, mesmo índice de argument. |
Payload: {"event": "payment", "fields_to_set": []}
externalEvent¶
Os parâmetros de externalEventEntry e ainda:
| Parâmetro | Tipo | Descrição |
|---|---|---|
period |
int | Tempo limite em segundos. Quando expira, o contacto segue para child2. Com 0, espera apenas pelo evento. |
Defina um tempo limite só quando precisar do segundo ramo.
wait¶
| Parâmetro | Tipo | Descrição |
|---|---|---|
period |
int | Espera em segundos. Tem de ser maior do que 0: com 0, o contacto fica no nó. |
Payload: {"period": 86400}
sendMessage¶
| Parâmetro | Tipo | Descrição |
|---|---|---|
message |
int | ID de uma mensagem deste objeto transacional. Os outros IDs são ignorados. |
Payload: {"message": 12}. O contacto recebe o email da mensagem se tiver endereço de email, e o
seu SMS se tiver número de telefone. Os contactos não subscritos ou com bounce não recebem nada,
mas continuam no fluxo.
setField¶
| Parâmetro | Tipo | Descrição |
|---|---|---|
fields_to_set[argument][] |
array de string | Obrigatório. Valores a gravar |
fields_to_set[custom_field][] |
array de int | Obrigatório. IDs dos campos personalizados da lista, mesmo índice dos valores |
Payload: {"fields_to_set": {"VIP": "43"}} (valor → ID do campo). Cada valor só pode ser usado
uma vez por nó: para gravar o mesmo valor em dois campos, use dois nós setField.
ifElse¶
| Parâmetro | Tipo | Descrição |
|---|---|---|
payload[topoperator] |
string | AND (todas as condições) ou OR (qualquer condição). Qualquer outro valor equivale a OR. |
payload[condition_field][] |
array de string | email, telephone ou o ID de um campo personalizado da lista |
payload[condition_operator][] |
array de string | ==, !=, contains, !contains, starts_with, !starts_with, ends_with, !ends_with; > e < para números; before, after e is_today para datas (AAAA-MM-DD ou AAAA-MM-DD HH:MM:SS) |
payload[condition_operand][] |
array de string | Valor a comparar (vazio em is_today) |
Payload: {"topoperator": "AND", "operands": [{"field": "45", "operator": "==", "operand": "yes"}]}.
Verdadeiro → child, falso → child2.
Dica
Envie apenas condições completas, com campos da lista do objeto transacional, e sem linhas
vazias. Nos campos de texto, prefira == e !=. Verifique cada condição com um contacto de
teste antes de ativar a automação.
httpCallback¶
| Parâmetro | Tipo | Descrição |
|---|---|---|
url |
string | Obrigatório. URL http:// ou https:// do seu serviço |
parameterName[] |
array de string | Nomes dos campos do corpo |
parameterSource[] |
array de string | static (valor fixo) ou field (valor do contacto) |
parameterStaticValue[] |
array de string | O valor, quando a origem é static |
parameterFieldValue[] |
array de string | email, telephone ou o ID de um campo personalizado, quando a origem é field |
http_error |
int | Opcional. ID de um campo personalizado que recebe o código de estado HTTP. Quando definido, o contacto segue também para child depois de um erro. |
http_result |
int | Opcional. ID de um campo personalizado que recebe o corpo da resposta |
Envie os quatro arrays parameter…[] com uma entrada por parâmetro, com valores vazios onde não
se aplicam. Um parâmetro com nome vazio é ignorado.
Payload: {"url": "https://example.com/duo/hook", "http_error": null, "http_result": 44, "http_parameters": [{"name": "email", "source": "field", "fieldValue": "email"}, {"name": "token", "source": "static", "staticValue": "s3cr3t"}]}
O pedido que a DUO faz: POST <url> com Content-Type: application/x-www-form-urlencoded e
os parâmetros como campos do corpo (sem corpo se não houver nenhum), User-Agent: duo/<versão>
e tempo limite de 60 segundos. Uma resposta 2xx faz o contacto seguir para child. Com
qualquer outra resposta, ou se o pedido falhar, o contacto não continua, exceto se http_error
estiver definido. Os pedidos não são assinados nem repetidos: coloque um token secreto num
parâmetro static e verifique-o do seu lado.
Exemplo — configurar um nó httpCallback:
curl -u "username:api_key" -H "Accept: application/json" \
--data-urlencode "x-verb=PUT" \
--data-urlencode "url=https://example.com/duo/hook" \
--data-urlencode "parameterName[]=email" --data-urlencode "parameterSource[]=field" \
--data-urlencode "parameterStaticValue[]=" --data-urlencode "parameterFieldValue[]=email" \
--data-urlencode "parameterName[]=token" --data-urlencode "parameterSource[]=static" \
--data-urlencode "parameterStaticValue[]=s3cr3t" --data-urlencode "parameterFieldValue[]=" \
--data-urlencode "http_error=" --data-urlencode "http_result=" \
https://app.duo.pt/transactional/{transactional_id}/automation/{automation_id}/node/{node_id}/httpCallback
smsReceivedEntry, smsReceived¶
| Parâmetro | Tipo | Descrição |
|---|---|---|
inbound_telephone |
int | Opcional. ID de um dos seus números de receção de SMS. Vazio para qualquer um deles. |
field_to_set |
int | Opcional. ID de um campo personalizado que recebe o texto do SMS |
value_regex |
string | Opcional. Expressão regular com um grupo de captura. É gravado o texto capturado em vez do SMS inteiro (sem distinguir maiúsculas). |
period |
int | Só em smsReceived. Tempo limite em segundos; quando expira, o contacto segue também para child. Com 0, espera sem tempo limite. |
Payload: {"inbound_telephone": null, "set_field": {"field": 45, "source": "regex", "regex": "^SIM (\\d+)"}, "timeout": 3600}
DELETE /transactional/<transactional>/automation/<automation>/node/<node>¶
Elimina o nó. Os nós que apontavam para ele passam a apontar para o seu child. Eliminar um nó
ifElse ou externalEvent elimina também o primeiro nó do seu segundo ramo: elimine primeiro
os nós desse ramo, do último para o primeiro.
Devolve: transactional, transactionalAutomation e o transactionalAutomationNode
eliminado.
Exemplo: