关于 Electron 进程间通信的一个小小实践

Electron 是一个跨平台桌面框架,它集成了 node.js 和 chromium,所以我们可以借助 node.js 实现桌面客户端访问操作系统资源的功能(出于安全,浏览器是不可以访问操作系统的),而 chromium 允许我们使用前端工具HTML、JS、CSS 甚至结合 React、Vue 等渲染出用户界面。

用进程间通信模拟实现 B/S 架构

B/S 即 ‘浏览器/服务器’ 架构。既然 Electron 由 node.js 和 chromium 集成, 把 Electron 的渲染进程直接当作客户端浏览器进程,主进程当作服务器进程,把访问操作系统资源、读写文件等都放在主进程里,而渲染进程专心用于渲染页面和向主进程‘请求’操作资源,主进程和渲染进程之间可以实现进程间通信,可以模拟浏览器和服务器之间的 ajax 请求。

一个结合 Electron 的项目架构:

640?wx_fmt=other

下面以一个获取 github 用户信息和远程仓库的 Electron APP 为例,用具体的代码来展示如何实现

渲染进程里使用 ipcRenderer 封装一个类 api 请求:

var electron = window.electron
var { ipcRenderer } = electron
import ipc_channel from '../const/ipc_channel'

export default {
  loginGithub: ({username, password, cb}) => {
    ipcRenderer.send(ipc_channel.LOGIN_GITHUB, {username, password})
 
    ipcRenderer.on(ipc_channel.LOGIN_GITHUB, (e, res) => {
      cb(res)
    })
  },
  logoutGithub: ({username, password, id, cb}) => {
    ipcRenderer.send(ipc_channel.LOGOUT_GITHUB, {username, password, id})

    ipcRenderer.on(ipc_channel.LOGOUT_GITHUB, (e, res) => {
      cb(res)
    })
  }
}

主进程使用 ipcMain 将渲染进程的各个请求路由到相应的路由处理器,并且传递一个回调函数方便路由处理器向渲染进程发送响应:

const routes = require('./server-routes/routes')
for(let routeName in routes) {
  ipcMain.on(routeName, (e, params) => {
    routes[routeName]({
      params,
      cb: (respond) => {
        e.sender.send(routeName, respond)}
      })
    })
}

路由处理器:

var github = require('octonode')
var ipc_channel = require('../../const/ipc_channel')
const fs = require('fs')

const {getABranchContent, readLocalDir_OR_FileWithPath, readAFile} = require('./middleweres')

module.exports = {
  [ipc_channel.LOGIN_GITHUB]: ({params, cb}) => {
    let {username, password} = params

    var scopes = {
      'scopes': ['user', 'repo', 'gist'],
      'note': 'admin script'
    }
    
    github.auth.config({
      username,
      password
    }).login(scopes, function (err, id, token, headers) {
      console.log(id, token)
      if(!err) cb({id, token})
    })
  },

  [ipc_channel.LOGOUT_GITHUB]: ({params, cb}) => {
    let {username, password, id} = params

    github.auth.config({
      username,
      password
    }).revoke(id, function (err) {
      if (err) throw err
      else cb({msg: '已经退出登录'})
    })
  }
}

用一个单独的文件导出各个 ipc channel:

module.exports = {
    LOGIN_GITHUB: 'login-github-for-token',
    LOGOUT_GITHUB: 'logout-and-revoke-token',
    GET_REPO: 'get-a-repo',
    READ_LOCAL_PATH: 'read-local-path',
    READ_LOCAL_FILE: 'read-local-file',
    READ_LOCAL_REPO_INFO_FILE: 'read-repo-info-file'
}

这样借鉴了 web 中前后端分离的思想,个人认为可以很清晰的分离应用的逻辑。

本文的素材源自个人的 Electron 小项目:

https://github.com/qumuchegi/github-code-viewer

 好文 推 荐 

☞ 不只是同构应用(isomorphic 工程化你所忽略的细节)

☞ ES2019 新特性

☞ 愿未来没有 Webpack

640?wx_fmt=png

好文章,我 在看 

640?wx_fmt=jpeg

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值