Electron의 IPC 통신 방법
Electron의 IPC 통신 방법에 대해 학습합니다
게시글 목적
> Electron을 이해하고 electron에서 IPC 통신을 어떻게 하는지 설명합니다.
추천대상
> Electron을 입문하는 개발자, 본인이 만든 React 프로젝트를 데스크 어플리케이션으로 만들고 싶은 개발자.
본문
> Electron은 웹 개발을 위한 자바스크립트 기반의 오픈 소스 프레임워크로, 데스크톱 애플리케이션을 개발하는 데 사용됩니다.
Electron의 폴더 구조
Electron 프로젝트는 일반적으로 다음과 같은 폴더 구조를 가지고 있습니다:
- main.js: Electron의 메인 프로세스를 정의하는 파일입니다. 이 파일에서는 주요 창을 생성하고 IPC 통신을 설정하는 등의 작업을 수행합니다.
- renderer.js: Electron의 렌더러 프로세스를 정의하는 파일입니다. 이 파일에서는 웹 페이지를 렌더링하고 IPC 통신을 처리하는 등의 작업을 수행합니다.
- index.html: Electron 애플리케이션의 첫 번째로 로드되는 HTML 파일입니다. 이 파일에서는 웹 페이지의 구조 및 내용을 정의합니다.
- package.json: Electron 애플리케이션의 설정 정보와 종속성을 정의하는 파일입니다.
- node_modules: Electron 애플리케이션에 필요한 외부 모듈이 설치되는 폴더입니다.
- assets: 애플리케이션에 사용되는 이미지, 아이콘 등의 자원 파일이 저장되는 폴더입니다.
- styles: 애플리케이션의 스타일 시트 파일이 저장되는 폴더입니다.
이 외에도 필요에 따라 추가적인 폴더나 파일을 생성할 수 있습니다. Electron의 폴더 구조는 프로젝트의 규모와 요구사항에 따라 다양하게 조정될 수 있습니다.
main 프로세스
- Electron 애플리케이션의 메인 프로세스를 정의합니다.
- 주요 창을 생성하고 관리합니다.
- 웹 페이지에 접근하지 않고 시스템 리소스에 접근하고 네이티브 기능을 사용할 수 있습니다.
- IPC 통신을 설정하고 렌더러 프로세스와 통신합니다.
renderer 프로세스
- Electron 애플리케이션의 렌더러 프로세스를 정의합니다.
- 웹 페이지를 렌더링하고 사용자와 상호작용합니다.
- IPC 통신을 통해 main 프로세스와 통신하고 필요한 데이터를 주고받을 수 있습니다.
- 보안을 강화하기 위해 시스템 리소스에 직접 접근하지 않습니다.
- 여러 개의 렌더러 프로세스를 동시에 실행하여 성능을 향상시킬 수 있습니다.
Electron에서 프로세스가 main 프로세스와 renderer 프로세스로 구분되어 있는 이유는 다음과 같습니다:
1. 보안: Electron은 Chromium 기반으로 동작하며, 웹 페이지를 렌더링하는 부분과 시스템 리소스에 접근하는 부분을 분리함으로써 보안을 강화합니다. 렌더러 프로세스는 웹 페이지를 표시하고 사용자와 상호작용하는 역할을 담당하며, main 프로세스는 시스템 자원에 접근하고 네이티브 기능을 사용하는 역할을 담당합니다. 이렇게 분리함으로써 악성 코드가 웹 페이지에서 시스템에 접근하는 것을 방지할 수 있습니다.
2. 성능: Electron은 Chromium의 멀티 프로세스 아키텍처를 사용하여 여러 개의 렌더러 프로세스를 동시에 실행할 수 있습니다. 이를 통해 렌더링 작업을 병렬로 처리하고, 한 프로세스가 충돌하더라도 다른 프로세스는 계속해서 동작할 수 있습니다. 또한 main 프로세스와 렌더러 프로세스 간의 통신을 비동기적으로 처리하므로, 애플리케이션의 응답성과 성능을 향상시킬 수 있습니다.
3. 모듈 분리: main 프로세스와 렌더러 프로세스는 각각 별도의 JavaScript 컨텍스트를 가지고 있으며, 모듈 시스템을 통해 필요한 모듈을 독립적으로 로드할 수 있습니다. 이를 통해 코드의 유지보수성과 재사용성을 높일 수 있습니다. 또한, main 프로세스와 렌더러 프로세스 간의 통신을 통해 데이터를 주고받을 수 있으므로, 애플리케이션의 다양한 부분 간에 상호작용이 가능합니다.
따라서, main 프로세스와 renderer 프로세스의 구분은 보안, 성능, 모듈 분리 등의 이점을 제공하여 Electron 애플리케이션을 더욱 안정적이고 효율적으로 개발할 수 있도록 합니다.
IPC (Inter-Process Communication)
Electron에서는 메인 프로세스와 렌더러 프로세스 간에 통신을 위해 IPC를 사용합니다. IPC는 메시지 패싱 방식으로 작동하며, `ipcMain`과 `ipcRenderer` 모듈을 통해 구현됩니다.
- ipcMain: 메인 프로세스에서 사용되며, 렌더러 프로세스로부터 메시지를 수신하고 응답을 보낼 수 있습니다.
- ipcRenderer: 렌더러 프로세스에서 사용되며, 메인 프로세스에 메시지를 보내고 응답을 수신할 수 있습니다.
이러한 구조와 IPC 메커니즘을 통해 Electron은 웹 기술을 활용하여 데스크탑 애플리케이션을 만들 수 있습니다.
그렇다면 실제 코드는 어떻게 구현될까요??
import { app, BrowserWindow, ipcMain } from 'electron';
import { exec } from 'child_process';
let mainWindow: BrowserWindow | null = null;
app.whenReady().then(() => {
mainWindow = new BrowserWindow({
webPreferences: {
nodeIntegration: true,
},
});
mainWindow.loadFile('index.html');
ipcMain API를 이용하여 메인 프로세스에서 렌더러 프로세스로 통신이 가능합니다.
ipcMain.on('check-docker', (event) => {
exec('docker --version', (error, stdout) => {
if (error || !stdout.includes('Docker version')) {
event.reply('docker-status', false);
} else {
event.reply('docker-status', true);
}
});
});
});
import React, { useEffect } from 'react';
// Electron ipcRenderer
const { ipcRenderer } = window.require('electron');
ipcRenderer로 메인 프로세스와 통신이 가능합니다.
const App: React.FC = () => {
useEffect(() => {
ipcRenderer.on('docker-status', (_event: any, isInstalled: boolean) => {
if (isInstalled) {
console.log('Docker is installed.');
} else {
console.log('Docker is not installed.');
}
});
}, []);
const checkDocker = () => {
ipcRenderer.send('check-docker');
};
return (
<div>
<button onClick={checkDocker}>Check Docker</button>
</div>
);
};
export default App;
용어설명
프로세스란?
프로세스(Process)는 컴퓨터에서 연속적으로 실행되고 있는 컴퓨터 프로그램 인스턴스를 의미합니다. 운영체제는 이러한 프로세스들을 관리하며, 각 프로세스는 독립된 메모리 공간과 자원을 할당받아 실행됩니다.
그렇다면 CRA로 프로젝트를 생성 한 다음 npm start명령어를 이용하여 프로그램을 실행한다면 몇 개의 프로세스가 생길까요?
2개입니다.
1. Node.js 서버 프로세스: CRA는 웹팩(Webpack) 데브 서버를 사용하여 개발 서버를 구동합니다. 이 서버는 Node.js 환경에서 실행되는 하나의 프로세스입니다.
2. 브라우저 프로세스: `npm start`를 실행하면 기본 웹 브라우저가 자동으로 열리게 설정되어 있습니다. 이 웹 브라우저도 별도의 프로세스로 실행됩니다.
따라서, 최소한 두 개 이상의 프로세스가 관련됩니다. 하나는 Node.js에서 웹팩 개발 서버를 실행하는 프로세스, 다른 하나는 앱을 렌더링하는 브라우저의 프로세스입니다.
Electron과의 차이점
Electron 환경에서는 메인 프로세스와 렌더러 프로세스라는 두 종류의 프로세스가 명시적으로 존재합니다. 이는 웹 브라우저 환경과 다르게, 하나의 애플리케이션 내에서 백엔드 로직과 프론트엔드 로직이 동시에 실행될 수 있도록 설계되어 있습니다.
CRA와 같은 일반적인 웹 개발 환경에서는 이러한 구분이 명확하지 않으며, 대부분의 로직이 브라우저 내에서 실행됩니다. 이 때문에 "프로세스"의 개념이 Electron과 같이 명확하게 나뉘지 않습니다.
실제 사용 예시
onDemand환경을 구축 할 때 서버가 실행되어있지 않으면 프론트 서비스를 시작 할 수 없는 문제가 발생하였습니다. IPC통신을 이용하여 docker의 설치 유무를 판단하고 docker를 이용해 서버 컨테이너를 다운 시키고 서버 컨테이너를 실행 시켜 서비스가 동작하도록 구현하였습니다.
댓글을 작성해보세요.