n8n-nodes-levvex 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/README.md +129 -0
- package/dist/credentials/LevvexWebhookApi.credentials.d.ts +11 -0
- package/dist/credentials/LevvexWebhookApi.credentials.js +24 -0
- package/dist/credentials/LevvexWebhookApi.credentials.js.map +1 -0
- package/dist/credentials/levvex.svg +5 -0
- package/dist/nodes/LevvexWebhook/LevvexWebhook.node.json +17 -0
- package/dist/nodes/LevvexWebhook/LevvexWebhook.trigger.d.ts +12 -0
- package/dist/nodes/LevvexWebhook/LevvexWebhook.trigger.js +115 -0
- package/dist/nodes/LevvexWebhook/LevvexWebhook.trigger.js.map +1 -0
- package/dist/nodes/LevvexWebhook/eventDefinitions.d.ts +2 -0
- package/dist/nodes/LevvexWebhook/eventDefinitions.js +121 -0
- package/dist/nodes/LevvexWebhook/eventDefinitions.js.map +1 -0
- package/dist/nodes/LevvexWebhook/levvex-icon.svg +5 -0
- package/package.json +51 -0
package/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 GBSOLUCOES
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
package/README.md
ADDED
|
@@ -0,0 +1,129 @@
|
|
|
1
|
+
# n8n-nodes-levvex
|
|
2
|
+
|
|
3
|
+
Community node para [n8n](https://n8n.io/) que recebe webhooks da plataforma [Levvex](https://levvex.com).
|
|
4
|
+
|
|
5
|
+
## Funcionalidades
|
|
6
|
+
|
|
7
|
+
- **Trigger Node** que recebe webhooks da Levvex automaticamente
|
|
8
|
+
- **21 eventos** suportados (compras, assinaturas, MiniApp, ingressos)
|
|
9
|
+
- **Filtro de eventos** via multi-select — escolha quais eventos ativam o workflow
|
|
10
|
+
- **Validacao de secret** — garante que apenas webhooks legítimos disparam o workflow
|
|
11
|
+
- **Payload completo** — todos os dados da Levvex disponíveis nos nós seguintes
|
|
12
|
+
|
|
13
|
+
## Instalação
|
|
14
|
+
|
|
15
|
+
### No n8n (Community Nodes)
|
|
16
|
+
|
|
17
|
+
1. Acesse **Settings > Community Nodes**
|
|
18
|
+
2. Clique em **Install a community node**
|
|
19
|
+
3. Digite `n8n-nodes-levvex` e clique em **Install**
|
|
20
|
+
|
|
21
|
+
### Via npm (self-hosted)
|
|
22
|
+
|
|
23
|
+
```bash
|
|
24
|
+
cd ~/.n8n
|
|
25
|
+
npm install n8n-nodes-levvex
|
|
26
|
+
```
|
|
27
|
+
|
|
28
|
+
Reinicie o n8n após a instalação.
|
|
29
|
+
|
|
30
|
+
## Configuração
|
|
31
|
+
|
|
32
|
+
### 1. Criar o trigger no n8n
|
|
33
|
+
|
|
34
|
+
1. Adicione o nó **Levvex Webhook** ao seu workflow
|
|
35
|
+
2. Selecione os eventos que deseja receber (ou "Todos os Eventos")
|
|
36
|
+
3. Copie a **Webhook URL** gerada (Production URL)
|
|
37
|
+
4. Ative o workflow
|
|
38
|
+
|
|
39
|
+
### 2. Configurar o webhook na Levvex
|
|
40
|
+
|
|
41
|
+
1. No painel do seller: **Integrações > Webhooks > Novo Webhook**
|
|
42
|
+
2. Cole a URL do n8n no campo **URL**
|
|
43
|
+
3. Selecione os mesmos eventos que configurou no n8n
|
|
44
|
+
4. Copie o **Secret** gerado pela Levvex
|
|
45
|
+
|
|
46
|
+
### 3. Configurar a credencial no n8n
|
|
47
|
+
|
|
48
|
+
1. No nó Levvex Webhook, clique em **Create New Credential**
|
|
49
|
+
2. Cole o **Secret** copiado da Levvex
|
|
50
|
+
3. Salve
|
|
51
|
+
|
|
52
|
+
## Eventos Disponíveis
|
|
53
|
+
|
|
54
|
+
### Compras
|
|
55
|
+
| Evento | Descrição |
|
|
56
|
+
|--------|-----------|
|
|
57
|
+
| `purchase_approved` | Pagamento confirmado |
|
|
58
|
+
| `purchase_refused` | Pagamento recusado |
|
|
59
|
+
| `pix_generated` | PIX criado aguardando pagamento |
|
|
60
|
+
| `refund` | Reembolso processado |
|
|
61
|
+
| `chargeback` | Contestação recebida |
|
|
62
|
+
|
|
63
|
+
### Checkout & Entrega
|
|
64
|
+
| Evento | Descrição |
|
|
65
|
+
|--------|-----------|
|
|
66
|
+
| `checkout_abandonment` | Carrinho abandonado |
|
|
67
|
+
| `product_access` | Acesso ao produto liberado |
|
|
68
|
+
| `product_access_personalized` | Entrega personalizada |
|
|
69
|
+
|
|
70
|
+
### Assinaturas
|
|
71
|
+
| Evento | Descrição |
|
|
72
|
+
|--------|-----------|
|
|
73
|
+
| `subscription_renewed` | Cobrança recorrente aprovada |
|
|
74
|
+
| `subscription_canceled` | Assinatura cancelada |
|
|
75
|
+
| `subscription_failed` | Falha na cobrança |
|
|
76
|
+
| `subscription_unpaid` | Pagamento pendente |
|
|
77
|
+
| `subscription_expiring` | Próxima do vencimento |
|
|
78
|
+
|
|
79
|
+
### MiniApp
|
|
80
|
+
| Evento | Descrição |
|
|
81
|
+
|--------|-----------|
|
|
82
|
+
| `miniapp_lesson_completed` | Aluno concluiu aula |
|
|
83
|
+
| `miniapp_student_joined` | Aluno adicionado |
|
|
84
|
+
| `miniapp_student_removed` | Aluno removido |
|
|
85
|
+
|
|
86
|
+
### Eventos (Ingressos)
|
|
87
|
+
| Evento | Descrição |
|
|
88
|
+
|--------|-----------|
|
|
89
|
+
| `event_ticket_purchased` | Ingresso comprado |
|
|
90
|
+
| `event_ticket_cancelled` | Ingresso cancelado |
|
|
91
|
+
| `event_checkin` | Check-in realizado |
|
|
92
|
+
| `event_attendee_registered` | Participante registrado |
|
|
93
|
+
| `event_ticket_transferred` | Ingresso transferido |
|
|
94
|
+
|
|
95
|
+
## Acessando os dados no workflow
|
|
96
|
+
|
|
97
|
+
Os dados ficam disponíveis em `$json.data`:
|
|
98
|
+
|
|
99
|
+
```
|
|
100
|
+
{{ $json.event }} → Nome do evento
|
|
101
|
+
{{ $json.data.customer.name }} → Nome do cliente
|
|
102
|
+
{{ $json.data.customer.email }} → Email do cliente
|
|
103
|
+
{{ $json.data.order.id }} → ID do pedido (UUID)
|
|
104
|
+
{{ $json.data.order.refId }} → Código do pedido
|
|
105
|
+
{{ $json.data.order.status }} → Status do pedido
|
|
106
|
+
{{ $json.data.product.name }} → Nome do produto
|
|
107
|
+
{{ $json.data.offer.name }} → Nome da oferta
|
|
108
|
+
{{ $json.data.offer.price }} → Preço da oferta
|
|
109
|
+
{{ $json.data.transaction.amount }} → Valor da transação
|
|
110
|
+
{{ $json.data.transaction.paymentMethod }} → Método de pagamento
|
|
111
|
+
{{ $json.data.metadata.utmSource }} → UTM Source
|
|
112
|
+
```
|
|
113
|
+
|
|
114
|
+
## Desenvolvimento
|
|
115
|
+
|
|
116
|
+
```bash
|
|
117
|
+
# Instalar dependências
|
|
118
|
+
npm install
|
|
119
|
+
|
|
120
|
+
# Compilar
|
|
121
|
+
npm run build
|
|
122
|
+
|
|
123
|
+
# Modo desenvolvimento (watch)
|
|
124
|
+
npm run dev
|
|
125
|
+
```
|
|
126
|
+
|
|
127
|
+
## Licença
|
|
128
|
+
|
|
129
|
+
[MIT](LICENSE)
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import type { ICredentialType, INodeProperties } from 'n8n-workflow';
|
|
2
|
+
export declare class LevvexWebhookApi implements ICredentialType {
|
|
3
|
+
name: string;
|
|
4
|
+
displayName: string;
|
|
5
|
+
icon: {
|
|
6
|
+
readonly light: "file:levvex.svg";
|
|
7
|
+
readonly dark: "file:levvex.svg";
|
|
8
|
+
};
|
|
9
|
+
documentationUrl: string;
|
|
10
|
+
properties: INodeProperties[];
|
|
11
|
+
}
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.LevvexWebhookApi = void 0;
|
|
4
|
+
class LevvexWebhookApi {
|
|
5
|
+
constructor() {
|
|
6
|
+
this.name = 'levvexWebhookApi';
|
|
7
|
+
this.displayName = 'Levvex Webhook';
|
|
8
|
+
this.icon = { light: 'file:levvex.svg', dark: 'file:levvex.svg' };
|
|
9
|
+
this.documentationUrl = 'https://app.levvex.com';
|
|
10
|
+
this.properties = [
|
|
11
|
+
{
|
|
12
|
+
displayName: 'Webhook Secret',
|
|
13
|
+
name: 'secret',
|
|
14
|
+
type: 'string',
|
|
15
|
+
typeOptions: { password: true },
|
|
16
|
+
default: '',
|
|
17
|
+
required: true,
|
|
18
|
+
description: 'O secret do webhook configurado no painel Levvex. Encontre em: Painel do Seller → Integrações → Webhooks → Secret do webhook.',
|
|
19
|
+
},
|
|
20
|
+
];
|
|
21
|
+
}
|
|
22
|
+
}
|
|
23
|
+
exports.LevvexWebhookApi = LevvexWebhookApi;
|
|
24
|
+
//# sourceMappingURL=LevvexWebhookApi.credentials.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"LevvexWebhookApi.credentials.js","sourceRoot":"","sources":["../../credentials/LevvexWebhookApi.credentials.ts"],"names":[],"mappings":";;;AAKA,MAAa,gBAAgB;IAA7B;QACC,SAAI,GAAG,kBAAkB,CAAC;QAC1B,gBAAW,GAAG,gBAAgB,CAAC;QAC/B,SAAI,GAAG,EAAE,KAAK,EAAE,iBAAiB,EAAE,IAAI,EAAE,iBAAiB,EAAW,CAAC;QACtE,qBAAgB,GAAG,wBAAwB,CAAC;QAE5C,eAAU,GAAsB;YAC/B;gBACC,WAAW,EAAE,gBAAgB;gBAC7B,IAAI,EAAE,QAAQ;gBACd,IAAI,EAAE,QAAQ;gBACd,WAAW,EAAE,EAAE,QAAQ,EAAE,IAAI,EAAE;gBAC/B,OAAO,EAAE,EAAE;gBACX,QAAQ,EAAE,IAAI;gBACd,WAAW,EACV,+HAA+H;aAChI;SACD,CAAC;IACH,CAAC;CAAA;AAlBD,4CAkBC"}
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
<svg xmlns="http://www.w3.org/2000/svg" width="60" height="60" viewBox="0 0 60 60">
|
|
2
|
+
<rect width="60" height="60" rx="8" fill="white" stroke="#E5E7EB" stroke-width="1"/>
|
|
3
|
+
<polygon points="46.4,12.1 49,7 35.8,7 18.9,40 25.5,52.9" fill="#0098FF"/>
|
|
4
|
+
<polygon points="22,28.6 15.4,15.6 10.9,24.4 17.6,37.3" fill="#0098FF"/>
|
|
5
|
+
</svg>
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
{
|
|
2
|
+
"node": "n8n-nodes-levvex.levvexWebhookTrigger",
|
|
3
|
+
"nodeVersion": "1.0",
|
|
4
|
+
"codexVersion": "1.0",
|
|
5
|
+
"categories": ["Communication"],
|
|
6
|
+
"subcategories": {
|
|
7
|
+
"Communication": ["Trigger"]
|
|
8
|
+
},
|
|
9
|
+
"resources": {
|
|
10
|
+
"primaryDocumentation": [
|
|
11
|
+
{
|
|
12
|
+
"url": "https://github.com/GBSOLUCOES/n8n-nodes-levvex"
|
|
13
|
+
}
|
|
14
|
+
]
|
|
15
|
+
},
|
|
16
|
+
"alias": ["levvex", "webhook", "checkout", "payment", "ecommerce", "subscription", "miniapp"]
|
|
17
|
+
}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import type { IHookFunctions, INodeType, INodeTypeDescription, IWebhookFunctions, IWebhookResponseData } from 'n8n-workflow';
|
|
2
|
+
export declare class LevvexWebhookTrigger implements INodeType {
|
|
3
|
+
description: INodeTypeDescription;
|
|
4
|
+
webhookMethods: {
|
|
5
|
+
default: {
|
|
6
|
+
checkExists(this: IHookFunctions): Promise<boolean>;
|
|
7
|
+
create(this: IHookFunctions): Promise<boolean>;
|
|
8
|
+
delete(this: IHookFunctions): Promise<boolean>;
|
|
9
|
+
};
|
|
10
|
+
};
|
|
11
|
+
webhook(this: IWebhookFunctions): Promise<IWebhookResponseData>;
|
|
12
|
+
}
|
|
@@ -0,0 +1,115 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.LevvexWebhookTrigger = void 0;
|
|
4
|
+
const crypto_1 = require("crypto");
|
|
5
|
+
const n8n_workflow_1 = require("n8n-workflow");
|
|
6
|
+
const eventDefinitions_1 = require("./eventDefinitions");
|
|
7
|
+
class LevvexWebhookTrigger {
|
|
8
|
+
constructor() {
|
|
9
|
+
this.description = {
|
|
10
|
+
displayName: 'Levvex Webhook',
|
|
11
|
+
name: 'levvexWebhookTrigger',
|
|
12
|
+
icon: 'file:levvex-icon.svg',
|
|
13
|
+
group: ['trigger'],
|
|
14
|
+
version: 1,
|
|
15
|
+
subtitle: '={{$parameter["events"].length === 1 && $parameter["events"][0] === "*" ? "Todos os Eventos" : $parameter["events"].length + " evento(s)"}}',
|
|
16
|
+
description: 'Recebe webhooks da plataforma Levvex (compras, assinaturas, MiniApp, eventos)',
|
|
17
|
+
defaults: {
|
|
18
|
+
name: 'Levvex Webhook',
|
|
19
|
+
},
|
|
20
|
+
inputs: [],
|
|
21
|
+
outputs: [n8n_workflow_1.NodeConnectionTypes.Main],
|
|
22
|
+
credentials: [
|
|
23
|
+
{
|
|
24
|
+
name: 'levvexWebhookApi',
|
|
25
|
+
required: true,
|
|
26
|
+
},
|
|
27
|
+
],
|
|
28
|
+
webhooks: [
|
|
29
|
+
{
|
|
30
|
+
name: 'default',
|
|
31
|
+
httpMethod: 'POST',
|
|
32
|
+
responseMode: 'onReceived',
|
|
33
|
+
path: 'webhook',
|
|
34
|
+
},
|
|
35
|
+
],
|
|
36
|
+
properties: [
|
|
37
|
+
{
|
|
38
|
+
displayName: 'Eventos',
|
|
39
|
+
name: 'events',
|
|
40
|
+
type: 'multiOptions',
|
|
41
|
+
options: eventDefinitions_1.LEVVEX_EVENTS,
|
|
42
|
+
default: ['*'],
|
|
43
|
+
required: true,
|
|
44
|
+
description: 'Selecione quais eventos da Levvex devem ativar este trigger. "Todos os Eventos" aceita qualquer evento.',
|
|
45
|
+
},
|
|
46
|
+
],
|
|
47
|
+
};
|
|
48
|
+
this.webhookMethods = {
|
|
49
|
+
default: {
|
|
50
|
+
async checkExists() {
|
|
51
|
+
return true;
|
|
52
|
+
},
|
|
53
|
+
async create() {
|
|
54
|
+
return true;
|
|
55
|
+
},
|
|
56
|
+
async delete() {
|
|
57
|
+
return true;
|
|
58
|
+
},
|
|
59
|
+
},
|
|
60
|
+
};
|
|
61
|
+
}
|
|
62
|
+
async webhook() {
|
|
63
|
+
const body = this.getBodyData();
|
|
64
|
+
// Validate: payload must have an event field
|
|
65
|
+
const event = body.event;
|
|
66
|
+
if (!event) {
|
|
67
|
+
return {
|
|
68
|
+
webhookResponse: {
|
|
69
|
+
status: 400,
|
|
70
|
+
body: { error: 'Missing event field' },
|
|
71
|
+
},
|
|
72
|
+
workflowData: undefined,
|
|
73
|
+
};
|
|
74
|
+
}
|
|
75
|
+
// Validate: secret must match
|
|
76
|
+
const credentials = await this.getCredentials('levvexWebhookApi');
|
|
77
|
+
const expectedSecret = credentials.secret;
|
|
78
|
+
const payloadSecret = body.secret;
|
|
79
|
+
if (expectedSecret && (!payloadSecret
|
|
80
|
+
|| expectedSecret.length !== payloadSecret.length
|
|
81
|
+
|| !(0, crypto_1.timingSafeEqual)(Buffer.from(expectedSecret), Buffer.from(payloadSecret)))) {
|
|
82
|
+
return {
|
|
83
|
+
webhookResponse: {
|
|
84
|
+
status: 403,
|
|
85
|
+
body: { error: 'Invalid secret' },
|
|
86
|
+
},
|
|
87
|
+
workflowData: undefined,
|
|
88
|
+
};
|
|
89
|
+
}
|
|
90
|
+
// Filter: check if this event is in the selected events
|
|
91
|
+
const selectedEvents = this.getNodeParameter('events', []);
|
|
92
|
+
const acceptAllEvents = selectedEvents.includes('*');
|
|
93
|
+
if (!acceptAllEvents && !selectedEvents.includes(event)) {
|
|
94
|
+
return {
|
|
95
|
+
webhookResponse: {
|
|
96
|
+
status: 200,
|
|
97
|
+
body: { status: 'received', processed: false },
|
|
98
|
+
},
|
|
99
|
+
workflowData: undefined,
|
|
100
|
+
};
|
|
101
|
+
}
|
|
102
|
+
// Success: pass full payload to workflow
|
|
103
|
+
return {
|
|
104
|
+
workflowData: [
|
|
105
|
+
[{ json: body }],
|
|
106
|
+
],
|
|
107
|
+
webhookResponse: {
|
|
108
|
+
status: 200,
|
|
109
|
+
body: { status: 'received', processed: true },
|
|
110
|
+
},
|
|
111
|
+
};
|
|
112
|
+
}
|
|
113
|
+
}
|
|
114
|
+
exports.LevvexWebhookTrigger = LevvexWebhookTrigger;
|
|
115
|
+
//# sourceMappingURL=LevvexWebhook.trigger.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"LevvexWebhook.trigger.js","sourceRoot":"","sources":["../../../nodes/LevvexWebhook/LevvexWebhook.trigger.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,121 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.LEVVEX_EVENTS = void 0;
|
|
4
|
+
exports.LEVVEX_EVENTS = [
|
|
5
|
+
{
|
|
6
|
+
name: 'Todos os Eventos',
|
|
7
|
+
value: '*',
|
|
8
|
+
description: 'Receber todos os eventos da Levvex',
|
|
9
|
+
},
|
|
10
|
+
// ── Compras ──────────────────────────────────────────────
|
|
11
|
+
{
|
|
12
|
+
name: 'Compra Aprovada',
|
|
13
|
+
value: 'purchase_approved',
|
|
14
|
+
description: 'Pagamento confirmado (cartão ou PIX)',
|
|
15
|
+
},
|
|
16
|
+
{
|
|
17
|
+
name: 'Compra Recusada',
|
|
18
|
+
value: 'purchase_refused',
|
|
19
|
+
description: 'Pagamento recusado pelo gateway',
|
|
20
|
+
},
|
|
21
|
+
{
|
|
22
|
+
name: 'PIX Gerado',
|
|
23
|
+
value: 'pix_generated',
|
|
24
|
+
description: 'PIX criado aguardando pagamento',
|
|
25
|
+
},
|
|
26
|
+
{
|
|
27
|
+
name: 'Reembolso',
|
|
28
|
+
value: 'refund',
|
|
29
|
+
description: 'Reembolso processado',
|
|
30
|
+
},
|
|
31
|
+
{
|
|
32
|
+
name: 'Chargeback',
|
|
33
|
+
value: 'chargeback',
|
|
34
|
+
description: 'Contestação ou chargeback recebido',
|
|
35
|
+
},
|
|
36
|
+
// ── Checkout & Entrega ───────────────────────────────────
|
|
37
|
+
{
|
|
38
|
+
name: 'Abandono de Checkout',
|
|
39
|
+
value: 'checkout_abandonment',
|
|
40
|
+
description: 'Carrinho abandonado sem finalizar compra',
|
|
41
|
+
},
|
|
42
|
+
{
|
|
43
|
+
name: 'Acesso ao Produto',
|
|
44
|
+
value: 'product_access',
|
|
45
|
+
description: 'Acesso ao produto liberado para o cliente',
|
|
46
|
+
},
|
|
47
|
+
{
|
|
48
|
+
name: 'Entrega Personalizada',
|
|
49
|
+
value: 'product_access_personalized',
|
|
50
|
+
description: 'Email de entrega personalizada enviado',
|
|
51
|
+
},
|
|
52
|
+
// ── Assinaturas ──────────────────────────────────────────
|
|
53
|
+
{
|
|
54
|
+
name: 'Assinatura Renovada',
|
|
55
|
+
value: 'subscription_renewed',
|
|
56
|
+
description: 'Cobrança recorrente aprovada',
|
|
57
|
+
},
|
|
58
|
+
{
|
|
59
|
+
name: 'Assinatura Cancelada',
|
|
60
|
+
value: 'subscription_canceled',
|
|
61
|
+
description: 'Assinatura cancelada pelo seller ou cliente',
|
|
62
|
+
},
|
|
63
|
+
{
|
|
64
|
+
name: 'Falha na Cobrança',
|
|
65
|
+
value: 'subscription_failed',
|
|
66
|
+
description: 'Tentativa de cobrança da assinatura falhou',
|
|
67
|
+
},
|
|
68
|
+
{
|
|
69
|
+
name: 'Assinatura Não Paga',
|
|
70
|
+
value: 'subscription_unpaid',
|
|
71
|
+
description: 'Assinatura com pagamento pendente',
|
|
72
|
+
},
|
|
73
|
+
{
|
|
74
|
+
name: 'Assinatura Expirando',
|
|
75
|
+
value: 'subscription_expiring',
|
|
76
|
+
description: 'Assinatura próxima do vencimento',
|
|
77
|
+
},
|
|
78
|
+
// ── MiniApp ──────────────────────────────────────────────
|
|
79
|
+
{
|
|
80
|
+
name: 'Aula Concluída',
|
|
81
|
+
value: 'miniapp_lesson_completed',
|
|
82
|
+
description: 'Aluno concluiu uma aula no MiniApp',
|
|
83
|
+
},
|
|
84
|
+
{
|
|
85
|
+
name: 'Aluno Adicionado',
|
|
86
|
+
value: 'miniapp_student_joined',
|
|
87
|
+
description: 'Novo aluno adicionado ao MiniApp',
|
|
88
|
+
},
|
|
89
|
+
{
|
|
90
|
+
name: 'Aluno Removido',
|
|
91
|
+
value: 'miniapp_student_removed',
|
|
92
|
+
description: 'Aluno removido do MiniApp',
|
|
93
|
+
},
|
|
94
|
+
// ── Eventos (Ingressos) ──────────────────────────────────
|
|
95
|
+
{
|
|
96
|
+
name: 'Ingresso Comprado',
|
|
97
|
+
value: 'event_ticket_purchased',
|
|
98
|
+
description: 'Ingresso comprado para evento',
|
|
99
|
+
},
|
|
100
|
+
{
|
|
101
|
+
name: 'Ingresso Cancelado',
|
|
102
|
+
value: 'event_ticket_cancelled',
|
|
103
|
+
description: 'Ingresso cancelado',
|
|
104
|
+
},
|
|
105
|
+
{
|
|
106
|
+
name: 'Check-in Realizado',
|
|
107
|
+
value: 'event_checkin',
|
|
108
|
+
description: 'Participante fez check-in no evento',
|
|
109
|
+
},
|
|
110
|
+
{
|
|
111
|
+
name: 'Participante Registrado',
|
|
112
|
+
value: 'event_attendee_registered',
|
|
113
|
+
description: 'Participante registrado no evento',
|
|
114
|
+
},
|
|
115
|
+
{
|
|
116
|
+
name: 'Ingresso Transferido',
|
|
117
|
+
value: 'event_ticket_transferred',
|
|
118
|
+
description: 'Ingresso transferido para outra pessoa',
|
|
119
|
+
},
|
|
120
|
+
];
|
|
121
|
+
//# sourceMappingURL=eventDefinitions.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"eventDefinitions.js","sourceRoot":"","sources":["../../../nodes/LevvexWebhook/eventDefinitions.ts"],"names":[],"mappings":";;;AAEa,QAAA,aAAa,GAA2B;IACpD;QACC,IAAI,EAAE,kBAAkB;QACxB,KAAK,EAAE,GAAG;QACV,WAAW,EAAE,oCAAoC;KACjD;IAED,4DAA4D;IAC5D;QACC,IAAI,EAAE,iBAAiB;QACvB,KAAK,EAAE,mBAAmB;QAC1B,WAAW,EAAE,sCAAsC;KACnD;IACD;QACC,IAAI,EAAE,iBAAiB;QACvB,KAAK,EAAE,kBAAkB;QACzB,WAAW,EAAE,iCAAiC;KAC9C;IACD;QACC,IAAI,EAAE,YAAY;QAClB,KAAK,EAAE,eAAe;QACtB,WAAW,EAAE,iCAAiC;KAC9C;IACD;QACC,IAAI,EAAE,WAAW;QACjB,KAAK,EAAE,QAAQ;QACf,WAAW,EAAE,sBAAsB;KACnC;IACD;QACC,IAAI,EAAE,YAAY;QAClB,KAAK,EAAE,YAAY;QACnB,WAAW,EAAE,oCAAoC;KACjD;IAED,4DAA4D;IAC5D;QACC,IAAI,EAAE,sBAAsB;QAC5B,KAAK,EAAE,sBAAsB;QAC7B,WAAW,EAAE,0CAA0C;KACvD;IACD;QACC,IAAI,EAAE,mBAAmB;QACzB,KAAK,EAAE,gBAAgB;QACvB,WAAW,EAAE,2CAA2C;KACxD;IACD;QACC,IAAI,EAAE,uBAAuB;QAC7B,KAAK,EAAE,6BAA6B;QACpC,WAAW,EAAE,wCAAwC;KACrD;IAED,4DAA4D;IAC5D;QACC,IAAI,EAAE,qBAAqB;QAC3B,KAAK,EAAE,sBAAsB;QAC7B,WAAW,EAAE,8BAA8B;KAC3C;IACD;QACC,IAAI,EAAE,sBAAsB;QAC5B,KAAK,EAAE,uBAAuB;QAC9B,WAAW,EAAE,6CAA6C;KAC1D;IACD;QACC,IAAI,EAAE,mBAAmB;QACzB,KAAK,EAAE,qBAAqB;QAC5B,WAAW,EAAE,4CAA4C;KACzD;IACD;QACC,IAAI,EAAE,qBAAqB;QAC3B,KAAK,EAAE,qBAAqB;QAC5B,WAAW,EAAE,mCAAmC;KAChD;IACD;QACC,IAAI,EAAE,sBAAsB;QAC5B,KAAK,EAAE,uBAAuB;QAC9B,WAAW,EAAE,kCAAkC;KAC/C;IAED,4DAA4D;IAC5D;QACC,IAAI,EAAE,gBAAgB;QACtB,KAAK,EAAE,0BAA0B;QACjC,WAAW,EAAE,oCAAoC;KACjD;IACD;QACC,IAAI,EAAE,kBAAkB;QACxB,KAAK,EAAE,wBAAwB;QAC/B,WAAW,EAAE,kCAAkC;KAC/C;IACD;QACC,IAAI,EAAE,gBAAgB;QACtB,KAAK,EAAE,yBAAyB;QAChC,WAAW,EAAE,2BAA2B;KACxC;IAED,4DAA4D;IAC5D;QACC,IAAI,EAAE,mBAAmB;QACzB,KAAK,EAAE,wBAAwB;QAC/B,WAAW,EAAE,+BAA+B;KAC5C;IACD;QACC,IAAI,EAAE,oBAAoB;QAC1B,KAAK,EAAE,wBAAwB;QAC/B,WAAW,EAAE,oBAAoB;KACjC;IACD;QACC,IAAI,EAAE,oBAAoB;QAC1B,KAAK,EAAE,eAAe;QACtB,WAAW,EAAE,qCAAqC;KAClD;IACD;QACC,IAAI,EAAE,yBAAyB;QAC/B,KAAK,EAAE,2BAA2B;QAClC,WAAW,EAAE,mCAAmC;KAChD;IACD;QACC,IAAI,EAAE,sBAAsB;QAC5B,KAAK,EAAE,0BAA0B;QACjC,WAAW,EAAE,wCAAwC;KACrD;CACD,CAAC"}
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
<svg xmlns="http://www.w3.org/2000/svg" width="60" height="60" viewBox="0 0 60 60">
|
|
2
|
+
<rect width="60" height="60" rx="8" fill="white" stroke="#E5E7EB" stroke-width="1"/>
|
|
3
|
+
<polygon points="46.4,12.1 49,7 35.8,7 18.9,40 25.5,52.9" fill="#0098FF"/>
|
|
4
|
+
<polygon points="22,28.6 15.4,15.6 10.9,24.4 17.6,37.3" fill="#0098FF"/>
|
|
5
|
+
</svg>
|
package/package.json
ADDED
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "n8n-nodes-levvex",
|
|
3
|
+
"version": "0.1.0",
|
|
4
|
+
"description": "n8n community node for Levvex — receive webhook events from Levvex platform (purchases, subscriptions, miniapp, events)",
|
|
5
|
+
"keywords": [
|
|
6
|
+
"n8n-community-node-package",
|
|
7
|
+
"n8n",
|
|
8
|
+
"levvex",
|
|
9
|
+
"webhook",
|
|
10
|
+
"ecommerce",
|
|
11
|
+
"infoproduct",
|
|
12
|
+
"checkout",
|
|
13
|
+
"subscription",
|
|
14
|
+
"miniapp"
|
|
15
|
+
],
|
|
16
|
+
"license": "MIT",
|
|
17
|
+
"homepage": "https://github.com/GBSOLUCOES/n8n-nodes-levvex",
|
|
18
|
+
"repository": {
|
|
19
|
+
"type": "git",
|
|
20
|
+
"url": "https://github.com/GBSOLUCOES/n8n-nodes-levvex.git"
|
|
21
|
+
},
|
|
22
|
+
"main": "index.js",
|
|
23
|
+
"scripts": {
|
|
24
|
+
"build": "tsc && gulp build:icons",
|
|
25
|
+
"dev": "tsc --watch",
|
|
26
|
+
"clean": "rimraf dist",
|
|
27
|
+
"prepublishOnly": "npm run build"
|
|
28
|
+
},
|
|
29
|
+
"files": [
|
|
30
|
+
"dist"
|
|
31
|
+
],
|
|
32
|
+
"n8n": {
|
|
33
|
+
"n8nNodesApiVersion": 1,
|
|
34
|
+
"credentials": [
|
|
35
|
+
"dist/credentials/LevvexWebhookApi.credentials.js"
|
|
36
|
+
],
|
|
37
|
+
"nodes": [
|
|
38
|
+
"dist/nodes/LevvexWebhook/LevvexWebhook.trigger.js"
|
|
39
|
+
]
|
|
40
|
+
},
|
|
41
|
+
"devDependencies": {
|
|
42
|
+
"@types/node": "^20.11.0",
|
|
43
|
+
"gulp": "^4.0.2",
|
|
44
|
+
"n8n-workflow": "*",
|
|
45
|
+
"rimraf": "^5.0.5",
|
|
46
|
+
"typescript": "~5.4.0"
|
|
47
|
+
},
|
|
48
|
+
"peerDependencies": {
|
|
49
|
+
"n8n-workflow": "*"
|
|
50
|
+
}
|
|
51
|
+
}
|