n8n 웹 크롤링 및 Markdown 변환 워크플로우 만들기

요즘 자주 쓰고 있는 n8n 에서 몇가지 웹 크롤링 작업을 해보았는데, 생각보다 쉽지가 않았던 기억이 있습니다. 나중을 위해서라도 기록을 남기려고, 몇자 적어 봅니다. 

웹크롤링을 해야 할떄 유용하게 쓰일 수 있을 것 같습니다.




1단계: n8n 설치 및 준비

  • n8n이 설치되어 있지 않다면 설치를 진행합니다
  • n8n을 실행하고 워크플로우 생성을 시작합니다

2단계: 새 워크플로우 생성

  1. n8n 대시보드에서 "New Workflow" 버튼을 클릭합니다
  2. 워크플로우에 "Web Crawler to Markdown"과 같은 이름을 부여합니다

3단계: HTTP Request 노드 추가

  1. "+" 버튼을 클릭하여 노드 추가
  2. 검색창에 "HTTP Request" 입력하고 선택
  3. 다음과 같이 설정합니다:
    • Method: GET
    • URL: 크롤링할 웹사이트 URL 입력 (예: https://example.com)
    • Authentication: 필요한 경우 설정
  4. "Execute Node"를 클릭하여 테스트합니다

4단계: HTML 파싱을 위한 Cheerio 노드 추가

  1. HTTP Request 노드에 연결하여 Cheerio 노드 추가
  2. Cheerio 노드 설정:
    • Source Data: HTML에서 추출할 요소 선택
    • Selector: 필요한 HTML 요소의 CSS 선택자 입력 (예: article, div.content, h1, p)
    • Return Value: "All matching elements"

5단계: Markdown 변환 노드 추가 (Function 노드 사용)

  1. Cheerio 노드에 연결하여 Function 노드 추가
  2. 다음과 같은 코드를 작성하여 HTML을 Markdown으로 변환합니다:
// 결과를 저장할 배열 초기화
const markdownItems = [];

// 각 항목을 Markdown으로 변환
for (const item of items) {
  // HTML 내용을 Markdown으로 변환
  let content = '';
  
  // 제목 추출 (있는 경우)
  if (item.title) {
    content += `# ${item.title}\n\n`;
  }
  
  // 본문 내용 변환
  if (item.content) {
    content += turndownService.turndown(item.content);
  } else if (item.html) {
    content += turndownService.turndown(item.html);
  } else {
    // HTML이 직접 선택자로 추출된 경우
    content += turndownService.turndown(item);
  }
  
  markdownItems.push({
    markdown: content,
    url: $node["HTTP Request"].json.url,
    timestamp: new Date().toISOString()
  });
}

6단계: Write Binary File 노드 추가

  1. Function 노드에 연결하여 Write Binary File 노드 추가
  2. 다음과 같이 설정합니다:
    • File Name: '{{node["HTTP Request"].parameter["url"].split("/")[2]}}-{{ now}}.md'
    • Property Name: 'data'
    • Binary Property: 'data'
    • 파일 내용 설정:
    {{$json["markdown"]}}
    
    ---
    Source: {{$json["url"]}}
    Created: {{$json["timestamp"]}}
    


7단계: Function 노드에서 Markdown 데이터를 바이너리로 변환

Function 노드 코드를 수정하여 바이너리 데이터로 변환합니다:

const TurndownService = require('turndown');
const turndownService = new TurndownService();

// 결과를 저장할 배열 초기화
const markdownItems = [];

// 각 항목을 Markdown으로 변환
for (const item of items) {
  // HTML 내용을 Markdown으로 변환
  let content = '';
  
  // 제목 추출 (있는 경우)
  if (item.title) {
    content += `# ${item.title}\n\n`;
  }
  
  // 본문 내용 변환
  if (item.content) {
    content += turndownService.turndown(item.content);
  } else if (item.html) {
    content += turndownService.turndown(item.html);
  } else {
    // HTML이 직접 선택자로 추출된 경우
    content += turndownService.turndown(item);
  }
  
  // 메타데이터 추가
  const sourceUrl = $node["HTTP Request"].json.url;
  const timestamp = new Date().toISOString();
  const fullContent = `${content}\n\n---\nSource: ${sourceUrl}\nCreated: ${timestamp}`;
  
  // 바이너리 데이터로 변환
  const buffer = Buffer.from(fullContent);
  const base64 = buffer.toString('base64');

  markdownItems.push({
    json: {
      url: sourceUrl,
      timestamp: timestamp,
    },
    binary: {
      data: {
        data: base64,
        mimeType: 'text/markdown',
        fileName: `${sourceUrl.split('/')[2]}-${Date.now()}.md`,
      }
    }
  });
}

return markdownItems;

8단계: 워크플로우 저장 및 테스트

  1. 우측 상단의 "Save" 버튼 클릭
  2. "Execute Workflow" 버튼을 클릭하여 전체 워크플로우 테스트
  3. 실행 결과를 확인하고 필요한 경우 조정

9단계: 워크플로우 자동화 (선택 사항)

  1. 워크플로우가 제대로 작동하면 트리거 노드를 추가하여 자동화 가능:
    • Schedule 트리거: 정기적인 크롤링
    • Webhook 트리거: API 호출로 크롤링 시작

추가 팁:

  • 여러 페이지를 크롤링하려면 "Split In Batches" 노드와 루프를 사용하세요
  • 이미지도 함께 다운로드하려면 추가 HTTP Request 노드가 필요합니다
  • 크롤링 간격을 조절하여 웹사이트 서버에 부담을 주지 않도록 하세요

이렇게 구성하면 웹사이트 콘텐츠를 크롤링하여 마크다운 파일로 변환하는 n8n 워크플로우가 완성됩니다.


Popular posts from this blog

Meta's VideoJam: The Future of AI Video Generation

Switching from ChatGPT Plus to Perplexity Pro: A User’s Perspective

Nintendo Switch 2 Joy-Con Features Excite Developers

Xbox Multiplatform Strategy: Insights from Shawn Layden

White Goat's Farm Adventure with Gemini Image Gen.

Grok 3 Release Date

A Very Simple Agentic AI Implementation

챗GPT 사용법과 마케팅 활용 전략

ComfyUI Tips for Non-Developers