Xây dựng ứng dụng Desktop với Electron, sử dụng ReactJS với Create-React-App
nodejs
85
Electron
6
reactjs
56
White

Trọng Hiếu viết ngày 07/04/2020

Chào mọi người!
Gần đây mình muốn xây dựng một ứng Desktop nhưng mình cũng chỉ biết mỗi NodeJs nên đành phải sử dụng Electron Framework. Với lại cũng muốn làm về React nên dùng luôn. Nào bắt tay vào làm thôi!!!

1. Cài Đặt

Mình sẽ hướng dẫn cơ bản cài đặt với npm. Ai dùng yarn thì làm tương tự nhé.
Đầu tiên mình khởi tạo dự án với Create-React-App.

$ create-react-app electron-demo

Sau khi cài đặt xong, mình tiến hành cài đặt 2 module nữa là electron và electron-builder.

$ npm install --save-dev electron

2. Sử Dụng Electron

Bước 1: Tạo file electron.js trong thư mục public của React và chép đoạn code sau vào.

const electron = require('electron');
// Module to control application life.
const app = electron.app;
// Module to create native browser window.
const BrowserWindow = electron.BrowserWindow;
const path = require('path');
const url = require('url');
// Keep a global reference of the window object, if you don't, the window will
// be closed automatically when the JavaScript object is garbage collected.
let mainWindow;
function createWindow() {
    // Create the browser window.
    mainWindow = new BrowserWindow({width: 800, height: 600});
    // and load the index.html of the app.
    mainWindow.loadURL('http://localhost:3000');
    // Open the DevTools.
    mainWindow.webContents.openDevTools();
    // Emitted when the window is closed.
    mainWindow.on('closed', function () {
        // Dereference the window object, usually you would store windows
        // in an array if your app supports multi windows, this is the time
        // when you should delete the corresponding element.
        mainWindow = null
    })
}
// This method will be called when Electron has finished
// initialization and is ready to create browser windows.
// Some APIs can only be used after this event occurs.
app.on('ready', createWindow);
// Quit when all windows are closed.
app.on('window-all-closed', function () {
    // On OS X it is common for applications and their menu bar
    // to stay active until the user quits explicitly with Cmd + Q
    if (process.platform !== 'darwin') {
        app.quit()
    }
});
app.on('activate', function () {
    // On OS X it's common to re-create a window in the app when the
    // dock icon is clicked and there are no other windows open.
    if (mainWindow === null) {
        createWindow()
    }
});
// In this file you can include the rest of your app's specific main process
// code. You can also put them in separate files and require them here.

Bởi vì đang ở môi trường developments nên mình phải sử dụng mainWindow.loadURL để load localhost:3000.

Bước 2: Bạn chỉnh sửa file package.json như sau.

{
    "main": "public/electron.js",
    "scripts": {
        "start": "react-scripts start",
        "build": "react-scripts build",
        "test": "react-scripts test --env=jsdom",
        "eject": "react-scripts eject",
        "electron": "electron .",
      },
}

Sau nó bạn mở terminal nên và chạy npm startnpm run electron.

3. Sử dụng loadURL trong môi trường Developments.

Chúng ta sẽ thêm 1 mục nữa vào file package.json.

"electron-dev": "ELECTRON_START_URL=http://localhost:3000 electron ."

Bạn nào sử dụng Window thì dùng câu lệnh này:

"electron-dev": "set ELECTRON_START_URL=http://localhost:3000 && electron ."

Ở trong file electron.js các bạn sửa lại mainWindow.loadURL('http://localhost:3000'); thành như sau:

const startUrl = process.env.ELECTRON_START_URL || url.format({
    pathname: path.join(__dirname, '/../build/index.html'),
    protocol: 'file:',
    slashes: true
  });
  mainWindow.loadURL(startUrl);

Có 1 số vấn đề có thể phát sinh do create-react-app các bạn thêm vào file package.json đoạn sau:

"homepage": "./",

Sau đó bạn chạy npm startnpm run electron-dev để xem thành quả.

Nếu muốn sử dụng file static của React bạn chạy npm run build.
Khi đó bạn có thể sử dụng được npm run electron để chạy file static.

4. Build Electron ra App.

Bạn tiến hành cài đặt thêm electron-builder để sử dụng.

$ npm install --save-dev electron-builder

Thêm 2 "script" sau vào file package.json:

"script": {
    ...
    "pack": "electron-builder --dir",
    "dist": "electron-builder"
}

Sau đó bạn chạy npm run dist.

Oh No! Xuất hiện một lỗi phát sinh:

Error: Application entry file "build/electron.js" in the "/Users/jarvis/Dev/sandbox/elec-app/dist/mac/elec-app.app/Contents/Resources/app.asar" does not exist. Seems like a wrong configuration.
    at error (/Users/jarvis/Dev/sandbox/elec-app/node_modules/electron-builder-lib/src/asar/asarFileChecker.ts:7:12)
    at /Users/jarvis/Dev/sandbox/elec-app/node_modules/electron-builder-lib/src/asar/asarFileChecker.ts:33:11
    at next (native)
    at /Users/jarvis/Dev/sandbox/elec-app/node_modules/graceful-fs/polyfills.js:287:18
    at FSReqWrap.oncomplete (fs.js:123:15)
:

Để fix lỗi này, bạn phải cài đặt lại react-scripts trong môi trường Developments với câu lệnh sau. (Mặc định create-react-app cài trong môi trường production)

$ npm uninstall react-scripts
$ npm install --save-dev react-scripts

Xong! Bạn đã có thể build app bình thường rồi.


Update 07/04/2020: Nếu cách trên không fix được bạn tìm đến file package.json thay đổi:

"eslintConfig": { 
    "extends": "react-app"
},

thành:

"eslintConfig": { 
    "extends": null
},

Tham khảo:
- https://www.freecodecamp.org/news/building-an-electron-application-with-create-react-app-97945861647c/
- https://medium.com/@kitze/%EF%B8%8F-from-react-to-an-electron-app-ready-for-production-a0468ecb1da3
- https://github.com/electron-userland/electron-builder/issues/2404

Bình luận


White
{{ comment.user.name }}
Bỏ hay Hay
{{comment.like_count}}
Male avatar
{{ comment_error }}
Hủy
   

Hiển thị thử

Chỉnh sửa

White

Trọng Hiếu

1 bài viết.
2 người follow
Kipalog
{{userFollowed ? 'Following' : 'Follow'}}
Bài viết liên quan
White
17 3
(Link) (Link) — tracks device battery state. (Link) (Link) — tracks geo location state of user's device. (Link) (Link) — tr...
Đinh Viễn viết 1 năm trước
17 3
White
5 2
Trải qua 1 thời gian khá dài trải nghiệm Angular, mình thấy RxJS khá hay. Bài này sẽ quay trở lại với bài toán Counter thần kì của React/Redux, như...
cdxf viết 2 năm trước
5 2
{{like_count}}

kipalog

{{ comment_count }}

bình luận

{{liked ? "Đã kipalog" : "Kipalog"}}


White
{{userFollowed ? 'Following' : 'Follow'}}
1 bài viết.
2 người follow

 Đầu mục bài viết

Vẫn còn nữa! x

Kipalog vẫn còn rất nhiều bài viết hay và chủ đề thú vị chờ bạn khám phá!