Skip to content

Commit

Permalink
Missing check admin
Browse files Browse the repository at this point in the history
  • Loading branch information
trungleduc committed Mar 13, 2024
1 parent e5be354 commit e84432e
Show file tree
Hide file tree
Showing 16 changed files with 79 additions and 65 deletions.
24 changes: 20 additions & 4 deletions jupyterhub_config.py
Original file line number Diff line number Diff line change
Expand Up @@ -45,13 +45,29 @@
sys.executable,
"-m",
"tljh_repo2docker",
"--TljhRepo2Docker.ip",
"--ip",
"127.0.0.1",
"--TljhRepo2Docker.port",
"--port",
"6789",
],
"oauth_no_confirm": True,
"admin": True
}
]
)
)

c.JupyterHub.load_roles = [
{
"description": "Role for tljh_repo2docker service",
"name": "tljh_repo2docker_role",
"scopes": ["read:users", "read:servers", "read:roles:users"],
"services": ["tljh_repo2docker"],
},
{
"name": "env-user",
"scopes": [
# access to the env page
"access:services"
],
"users": ["trung"],
},
]
4 changes: 2 additions & 2 deletions src/environments/LogDialog.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -42,10 +42,10 @@ function _EnvironmentLogButton(props: IEnvironmentLogButton) {

terminal.open(divRef.current);
fitAddon.fit();
const { baseUrl, xsrfToken } = jhData;
const { servicePrefix, xsrfToken } = jhData;

let logsUrl = urlJoin(
baseUrl,
servicePrefix,
'api',
'environments',
props.image,
Expand Down
4 changes: 2 additions & 2 deletions src/servers/OpenServerButton.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -20,9 +20,9 @@ function _OpenServerButton(props: IOpenServerButton) {

const [progress, setProgress] = useState(0);
useEffect(() => {
const { user, baseUrl, xsrfToken } = jhData;
const { user, hubPrefix, xsrfToken } = jhData;
let progressUrl = urlJoin(
baseUrl,
hubPrefix,
'api',
'users',
user,
Expand Down
10 changes: 3 additions & 7 deletions tljh_repo2docker/__init__.py
Original file line number Diff line number Diff line change
@@ -1,18 +1,14 @@
import os


from aiodocker import Docker
from dockerspawner import DockerSpawner
from jinja2 import Environment, BaseLoader
from jinja2 import BaseLoader, Environment
from jupyter_client.localinterfaces import public_ips

from jupyterhub.traitlets import ByteSpecification
from tljh.hooks import hookimpl
from tljh.configurer import load_config
from tljh.hooks import hookimpl
from traitlets import Unicode
from traitlets.config import Configurable
from .docker import list_images

from .docker import list_images

# Default CPU period
# See: https://docs.docker.com/config/containers/resource_constraints/#limit-a-containers-access-to-memory#configure-the-default-cfs-scheduler
Expand Down
28 changes: 16 additions & 12 deletions tljh_repo2docker/app.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,20 +3,19 @@
import socket
import typing as tp
from pathlib import Path
from urllib.parse import urlsplit, urlunsplit

from jinja2 import Environment, ChoiceLoader, FileSystemLoader, PackageLoader
from jinja2 import Environment, PackageLoader
from jupyterhub.app import DATA_FILES_PATH
from jupyterhub.handlers.static import LogoHandler
from jupyterhub.utils import url_path_join
from tornado import ioloop, web
from tornado.log import access_log, app_log, gen_log
from traitlets import Dict, Int, List, Unicode, default, validate
from traitlets.config.application import Application
from jupyterhub.utils import url_path_join
from jupyterhub.app import DATA_FILES_PATH
from jupyterhub.handlers.static import LogoHandler

from .builder import BuildHandler
from .servers import ServersHandler
from .environments import EnvironmentsHandler
from .logs import LogsHandler
from .servers import ServersHandler

if os.environ.get("JUPYTERHUB_API_TOKEN"):
from jupyterhub.services.auth import HubOAuthCallbackHandler
Expand All @@ -33,8 +32,6 @@ def get(self):
class TljhRepo2Docker(Application):
name = Unicode("tljh-repo2docker")

version = "1.0.0"

port = Int(6789, help="Port of the service", config=True)

base_url = Unicode(help="JupyterHub base URL", config=True)
Expand Down Expand Up @@ -105,6 +102,8 @@ def _logo_file_default(self):
def _default_log_level(self):
return logging.INFO

aliases = {"port": "TljhRepo2Docker.port", "ip": "TljhRepo2Docker.ip"}

def init_settings(self) -> tp.Dict:
"""Initialize settings for the service application."""
static_path = DATA_FILES_PATH + "/static/"
Expand Down Expand Up @@ -152,10 +151,15 @@ def init_handlers(self) -> tp.List:
),
(self.service_prefix, web.RedirectHandler, {"url": server_url}),
(server_url, ServersHandler),
(url_path_join(self.service_prefix, r"environments"), EnvironmentsHandler),
(
url_path_join(self.service_prefix, r"environments"),
EnvironmentsHandler,
),
(url_path_join(self.service_prefix, r"api/environments"), BuildHandler),
(
url_path_join(self.service_prefix, r"api/environments/([^/]+)/logs"),
url_path_join(
self.service_prefix, r"api/environments/([^/]+)/logs"
),
LogsHandler,
),
]
Expand Down Expand Up @@ -194,4 +198,4 @@ def start(self):
self.log.info("Stopping...")


main = TljhRepo2Docker.launch_instance
main = TljhRepo2Docker.launch_instance
30 changes: 17 additions & 13 deletions tljh_repo2docker/base.py
Original file line number Diff line number Diff line change
@@ -1,38 +1,42 @@
import json
import os
from typing import Dict
from tornado import web
from jupyterhub.utils import url_path_join
from jupyterhub.services.auth import HubOAuthenticated

from httpx import AsyncClient
from jinja2 import Template
from jupyterhub.services.auth import HubOAuthenticated
from jupyterhub.utils import url_path_join
from tornado import web
from jupyterhub.scopes import needs_scope
from .model import UserModel
from httpx import AsyncClient
import json

JUPYTERHUB_API_URL = os.environ.get("JUPYTERHUB_API_URL", "")
API_TOKEN = os.environ.get("JUPYTERHUB_API_TOKEN", None)
print("JUPYTERHUB_API_URL", JUPYTERHUB_API_URL)


class BaseHandler(HubOAuthenticated, web.RequestHandler):
"""
Base handler for tljh_repo2docker service
"""

_client = None

@property
def client(self):
if not BaseHandler._client:
api_url = os.environ.get("JUPYTERHUB_API_URL", "")
api_token = os.environ.get("JUPYTERHUB_API_TOKEN", None)
BaseHandler._client = AsyncClient(
base_url=JUPYTERHUB_API_URL,
headers={f"Authorization": f"Bearer {API_TOKEN}"},
base_url=api_url,
headers={f"Authorization": f"Bearer {api_token}"},
)
return BaseHandler._client

async def fetch_user(self) -> UserModel:
user = self.current_user
url = url_path_join("users", user["name"])
response = await self.client.get(url + "?include_stopped_servers")
user_model = response.json()
user_model: dict = response.json()
user_model.setdefault("name", user["name"])
user_model.setdefault("servers", {})
user_model.setdefault("admin", False)

return UserModel.from_dict(user_model)

def get_template(self, name: str) -> Template:
Expand Down
5 changes: 2 additions & 3 deletions tljh_repo2docker/builder.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,10 +2,9 @@
import re

from aiodocker import Docker, DockerError
from .base import BaseHandler
from jupyterhub.utils import admin_only
from tornado import web

from .base import BaseHandler
from .docker import build_image

IMAGE_NAME_RE = r"^[a-z0-9-_]+$"
Expand Down Expand Up @@ -73,4 +72,4 @@ async def post(self):
)

self.set_status(200)
self.finish(json.dumps({"status": "ok"}))
self.finish(json.dumps({"status": "ok"}))
3 changes: 1 addition & 2 deletions tljh_repo2docker/docker.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
import json

from urllib.parse import urlparse

from aiodocker import Docker
Expand Down Expand Up @@ -143,4 +142,4 @@ async def build_image(
)

async with Docker() as docker:
await docker.containers.run(config=config)
await docker.containers.run(config=config)
17 changes: 7 additions & 10 deletions tljh_repo2docker/environments.py
Original file line number Diff line number Diff line change
@@ -1,8 +1,7 @@
from inspect import isawaitable
from .base import BaseHandler
from jupyterhub.utils import admin_only
from tornado import web

from tornado import web
from .base import BaseHandler
from .docker import list_containers, list_images


Expand All @@ -14,21 +13,19 @@ class EnvironmentsHandler(BaseHandler):
@web.authenticated
async def get(self):
user = self.current_user
if not user['admin']:
raise web.HTTPError(
status_code=404,
reason="Unauthorized."
)

if not user["admin"]:
raise web.HTTPError(status_code=404, reason="Unauthorized.")
images = await list_images()
containers = await list_containers()
result = self.render_template(
"images.html",
images=images + containers,
default_mem_limit=self.settings.get("default_mem_limit"),
default_cpu_limit=self.settings.get("default_cpu_limit"),
machine_profiles=self.settings.get("machine_profiles",[]),
machine_profiles=self.settings.get("machine_profiles", []),
)
if isawaitable(result):
self.write(await result)
else:
self.write(result)
self.write(result)
4 changes: 2 additions & 2 deletions tljh_repo2docker/logs.py
Original file line number Diff line number Diff line change
@@ -1,12 +1,12 @@
import json

from aiodocker import Docker
from .base import BaseHandler
from jupyterhub.utils import admin_only
from tornado import web
from tornado.ioloop import IOLoop
from tornado.iostream import StreamClosedError

from .base import BaseHandler


class LogsHandler(BaseHandler):
"""
Expand Down
3 changes: 2 additions & 1 deletion tljh_repo2docker/model.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
from dataclasses import dataclass, fields


@dataclass
class UserModel:

Expand Down Expand Up @@ -28,4 +29,4 @@ def all_spawners(self) -> list:
"user_options": server.get("user_options", None),
}
)
return sp
return sp
3 changes: 2 additions & 1 deletion tljh_repo2docker/servers.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
from inspect import isawaitable
from .base import BaseHandler

from tornado import web

from .base import BaseHandler
from .docker import list_images


Expand Down
4 changes: 2 additions & 2 deletions tljh_repo2docker/tests/conftest.py
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import pytest

from aiodocker import Docker, DockerError
from tljh_repo2docker import tljh_custom_jupyterhub_config
from traitlets.config import Config

from tljh_repo2docker import tljh_custom_jupyterhub_config


async def remove_docker_image(image_name):
async with Docker() as docker:
Expand Down
3 changes: 1 addition & 2 deletions tljh_repo2docker/tests/test_builder.py
Original file line number Diff line number Diff line change
@@ -1,8 +1,7 @@
import pytest

from aiodocker import Docker, DockerError

from .utils import add_environment, wait_for_image, remove_environment
from .utils import add_environment, remove_environment, wait_for_image


@pytest.mark.asyncio
Expand Down
1 change: 0 additions & 1 deletion tljh_repo2docker/tests/test_images.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
import pytest

from jupyterhub.tests.utils import get_page

from .utils import add_environment, wait_for_image
Expand Down
1 change: 0 additions & 1 deletion tljh_repo2docker/tests/test_logs.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
import json

import pytest

from jupyterhub.tests.utils import api_request, async_requests

from .utils import add_environment, wait_for_image
Expand Down

0 comments on commit e84432e

Please sign in to comment.