Issues using 'showOpenDialog()' from a menu item


I am trying implement a basic File->Open menu item from the main process. After returning, I’m just trying to log the filename (if any) that was selected. The usual console.log() doesn’t work well on Windows, so I wrote a small logging function that passes log messages to the dev tools console in the renderer process:

function log(msg) {
  mainWindow.webContents.on("did-finish-load", () => {
    mainWindow.webContents.send("send-console", msg);


let template = [
  label: "File",
  submenu: [
	  label: "Open",
	  click: () => {
		let filenames = dialog.showOpenDialog({
		  properties: ["openFile"],
		  filters: [
			{name: "Images", extensions: ["jpg", "gif", "png"]},
			{name: "Videos", extensions: ["mpg", "mpeg", "mp4"]}
		log(`Opening file from menu: ${filenames[0]}`);

Full source is at:

The file open dialog appears and functions as expected. However, the log message never appears.

I’ve tried using dialog.showOpenDialog() in synchronous fashion, as well as asynchronous with a callback. I’ve tried building the native menu from a template, and building it manually. I’ve confirmed that the log() function works when called from other areas of the main process.

Curiously enough, I’ve found that when I use an asynchronous callback, and do something other than write a log message (e.g. open a new window)… that other instruction IS processed.

Is there some weird quirk where IPC or BrowserWindow.webContents isn’t accessible in conjunction with dialog.showOpenDialog()… or could I be missing something else? Really stumped at this point.


Huh… it looks like my log() function works when first called after creating the BrowserWindow, but does not work on subsequent calls. I suspect this is because log() wraps a webContents.on("did-finish-load", ...) event handler, and that is only a one-time event.

When I switch my File->Open menu item handler to call webContents.send("send-console", ...) directly, the selected filename does appear in the dev tools console output.

However, if I try to send an initialization log message immediately after creating the browser window, it doesn’t make it. Is there some way, other than a one-time did-finish-load event handler, to generally know when a browser window is finished loading and can accept console log messages?