Add entry to "Open With" only for certain files

I think I have a solution now. In your extension, you need to request the IFileBrowserFactory. We do this in order to get the tracker of the file browser instance, which tells us which files are selected:

export const someExtension: JupyterFrontEndPlugin<void> = {
  id: '@organisation/some:plugin',
  autoStart: true,
  requires: [JupyterFrontEnd.IPaths, INotebookTracker],
  optional: [ICommandPalette, IMainMenu, ILauncher,
             IFileBrowserFactory],  // <--
  activate: (
    app: JupyterFrontEnd,
    paths: JupyterFrontEnd.IPaths,
    notebooks: INotebookTracker,
    palette: ICommandPalette | null,
    menu: IMainMenu | null,
    launcher: ILauncher | null,
    browser: IFileBrowserFactory | null,  // <--
  ) => {
   // ...
  }
}

Then when adding your command to the context menu, use a custom isVisible function:

function selectionAllowsPreview() {
    const widget = browser?.tracker.currentWidget;
    if (!widget) return false;

    // put your custom critera here
    function good(item: Contents.IModel) {
        return item.path.startsWith("Desktop/")
    }

    const items = toArray(widget.selectedItems());
    return items.length > 0 && items.every(good);
}

commands.addCommand('myextension:test', {
    label: 'Run Dashboard',
    caption: 'Test',
    execute: (_) => {
       console.log("Would execute the command here");
    },
    isVisible: selectionAllowsPreview,
    icon: runIcon,
});
app.contextMenu.addItem({
    command: 'myextension:test',
    selector: '.jp-DirListing-item[data-isdir="false"]',
    rank: 2
});

This is basically the solution suggested here, but it was a bit tricky to figure out where to get the tracker from. Hope it is helpful for somebody else!

2 Likes