Filtros de Dados
A filtragem de dados é uma operação fundamental para processar e analisar informações de forma eficiente. Esta seção aborda como aplicar filtros, criar condições complexas e otimizar o processamento de dados no n8n.
Visão Geral
Filtros permitem selecionar dados específicos baseados em critérios definidos, reduzindo o volume de informações processadas e melhorando a performance dos workflows. No n8n, você pode filtrar dados usando:
- Filtros simples por valor
- Condições complexas com operadores lógicos
- Filtros baseados em expressões JavaScript
- Filtros temporais para datas
- Filtros de texto com regex
Tipos de Filtros
Filtros por Valor
Filtros básicos baseados em valores específicos:
javascript\n// Filtrar por valor exato\nconst filtrarPorValor = (dados, campo, valor) => {\n return dados.filter(item => item[campo] === valor);\n};\n\n// Exemplo: Filtrar clientes ativos\nconst clientesAtivos = filtrarPorValor(clientes, 'status', 'ativo');\n\n// Filtrar por múltiplos valores\nconst filtrarPorValores = (dados, campo, valores) => {\n return dados.filter(item => valores.includes(item[campo]));\n};\n\n// Exemplo: Filtrar por estados específicos\nconst estadosFiltrados = filtrarPorValores(clientes, 'estado', ['SP', 'RJ', 'MG']);\n
\n\n### Filtros Numéricos\n\nFiltros para valores numéricos com operadores de comparação:\n\njavascript\n// Filtrar por faixa de valores\nconst filtrarPorFaixa = (dados, campo, min, max) => {\n return dados.filter(item => {\n const valor = parseFloat(item[campo]);\n return valor >= min && valor <= max;\n });\n};\n\n// Exemplo: Filtrar produtos por preço\nconst produtosBaratos = filtrarPorFaixa(produtos, 'preco', 0, 100);\nconst produtosCaros = filtrarPorFaixa(produtos, 'preco', 500, 9999);\n\n// Filtrar por valor mínimo\nconst filtrarMinimo = (dados, campo, valor) => {\n return dados.filter(item => parseFloat(item[campo]) >= valor);\n};\n\n// Exemplo: Filtrar vendas acima de R$ 1000\nconst vendasAltas = filtrarMinimo(vendas, 'valor', 1000);\n
\n\n### Filtros de Texto\n\nFiltros para processamento de strings e texto:\n\njavascript\n// Filtrar por texto contido\nconst filtrarPorTexto = (dados, campo, texto) => {\n return dados.filter(item => \n item[campo].toLowerCase().includes(texto.toLowerCase())\n );\n};\n\n// Exemplo: Filtrar produtos por nome\nconst produtosEletronicos = filtrarPorTexto(produtos, 'nome', 'eletrônico');\n\n// Filtrar por regex\nconst filtrarPorRegex = (dados, campo, padrao) => {\n const regex = new RegExp(padrao, 'i');\n return dados.filter(item => regex.test(item[campo]));\n};\n\n// Exemplo: Filtrar emails válidos\nconst emailsValidos = filtrarPorRegex(clientes, 'email', '^[^@]+@[^@]+\\.[^@]+$');\n\n// Filtrar por início de texto\nconst filtrarPorInicio = (dados, campo, prefixo) => {\n return dados.filter(item => \n item[campo].toLowerCase().startsWith(prefixo.toLowerCase())\n );\n};\n\n// Exemplo: Filtrar clientes por nome\nconst clientesJoao = filtrarPorInicio(clientes, 'nome', 'João');\n
\n\n### Filtros Temporais\n\nFiltros para datas e timestamps:\n\njavascript\n// Filtrar por período\nconst filtrarPorPeriodo = (dados, campo, inicio, fim) => {\n const dataInicio = new Date(inicio);\n const dataFim = new Date(fim);\n \n return dados.filter(item => {\n const data = new Date(item[campo]);\n return data >= dataInicio && data <= dataFim;\n });\n};\n\n// Exemplo: Filtrar vendas do último mês\nconst hoje = new Date();\nconst inicioMes = new Date(hoje.getFullYear(), hoje.getMonth(), 1);\nconst vendasMes = filtrarPorPeriodo(vendas, 'data', inicioMes, hoje);\n\n// Filtrar por data específica\nconst filtrarPorData = (dados, campo, data) => {\n const dataFiltro = new Date(data);\n return dados.filter(item => {\n const itemData = new Date(item[campo]);\n return itemData.toDateString() === dataFiltro.toDateString();\n });\n};\n\n// Filtrar por período relativo\nconst filtrarPeriodoRelativo = (dados, campo, dias) => {\n const hoje = new Date();\n const inicio = new Date(hoje.getTime() - (dias * 24 * 60 * 60 * 1000));\n \n return dados.filter(item => {\n const data = new Date(item[campo]);\n return data >= inicio && data <= hoje;\n });\n};\n\n// Exemplo: Filtrar registros dos últimos 7 dias\nconst registrosRecentes = filtrarPeriodoRelativo(registros, 'dataCriacao', 7);\n
\n\n## Filtros Complexos\n\n### Filtros com Múltiplas Condições\n\nCombine diferentes critérios usando operadores lógicos:\n\njavascript\n// Filtro AND (todas as condições devem ser verdadeiras)\nconst filtrarAND = (dados, condicoes) => {\n return dados.filter(item => {\n return condicoes.every(condicao => {\n const { campo, operador, valor } = condicao;\n \n switch (operador) {\n case '==':\n return item[campo] === valor;\n case '!=':\n return item[campo] !== valor;\n case '>':\n return parseFloat(item[campo]) > valor;\n case '<':\n return parseFloat(item[campo]) < valor;\n case '>=':\n return parseFloat(item[campo]) >= valor;\n case '<=':\n return parseFloat(item[campo]) <= valor;\n case 'contains':\n return item[campo].toLowerCase().includes(valor.toLowerCase());\n case 'startsWith':\n return item[campo].toLowerCase().startsWith(valor.toLowerCase());\n default:\n return false;\n }\n });\n });\n};\n\n// Exemplo: Filtrar clientes ativos de SP com valor > 1000\nconst clientesFiltrados = filtrarAND(clientes, [\n { campo: 'status', operador: '==', valor: 'ativo' },\n { campo: 'estado', operador: '==', valor: 'SP' },\n { campo: 'valor', operador: '>', valor: 1000 }\n]);\n\n// Filtro OR (pelo menos uma condição deve ser verdadeira)\nconst filtrarOR = (dados, condicoes) => {\n return dados.filter(item => {\n return condicoes.some(condicao => {\n const { campo, operador, valor } = condicao;\n \n switch (operador) {\n case '==':\n return item[campo] === valor;\n case '!=':\n return item[campo] !== valor;\n case '>':\n return parseFloat(item[campo]) > valor;\n case '<':\n return parseFloat(item[campo]) < valor;\n case 'contains':\n return item[campo].toLowerCase().includes(valor.toLowerCase());\n default:\n return false;\n }\n });\n });\n};\n\n// Exemplo: Filtrar clientes de SP ou RJ\nconst clientesSPouRJ = filtrarOR(clientes, [\n { campo: 'estado', operador: '==', valor: 'SP' },\n { campo: 'estado', operador: '==', valor: 'RJ' }\n]);\n
\n\n### Filtros Aninhados\n\nFiltros para estruturas de dados complexas:\n\njavascript\n// Filtrar por propriedades aninhadas\nconst filtrarAninhado = (dados, caminho, valor) => {\n return dados.filter(item => {\n const valorAninhado = obterValorAninhado(item, caminho);\n return valorAninhado === valor;\n });\n};\n\nconst obterValorAninhado = (objeto, caminho) => {\n return caminho.split('.').reduce((obj, prop) => obj?.[prop], objeto);\n};\n\n// Exemplo: Filtrar por cidade do endereço\nconst clientesSaoPaulo = filtrarAninhado(clientes, 'endereco.cidade', 'São Paulo');\n\n// Filtrar arrays aninhados\nconst filtrarArrayAninhado = (dados, campoArray, criterio) => {\n return dados.filter(item => {\n const array = item[campoArray];\n if (!Array.isArray(array)) return false;\n \n return array.some(elemento => {\n return Object.entries(criterio).every(([campo, valor]) => \n elemento[campo] === valor\n );\n });\n });\n};\n\n// Exemplo: Filtrar clientes que têm pedido com status "pendente"\nconst clientesComPedidoPendente = filtrarArrayAninhado(clientes, 'pedidos', {\n status: 'pendente'\n});\n
\n\n## Filtros Específicos para Dados Brasileiros\n\n### Filtros de CPF/CNPJ\n\njavascript\n// Filtrar por tipo de documento\nconst filtrarPorTipoDocumento = (dados, campo, tipo) => {\n return dados.filter(item => {\n const documento = item[campo].replace(/[^\d]/g, '');\n \n if (tipo === 'CPF') {\n return documento.length === 11;\n } else if (tipo === 'CNPJ') {\n return documento.length === 14;\n }\n \n return false;\n });\n};\n\n// Exemplo: Separar pessoas físicas e jurídicas\nconst pessoasFisicas = filtrarPorTipoDocumento(clientes, 'documento', 'CPF');\nconst pessoasJuridicas = filtrarPorTipoDocumento(clientes, 'documento', 'CNPJ');\n\n// Filtrar por estado baseado no CPF\nconst filtrarPorEstadoCPF = (dados, campo, estado) => {\n const codigosEstado = {\n 'SP': [1, 2, 3, 4, 5, 6, 7, 8, 9],\n 'RJ': [20, 21, 22, 23, 24],\n 'MG': [30, 31, 32, 33, 34, 35, 36, 37, 38, 39],\n 'RS': [40, 41, 42, 43, 44, 45, 46, 47, 48, 49]\n };\n \n const codigos = codigosEstado[estado] || [];\n \n return dados.filter(item => {\n const cpf = item[campo].replace(/[^\d]/g, '');\n const codigo = parseInt(cpf.substring(8, 10));\n return codigos.includes(codigo);\n });\n};\n
\n\n### Filtros de CEP\n\njavascript\n// Filtrar por região baseada no CEP\nconst filtrarPorRegiaoCEP = (dados, campo, regiao) => {\n const regioesCEP = {\n 'Norte': ['69', '68', '67', '66', '65', '64', '63'],\n 'Nordeste': ['59', '58', '57', '56', '55', '54', '53', '52', '51', '50', '49', '48', '47', '46', '45', '44', '43', '42', '41', '40'],\n 'Centro-Oeste': ['79', '78', '77', '76', '75', '74', '73', '72', '71', '70'],\n 'Sudeste': ['39', '38', '37', '36', '35', '34', '33', '32', '31', '30', '29', '28', '27', '26', '25', '24', '23', '22', '21', '20'],\n 'Sul': ['99', '98', '97', '96', '95', '94', '93', '92', '91', '90', '89', '88', '87', '86', '85', '84', '83', '82', '81', '80']\n };\n \n const prefixos = regioesCEP[regiao] || [];\n \n return dados.filter(item => {\n const cep = item[campo].replace(/[^\d]/g, '');\n const prefixo = cep.substring(0, 2);\n return prefixos.includes(prefixo);\n });\n};\n\n// Exemplo: Filtrar clientes do Sudeste\nconst clientesSudeste = filtrarPorRegiaoCEP(clientes, 'endereco.cep', 'Sudeste');\n
\n\n## Otimização de Filtros\n\n### Filtros em Lote\n\nProcesse grandes volumes de dados eficientemente:\n\njavascript\n// Filtrar em lotes para melhor performance\nconst filtrarEmLotes = (dados, filtro, tamanhoLote = 1000) => {\n const resultados = [];\n \n for (let i = 0; i < dados.length; i += tamanhoLote) {\n const lote = dados.slice(i, i + tamanhoLote);\n const loteFiltrado = lote.filter(filtro);\n resultados.push(...loteFiltrado);\n }\n \n return resultados;\n};\n\n// Exemplo: Filtrar grandes volumes de dados\nconst dadosGrandes = Array.from({length: 100000}, (_, i) => ({\n id: i,\n valor: Math.random() * 1000,\n status: Math.random() > 0.5 ? 'ativo' : 'inativo'\n}));\n\nconst dadosFiltrados = filtrarEmLotes(dadosGrandes, item => \n item.status === 'ativo' && item.valor > 500\n);\n
\n\n### Filtros com Cache\n\nUse cache para filtros frequentemente aplicados:\n\njavascript\n// Cache de filtros\nconst cacheFiltros = new Map();\n\nconst filtrarComCache = (dados, criterios, chaveCache) => {\n // Verificar cache\n if (cacheFiltros.has(chaveCache)) {\n const { resultado, timestamp } = cacheFiltros.get(chaveCache);\n const agora = Date.now();\n \n // Cache válido por 5 minutos\n if (agora - timestamp < 5 * 60 * 1000) {\n return resultado;\n }\n }\n \n // Aplicar filtro\n const resultado = dados.filter(item => {\n return criterios.every(criterio => {\n const { campo, operador, valor } = criterio;\n \n switch (operador) {\n case '==':\n return item[campo] === valor;\n case '>':\n return parseFloat(item[campo]) > valor;\n case 'contains':\n return item[campo].toLowerCase().includes(valor.toLowerCase());\n default:\n return false;\n }\n });\n });\n \n // Salvar no cache\n cacheFiltros.set(chaveCache, {\n resultado,\n timestamp: Date.now()\n });\n \n return resultado;\n};\n\n// Exemplo: Filtrar com cache\nconst clientesAtivosSP = filtrarComCache(\n clientes,\n [\n { campo: 'status', operador: '==', valor: 'ativo' },\n { campo: 'estado', operador: '==', valor: 'SP' }\n ],\n 'clientes_ativos_sp'\n);\n
\n\n## Filtros Avançados\n\n### Filtros Fuzzy\n\nFiltros que toleram erros de digitação:\n\njavascript\n// Filtro fuzzy para texto\nconst filtrarFuzzy = (dados, campo, termo, tolerancia = 0.8) => {\n return dados.filter(item => {\n const valor = item[campo].toLowerCase();\n const termoBusca = termo.toLowerCase();\n \n // Calcular similaridade\n const similaridade = calcularSimilaridade(valor, termoBusca);\n return similaridade >= tolerancia;\n });\n};\n\n// Algoritmo de similaridade simples (Levenshtein)\nconst calcularSimilaridade = (str1, str2) => {\n const matrix = [];\n \n for (let i = 0; i <= str2.length; i++) {\n matrix[i] = [i];\n }\n \n for (let j = 0; j <= str1.length; j++) {\n matrix[0][j] = j;\n }\n \n for (let i = 1; i <= str2.length; i++) {\n for (let j = 1; j <= str1.length; j++) {\n if (str2.charAt(i - 1) === str1.charAt(j - 1)) {\n matrix[i][j] = matrix[i - 1][j - 1];\n } else {\n matrix[i][j] = Math.min(\n matrix[i - 1][j - 1] + 1,\n matrix[i][j - 1] + 1,\n matrix[i - 1][j] + 1\n );\n }\n }\n }\n \n const distancia = matrix[str2.length][str1.length];\n const maxLength = Math.max(str1.length, str2.length);\n \n return 1 - (distancia / maxLength);\n};\n\n// Exemplo: Busca fuzzy por nome\nconst clientesJoao = filtrarFuzzy(clientes, 'nome', 'João', 0.7);\n
\n\n### Filtros Temporais Avançados\n\njavascript\n// Filtrar por dia da semana\nconst filtrarPorDiaSemana = (dados, campo, dias) => {\n return dados.filter(item => {\n const data = new Date(item[campo]);\n const diaSemana = data.getDay(); // 0 = Domingo, 1 = Segunda, etc.\n return dias.includes(diaSemana);\n });\n};\n\n// Exemplo: Filtrar vendas de segunda a sexta\nconst vendasSemana = filtrarPorDiaSemana(vendas, 'data', [1, 2, 3, 4, 5]);\n\n// Filtrar por horário\nconst filtrarPorHorario = (dados, campo, horaInicio, horaFim) => {\n return dados.filter(item => {\n const data = new Date(item[campo]);\n const hora = data.getHours();\n return hora >= horaInicio && hora <= horaFim;\n });\n};\n\n// Exemplo: Filtrar transações em horário comercial\nconst transacoesComerciais = filtrarPorHorario(transacoes, 'timestamp', 8, 18);\n
\n\n## Workflows de Filtragem\n\n### Workflow: Filtro de Dados em Tempo Real\n\nmermaid\ngraph TD\n A[Webhook Trigger] --> B[HTTP Request: Buscar Dados]\n B --> C[Filter: Dados Válidos]\n C --> D[Filter: Critérios de Negócio]\n D --> E[Transform: Formatar Dados]\n E --> F[HTTP Request: Salvar Resultados]\n F --> G[Send Notification]\n
\n\n### Workflow: Análise de Dados Filtrados\n\nmermaid\ngraph TD\n A[Schedule Trigger] --> B[HTTP Request: Dados Brutos]\n B --> C[Filter: Período Específico]\n C --> D[Filter: Região Geográfica]\n D --> E[Aggregate: Calcular Métricas]\n E --> F[Generate Report]\n F --> G[Send Email]\n
Boas Práticas
Performance
- Aplique filtros cedo no pipeline de dados
- Use índices para campos frequentemente filtrados
- Processe em lotes para grandes volumes
- Cache resultados de filtros complexos
- Monitore performance de filtros
Manutenibilidade
- Documente critérios de filtro
- Use constantes para valores mágicos
- Crie funções reutilizáveis para filtros comuns
- Teste filtros com dados reais
- Valide resultados de filtros
Flexibilidade
- Torne filtros configuráveis via parâmetros
- Suporte múltiplos formatos de entrada
- Permita combinação de filtros
- Forneça valores padrão para filtros opcionais
- Implemente fallbacks para casos especiais
Recursos Adicionais
Ferramentas Úteis
- Lodash: Biblioteca com funções de filtragem avançadas
- Ramda: Biblioteca funcional para manipulação de dados
- date-fns: Biblioteca para manipulação de datas
- validator.js: Validação de dados
Padrões de Filtro
- Builder Pattern: Construir filtros complexos
- Strategy Pattern: Diferentes algoritmos de filtro
- Chain of Responsibility: Pipeline de filtros
- Observer Pattern: Notificações de mudanças
Próximo: Edição de Dados - Modifique e transforme dados