-
Notifications
You must be signed in to change notification settings - Fork 11
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Almost everything works though
- Loading branch information
Showing
18 changed files
with
1,132 additions
and
2 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,48 @@ | ||
========================== | ||
Jupyter Launcher Shortcuts | ||
========================== | ||
|
||
Extensions for JupyterLab and classic Jupyter Notebook to add | ||
**user defined** 'launcher' shortcuts. Primarily useful in | ||
JupyterHub / Binder situations. | ||
|
||
For JupyterLab, they're added in the launcher interface. | ||
|
||
.. image:: labextension.png | ||
|
||
For classic Jupyter Notebook, they are added under the 'New' button | ||
|
||
.. image:: nbextension.png | ||
|
||
Installation | ||
============ | ||
|
||
The supporting notebook server extension & classic notebook extension | ||
can be installed with ``pip``. | ||
|
||
.. code:: bash | ||
pip install jupyter-launcher-shortcuts | ||
The JupyterLab extension needs to be installed separately. | ||
|
||
.. code:: bash | ||
jupyter labextension install jupyterlab-launcher-shortcuts | ||
Configuring | ||
=========== | ||
|
||
The extension can be configured in a ``jupyter_notebook_config.py`` | ||
file created in any of the directories under ``config`` in the | ||
output of ``jupyter --paths`` command. | ||
|
||
.. code:: python | ||
c.LauncherShortcuts.shortcuts = { | ||
'my-shiny-application': { | ||
'title': 'Human Readable Shortcut Title', | ||
'target': '{base_url}shiny/my-shiny-application-directory/', | ||
'icon_path': '/path/to/svg/file' | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,72 @@ | ||
from notebook.utils import url_path_join as ujoin | ||
from .api import ShortcutsHandler, IconHandler | ||
from traitlets import Dict | ||
from traitlets.config import Configurable | ||
from collections import namedtuple | ||
|
||
Shortcut = namedtuple('Shortcut', ['name', 'title', 'icon_path', 'target']) | ||
|
||
class LauncherShortcuts(Configurable): | ||
shortcuts = Dict( | ||
{}, | ||
help=""" | ||
Dictionary of shortcuts to put in launchers. | ||
Key should be the name of the shortcut. | ||
Value should be a dictionary with the following keys: | ||
title | ||
Human readable title for the shortcut. Defaults to the name. | ||
target | ||
URL to open when shortcut is clicked. {base_url} is replaced with | ||
the notebook server's base_url | ||
icon_path | ||
Full path to an svg icon that could be used with a launcher. Currently only used by the | ||
JupyterLab launcher | ||
""", | ||
config=True | ||
) | ||
|
||
def shortcut_from_dict(name, shortcut_dict): | ||
return Shortcut( | ||
name, | ||
title=shortcut_dict.get('title', name), | ||
icon_path=shortcut_dict.get('icon_path'), | ||
target=shortcut_dict['target'] | ||
) | ||
|
||
def load_jupyter_server_extension(nbapp): | ||
# Set up handlers picked up via config | ||
base_url = nbapp.web_app.settings['base_url'] | ||
shortcuts = [ | ||
shortcut_from_dict(k, v) | ||
for k, v in LauncherShortcuts(parent=nbapp).shortcuts.items() | ||
] | ||
|
||
icons = {} | ||
for ls in shortcuts: | ||
if ls.icon_path: | ||
icons[ls.name] = ls.icon_path | ||
|
||
nbapp.web_app.add_handlers('.*', [ | ||
(ujoin(base_url, 'launcher-shortcuts/shortcuts'), ShortcutsHandler, {'shortcuts': shortcuts}), | ||
(ujoin(base_url, 'launcher-shortcuts/icon/(.*)'), IconHandler, {'icons': icons}) | ||
]) | ||
|
||
|
||
# Jupyter Extension points | ||
def _jupyter_server_extension_paths(): | ||
return [{ | ||
'module': 'jupyter_launcher_shortcuts', | ||
}] | ||
|
||
def _jupyter_nbextension_paths(): | ||
return [{ | ||
"section": "tree", | ||
"dest": "jupyter_launcher_shortcuts", | ||
'src': 'static', | ||
"require": "jupyter_launcher_shortcuts/tree" | ||
}] |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,60 @@ | ||
from tornado import web | ||
import mimetypes | ||
from notebook.base.handlers import IPythonHandler | ||
from notebook.utils import url_path_join as ujoin | ||
|
||
class ShortcutsHandler(IPythonHandler): | ||
def initialize(self, shortcuts): | ||
self.shortcuts = shortcuts | ||
|
||
@web.authenticated | ||
async def get(self): | ||
data = [] | ||
for ls in self.shortcuts: | ||
item = { | ||
'name': ls.name, | ||
'title': ls.title, | ||
'target': ls.target.format(base_url=self.base_url), | ||
} | ||
if ls.icon_path: | ||
icon_url = ujoin(self.base_url, 'launcher-shortcuts', 'icon', sp.name) | ||
data.append(item) | ||
|
||
self.write({'shortcuts': data}) | ||
|
||
|
||
# FIXME: Should be a StaticFileHandler subclass | ||
class IconHandler(IPythonHandler): | ||
""" | ||
Serve launcher icons | ||
""" | ||
def initialize(self, icons): | ||
""" | ||
icons is a dict of titles to paths | ||
""" | ||
self.icons = icons | ||
|
||
async def get(self, name): | ||
if name not in self.icons: | ||
raise web.HTTPError(404) | ||
path = self.icons[name] | ||
|
||
# Guess mimetype appropriately | ||
# Stolen from https://github.com/tornadoweb/tornado/blob/b399a9d19c45951e4561e6e580d7e8cf396ef9ff/tornado/web.py#L2881 | ||
mime_type, encoding = mimetypes.guess_type(path) | ||
if encoding == "gzip": | ||
content_type = "application/gzip" | ||
# As of 2015-07-21 there is no bzip2 encoding defined at | ||
# http://www.iana.org/assignments/media-types/media-types.xhtml | ||
# So for that (and any other encoding), use octet-stream. | ||
elif encoding is not None: | ||
content_type = "application/octet-stream" | ||
elif mime_type is not None: | ||
content_type = mime_type | ||
# if mime_type not detected, use application/octet-stream | ||
else: | ||
content_type = "application/octet-stream" | ||
|
||
with open(self.icons[name]) as f: | ||
self.write(f.read()) | ||
self.set_header('Content-Type', content_type) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,8 @@ | ||
""" | ||
Traitlets based configuration for jupyter_server_proxy | ||
""" | ||
from notebook.utils import url_path_join as ujoin | ||
from .handlers import SuperviseAndProxyHandler, AddSlashHandler | ||
import pkg_resources | ||
from collections import namedtuple | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,6 @@ | ||
{ | ||
"load_extensions": { | ||
"jupyter_launcher_extensions/tree": true | ||
} | ||
} | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,8 @@ | ||
{ | ||
"NotebookApp": { | ||
"nbserver_extensions": { | ||
"jupyter_launcher_shortcuts": true | ||
} | ||
} | ||
} | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,51 @@ | ||
define(['jquery', 'base/js/namespace', 'base/js/utils'], function($, Jupyter, utils) { | ||
var $ = require('jquery'); | ||
var Jupyter = require('base/js/namespace'); | ||
var utils = require('base/js/utils'); | ||
|
||
var base_url = utils.get_body_data('baseUrl'); | ||
|
||
function load() { | ||
if (!Jupyter.notebook_list) return; | ||
|
||
var servers_info_url = base_url + 'launcher-shortcuts/shortcuts' ; | ||
$.get(servers_info_url, function(data) { | ||
/* locate the right-side dropdown menu of apps and notebooks */ | ||
var $menu = $('.tree-buttons').find('.dropdown-menu'); | ||
|
||
/* create a divider */ | ||
var $divider = $('<li>') | ||
.attr('role', 'presentation') | ||
.addClass('divider'); | ||
|
||
|
||
/* add the divider */ | ||
$menu.append($divider); | ||
|
||
$.each(data.shortcuts, function(_, shortcut) { | ||
/* create our list item */ | ||
var $entry_container = $('<li>') | ||
.attr('role', 'presentation') | ||
.addClass('new-rstudio'); | ||
|
||
/* create our list item's link */ | ||
var $entry_link = $('<a>') | ||
.attr('role', 'menuitem') | ||
.attr('tabindex', '-1') | ||
.attr('href', shortcut.target) | ||
.attr('target', '_blank') | ||
.text(shortcut.title); | ||
|
||
/* add the link to the item and | ||
* the item to the menu */ | ||
$entry_container.append($entry_link); | ||
$menu.append($entry_container); | ||
|
||
}); | ||
}); | ||
} | ||
|
||
return { | ||
load_ipython_extension: load | ||
}; | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,5 @@ | ||
*.bundle.* | ||
lib/ | ||
node_modules/ | ||
*.egg-info/ | ||
.ipynb_checkpoints |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,32 @@ | ||
# jupyterlab-launcher-shortcuts | ||
|
||
Configurable launcher shortcuts for JupyterLab. | ||
|
||
|
||
## Prerequisites | ||
|
||
* JupyterLab | ||
|
||
## Installation | ||
|
||
```bash | ||
jupyter labextension install jupyterlab-launcher-shortcuts | ||
``` | ||
|
||
## Development | ||
|
||
For a development install (requires npm version 4 or later), do the following in the repository directory: | ||
|
||
```bash | ||
npm install | ||
npm run build | ||
jupyter labextension link . | ||
``` | ||
|
||
To rebuild the package and the JupyterLab app: | ||
|
||
```bash | ||
npm run build | ||
jupyter lab build | ||
``` | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,43 @@ | ||
{ | ||
"name": "jupyterlab-launcher-shortcuts", | ||
"version": "1.0.0-beta1", | ||
"description": "Provide arbitrary shortcuts for apps in JupyterLab", | ||
"keywords": [ | ||
"jupyter", | ||
"jupyterlab", | ||
"jupyterlab-extension" | ||
], | ||
"homepage": "https://github.com/yuvipanda/jupyter-launcher-shortcuts", | ||
"bugs": { | ||
"url": "https://github.com/yuvipanda/jupyter-launcher-shortcuts/issues" | ||
}, | ||
"license": "BSD-3-Clause", | ||
"author": "Yuvi Panda", | ||
"files": [ | ||
"lib/**/*.{d.ts,eot,gif,html,jpg,js,js.map,json,png,svg,woff2,ttf}", | ||
"style/**/*.{css,eot,gif,html,jpg,json,png,svg,woff2,ttf}" | ||
], | ||
"main": "lib/index.js", | ||
"types": "lib/index.d.ts", | ||
"repository": { | ||
"type": "git", | ||
"url": "https://github.com/yuvipanda/jupyter-launcher-shortcuts.git" | ||
}, | ||
"scripts": { | ||
"build": "tsc", | ||
"clean": "rimraf lib", | ||
"prepare": "npm run clean && npm run build", | ||
"watch": "tsc -w" | ||
}, | ||
"dependencies": { | ||
"@jupyterlab/application": "^0.19.1", | ||
"@jupyterlab/launcher": "^0.19.1" | ||
}, | ||
"devDependencies": { | ||
"rimraf": "^2.6.1", | ||
"typescript": "~3.1.1" | ||
}, | ||
"jupyterlab": { | ||
"extension": true | ||
} | ||
} |
Oops, something went wrong.