electron 设置伪协议和文件绑定

基于 electron-builder

package.json

// fileAssociations 为文件关联
// mac 环境需要在 extendInfo 中配置 CFBundleURLSchemes
"build": {
    "fileAssociations": {
        "ext": [
            "txt"
        ],
        "role": "Editor"
    },
    "mac": {
      "extendInfo": {
        "CFBundleURLSchemes": [
          "protocol"
        ]
      }
    }
}

main.js

let openFromProtocolUrl = ''
const openUrl = (url) => {
  mainWindow.isMinimized() && mainWindow.restore()
  // 正则中的 protocol 为自己定义的伪协议
  if (url.match(/^protocol:///)) {
    mainWindow.webContents.send('open-url', decodeURIComponent(url))
  } else {
    mainWindow.webContents.send('open-file', url)
  }
  mainWindow.focus()
}
if (isWin) {
  const argv = process.argv.slice()
  openFromProtocolUrl = argv.pop() // 启动参数的数组的最后一项是唤醒链接
}

// 省略代码
function createWindow() {
  mainWindow = new BrowserWindow({...})
  
  // 从协议打开应用时,mainWindow 还没有创建完成
  setTimeout(() => {
    if (openFromProtocolUrl) {
      openUrl(openFromProtocolUrl)
      openFromProtocolUrl = ''
    }
  }, 1500)
}

const openUrlListener = function (event, url) {
  if (mainWindow) {
    openUrl(url)
  } else {
    openFromProtocolUrl = url // 如果 mainWindow 还没创建,就先缓存
  }
}
app.on('open-url', openUrlListener)
app.on('open-file', openUrlListener)
app.setAsDefaultProtocolClient('protocol') // 设置伪协议

渲染进程

const fileAssociationsReg = /.txt$/g
const fileOpened = async (path) => {
    const match = path.match(fileAssociationsReg)
    if (!match) return console.log(`%c错误,该文件不为文本:${path}`, 'color:red')
    // 省略
}
ipcRenderer.on('open-file', fileOpened)

const urlListener = (event, url) => {
  const payload = url.replace(/protocol:///, '').split('/')
  // 省略
}
ipcRenderer.on('open-url', listener)

原文地址:https://www.cnblogs.com/NKnife/p/13475557.html