This workflow follows the Chainllm → OpenAI Chat recipe pattern — see all workflows that pair these two integrations.
The workflow JSON
Copy or download the full n8n JSON below. Paste it into a new n8n workflow, add your credentials, activate. Full import guide →
{
"name": "Jour 1 - Prompting Metier et Confidentialite",
"nodes": [
{
"parameters": {
"content": "## Jour 1 \u2014 Prompting M\u00e9tier & Confidentialit\u00e9\n\n**Flux :**\n1. **Contexte d'audit** (Set) \u2014 d\u00e9finit la clause \u00e0 analyser\n2. **Analyser clause** (Basic LLM Chain) \u2014 envoie le prompt au mod\u00e8le et impose le sch\u00e9ma JSON via le sous-n\u0153ud *Format JSON attendu*\n3. **Extraire champs** (Set) \u2014 rend visibles les 5 champs attendus\n4. **Sensibilit\u00e9 valide ?** (If) \u2014 v\u00e9rifie que `niveau_sensibilite` vaut Faible, Moyen ou Eleve\n5. **R\u00e9sultat OK / Erreur format** \u2014 deux branches lisibles\n\n**Point p\u00e9dagogique :** le Basic LLM Chain + Structured Output Parser garantit le format sans code. L'Agent (jours 2+) est r\u00e9serv\u00e9 aux workflows avec tools.\n\n**\u00c0 montrer :** changer la clause dans *Contexte d'audit*, ex\u00e9cuter, ouvrir *Extraire champs* pour voir le JSON, v\u00e9rifier la branche IF.",
"height": 320,
"width": 560,
"color": 5
},
"id": "d1-sticky-overview",
"name": "Vue d'ensemble",
"type": "n8n-nodes-base.stickyNote",
"typeVersion": 1,
"position": [
0,
0
]
},
{
"parameters": {},
"id": "d1-trigger",
"name": "D\u00e9clencheur Manuel",
"type": "n8n-nodes-base.manualTrigger",
"typeVersion": 1,
"position": [
280,
360
]
},
{
"parameters": {
"content": "**Set \u2014 Contexte d'audit**\n\nModifie `clause` pour tester une autre clause contractuelle.\n\nLa check-list RGPD et les consignes mod\u00e8le sont des r\u00e9f\u00e9rences p\u00e9dagogiques inject\u00e9es dans le prompt.",
"height": 180,
"width": 320,
"color": 7
},
"id": "d1-sticky-set",
"name": "Note Set",
"type": "n8n-nodes-base.stickyNote",
"typeVersion": 1,
"position": [
500,
140
]
},
{
"parameters": {
"mode": "manual",
"assignments": {
"assignments": [
{
"id": "d1-clause",
"name": "clause",
"value": "Prime annuelle li\u00e9e \u00e0 la performance, calcul\u00e9e sur la r\u00e9mun\u00e9ration brute, avec exclusion des absences injustifi\u00e9es.",
"type": "string"
},
{
"id": "d1-chatinput",
"name": "chatInput",
"value": "Analysez cette clause de paie et retournez un objet json : Prime annuelle li\u00e9e \u00e0 la performance, calcul\u00e9e sur la r\u00e9mun\u00e9ration brute, avec exclusion des absences injustifi\u00e9es.",
"type": "string"
},
{
"id": "d1-rgpd-1",
"name": "rgpd_1",
"value": "Supprimer les noms, NIR et identifiants avant traitement",
"type": "string"
},
{
"id": "d1-rgpd-2",
"name": "rgpd_2",
"value": "Ne pas envoyer de fichier brut contenant des donn\u00e9es personnelles vers une IA publique",
"type": "string"
},
{
"id": "d1-rgpd-3",
"name": "rgpd_3",
"value": "V\u00e9rifier le cadre RGPD et le secret professionnel avant toute exfiltration",
"type": "string"
},
{
"id": "d1-model-1",
"name": "conseil_modele_1",
"value": "Utiliser un mod\u00e8le de raisonnement pour une clause complexe",
"type": "string"
},
{
"id": "d1-model-2",
"name": "conseil_modele_2",
"value": "Garder une temp\u00e9rature basse (0) pour privil\u00e9gier la fiabilit\u00e9",
"type": "string"
},
{
"id": "d1-model-3",
"name": "conseil_modele_3",
"value": "Demander des justifications factuelles et non des suppositions",
"type": "string"
}
]
},
"options": {}
},
"id": "d1-set",
"name": "Contexte d'audit",
"type": "n8n-nodes-base.set",
"typeVersion": 3.4,
"position": [
500,
360
]
},
{
"parameters": {
"content": "**Basic LLM Chain \u2014 Analyser clause**\n\n\u00c0 montrer aux participants :\n- *Basic LLM Chain* = un prompt \u2192 une r\u00e9ponse structur\u00e9e. Pas de tools, pas de m\u00e9moire.\n- Le sous-n\u0153ud *Format JSON attendu* (Structured Output Parser) impose le sch\u00e9ma.\n- Le sous-n\u0153ud *Ollama* fournit le mod\u00e8le.\n\n**Diff\u00e9rence avec l'Agent (jours 2+) :** l'Agent peut appeler des tools et boucler. Ici on veut juste une r\u00e9ponse JSON fiable.",
"height": 240,
"width": 360,
"color": 7
},
"id": "d1-sticky-chain",
"name": "Note LLM Chain",
"type": "n8n-nodes-base.stickyNote",
"typeVersion": 1,
"position": [
760,
100
]
},
{
"parameters": {
"prompt": {
"values": [
{
"type": "HumanMessagePromptTemplate",
"message": "={{ $json.chatInput }}"
}
]
},
"hasOutputParser": true,
"options": {
"systemMessage": "Tu es un auditeur paie senior. On te soumet une clause contractuelle anonymis\u00e9e.\n\nR\u00e9ponds UNIQUEMENT avec un objet JSON valide (format json). Aucun texte en dehors du JSON.\n\nChamps obligatoires :\n- `lecture_metier` : r\u00e9sum\u00e9 m\u00e9tier court (string)\n- `risques_audit` : liste de risques (array de strings)\n- `questions_de_controle` : liste d'objets {question: string}\n- `anonymisation_requise` : bool\u00e9en\n- `niveau_sensibilite` : exactement `Faible`, `Moyen` ou `Eleve`\n\nSi la clause ne permet pas de conclure, ajoute une question de contr\u00f4le plut\u00f4t qu'une affirmation. Aucune donn\u00e9e nominative."
}
},
"id": "d1-chain",
"name": "Analyser clause",
"type": "@n8n/n8n-nodes-langchain.chainLlm",
"typeVersion": 1.4,
"position": [
760,
360
]
},
{
"parameters": {
"content": "**Extraire champs** (Set)\n\nRend visible chaque champ de la r\u00e9ponse du mod\u00e8le.\nOuvrir ce n\u0153ud apr\u00e8s ex\u00e9cution pour voir le r\u00e9sultat.\n\n**Sensibilit\u00e9 valide ?** (If)\n- Branche **true** = format respect\u00e9\n- Branche **false** = valeur inattendue, montrer l'erreur aux participants",
"height": 200,
"width": 340,
"color": 7
},
"id": "d1-sticky-extract",
"name": "Note Extraction",
"type": "n8n-nodes-base.stickyNote",
"typeVersion": 1,
"position": [
1020,
140
]
},
{
"parameters": {
"mode": "manual",
"assignments": {
"assignments": [
{
"id": "d1-extract-1",
"name": "lecture_metier",
"value": "={{ $json.output?.lecture_metier ?? $json.text?.lecture_metier ?? $json.lecture_metier }}",
"type": "string"
},
{
"id": "d1-extract-2",
"name": "risques_audit",
"value": "={{ $json.output?.risques_audit ?? $json.text?.risques_audit ?? $json.risques_audit }}",
"type": "array"
},
{
"id": "d1-extract-3",
"name": "questions_de_controle",
"value": "={{ $json.output?.questions_de_controle ?? $json.text?.questions_de_controle ?? $json.questions_de_controle }}",
"type": "array"
},
{
"id": "d1-extract-4",
"name": "anonymisation_requise",
"value": "={{ $json.output?.anonymisation_requise ?? $json.text?.anonymisation_requise ?? $json.anonymisation_requise }}",
"type": "boolean"
},
{
"id": "d1-extract-5",
"name": "niveau_sensibilite",
"value": "={{ ({faible: 'Faible', moyen: 'Moyen', eleve: 'Eleve', \u00e9lev\u00e9: 'Eleve'}[(($json.output?.niveau_sensibilite ?? $json.text?.niveau_sensibilite ?? $json.niveau_sensibilite) || '').toString().trim().toLowerCase()] ?? ($json.output?.niveau_sensibilite ?? $json.text?.niveau_sensibilite ?? $json.niveau_sensibilite)) }}",
"type": "string"
},
{
"id": "d1-extract-6",
"name": "clause_analysee",
"value": "={{ $('Contexte d\\'audit').item.json.clause }}",
"type": "string"
}
]
},
"options": {}
},
"id": "d1-extract",
"name": "Extraire champs",
"type": "n8n-nodes-base.set",
"typeVersion": 3.4,
"position": [
1020,
360
]
},
{
"parameters": {
"conditions": {
"options": {
"caseSensitive": true
},
"conditions": [
{
"id": "d1-if-valid-sensitivity",
"leftValue": "={{ ['Faible', 'Moyen', 'Eleve'].includes($json.niveau_sensibilite) }}",
"rightValue": true,
"operator": {
"type": "boolean",
"operation": "true"
}
}
],
"combinator": "and"
}
},
"id": "d1-if",
"name": "Sensibilite valide ?",
"type": "n8n-nodes-base.if",
"typeVersion": 2,
"position": [
1260,
360
]
},
{
"parameters": {
"mode": "manual",
"assignments": {
"assignments": [
{
"id": "d1-ok-1",
"name": "validation_format",
"value": "ok",
"type": "string"
},
{
"id": "d1-ok-2",
"name": "message",
"value": "Format respect\u00e9 \u2014 ouvrir ce n\u0153ud pour voir l'analyse compl\u00e8te",
"type": "string"
}
]
},
"options": {}
},
"id": "d1-result-ok",
"name": "Resultat OK",
"type": "n8n-nodes-base.set",
"typeVersion": 3.4,
"position": [
1500,
260
]
},
{
"parameters": {
"mode": "manual",
"assignments": {
"assignments": [
{
"id": "d1-err-1",
"name": "validation_format",
"value": "erreur",
"type": "string"
},
{
"id": "d1-err-2",
"name": "message",
"value": "={{ 'niveau_sensibilite invalide : ' + $json.niveau_sensibilite + ' \u2014 attendu : Faible, Moyen ou Eleve' }}",
"type": "string"
}
]
},
"options": {}
},
"id": "d1-result-err",
"name": "Erreur format",
"type": "n8n-nodes-base.set",
"typeVersion": 3.4,
"position": [
1500,
460
]
},
{
"parameters": {
"jsonSchemaExample": "{\n \"lecture_metier\": \"r\u00e9sum\u00e9 m\u00e9tier court\",\n \"risques_audit\": [\"risque 1\", \"risque 2\"],\n \"questions_de_controle\": [{\"question\": \"question \u00e0 poser\"}],\n \"anonymisation_requise\": false,\n \"niveau_sensibilite\": \"Moyen\"\n}"
},
"id": "d1-output-parser",
"name": "Format JSON attendu",
"type": "@n8n/n8n-nodes-langchain.outputParserStructured",
"typeVersion": 1.2,
"position": [
760,
560
]
},
{
"parameters": {
"model": {
"__rl": true,
"value": "gpt-4.1-nano",
"mode": "id"
},
"options": {
"temperature": 0
}
},
"id": "d1-openai",
"name": "OpenAI Gateway",
"type": "@n8n/n8n-nodes-langchain.lmChatOpenAi",
"typeVersion": 1.2,
"position": [
760,
560
],
"credentials": {
"openAiApi": {
"name": "<your credential>"
}
}
},
{
"parameters": {
"content": "**Exemples de clauses \u00e0 tester**\n\n- Prime annuelle li\u00e9e \u00e0 la performance\n- Indemnit\u00e9 de d\u00e9part \u00e0 la retraite\n- Clause de non-concurrence r\u00e9mun\u00e9r\u00e9e\n- Majoration pour travail de nuit\n- Cotisation patronale de pr\u00e9voyance",
"height": 160,
"width": 300,
"color": 3
},
"id": "d1-sticky-examples",
"name": "Exemples",
"type": "n8n-nodes-base.stickyNote",
"typeVersion": 1,
"position": [
0,
280
]
}
],
"connections": {
"D\u00e9clencheur Manuel": {
"main": [
[
{
"node": "Contexte d'audit",
"type": "main",
"index": 0
}
]
]
},
"Contexte d'audit": {
"main": [
[
{
"node": "Analyser clause",
"type": "main",
"index": 0
}
]
]
},
"Analyser clause": {
"main": [
[
{
"node": "Extraire champs",
"type": "main",
"index": 0
}
]
]
},
"Extraire champs": {
"main": [
[
{
"node": "Sensibilite valide ?",
"type": "main",
"index": 0
}
]
]
},
"Sensibilite valide ?": {
"main": [
[
{
"node": "Resultat OK",
"type": "main",
"index": 0
}
],
[
{
"node": "Erreur format",
"type": "main",
"index": 0
}
]
]
},
"OpenAI Gateway": {
"ai_languageModel": [
[
{
"node": "Analyser clause",
"type": "ai_languageModel",
"index": 0
}
]
]
},
"Format JSON attendu": {
"ai_outputParser": [
[
{
"node": "Analyser clause",
"type": "ai_outputParser",
"index": 0
}
]
]
}
},
"settings": {
"executionOrder": "v1"
},
"meta": {
"description": "Jour 1 - Prompting m\u00e9tier structur\u00e9: Set injecte la clause, Agent Auditeur demande un JSON strict, Code v\u00e9rifie la sortie et rend les erreurs visibles."
}
}
Credentials you'll need
Each integration node will prompt for credentials when you import. We strip credential IDs before publishing — you'll add your own.
openAiApi
For the full experience including quality scoring and batch install features for each workflow upgrade to Pro
About this workflow
Jour 1 - Prompting Metier et Confidentialite. Uses chainLlm, outputParserStructured, lmChatOpenAi. Event-driven trigger; 14 nodes.
Source: https://github.com/ssime-git/agentic_ai_auditing/blob/cf2b4946b77f32b80504627780437ebf85e6f60b/n8n/workflows/day1_acculturation.json — original creator credit. Request a take-down →
Related workflows
Workflows that share integrations, category, or trigger type with this one. All free to copy and import.
This template attempts to replicate OpenAI's DeepResearch feature which, at time of writing, is only available to their pro subscribers.
The best content automation template in the market is now even better—with “deep research” on time-sensitive topics\! Unlike most n8n content automation templates that are mainly for “demo purposes,”
Typeform IA - YT. Uses typeformTrigger, agent, lmChatOpenAi, toolWorkflow. Event-driven trigger; 75 nodes.
My workflow 53. Uses formTrigger, httpRequest, lmChatOpenAi, form. Event-driven trigger; 74 nodes.
Episode 23: UGC with nanobanana. Uses lmChatOpenAi, lmChatOllama, lmChatDeepSeek, lmChatOpenRouter. Event-driven trigger; 74 nodes.