diff --git a/backend/sophon/notebooks/admin.py b/backend/sophon/notebooks/admin.py index add45a7..3b2632e 100644 --- a/backend/sophon/notebooks/admin.py +++ b/backend/sophon/notebooks/admin.py @@ -39,7 +39,6 @@ class NotebookAdmin(SophonAdmin): "fields": ( "container_image", "container_id", - "internet_access", ), }, ), diff --git a/backend/sophon/notebooks/migrations/0012_alter_notebook_internal_url.py b/backend/sophon/notebooks/migrations/0012_alter_notebook_internal_url.py new file mode 100644 index 0000000..04239c0 --- /dev/null +++ b/backend/sophon/notebooks/migrations/0012_alter_notebook_internal_url.py @@ -0,0 +1,19 @@ +# Generated by Django 3.2.7 on 2021-10-19 19:46 + +from django.db import migrations, models + + +class Migration(migrations.Migration): + dependencies = [ + ('notebooks', '0011_auto_20211019_1745'), + ] + + operations = [ + migrations.AlterField( + model_name='notebook', + name='internal_url', + field=models.CharField(blank=True, + help_text='The URL reachable from the proxy where the container is available. Can be null if the notebook is not running.', + max_length=512, null=True, verbose_name='Internal URL'), + ), + ] diff --git a/backend/sophon/notebooks/models.py b/backend/sophon/notebooks/models.py index 0632472..7c93b57 100644 --- a/backend/sophon/notebooks/models.py +++ b/backend/sophon/notebooks/models.py @@ -114,10 +114,11 @@ class Notebook(SophonGroupModel): blank=True, null=True, ) - internal_url = models.IntegerField( + internal_url = models.CharField( "Internal URL", help_text="The URL reachable from the proxy where the container is available. Can be null if the notebook is not running.", blank=True, null=True, + max_length=512, ) def get_group(self) -> ResearchGroup: @@ -131,7 +132,6 @@ class Notebook(SophonGroupModel): "name", "locked_by", "container_image", - "internet_access", "is_running", "lab_url", "legacy_notebook_url", @@ -174,28 +174,28 @@ class Notebook(SophonGroupModel): """ :return: The name given to the container associated with this :class:`Notebook`. """ - return f"{settings.CONTAINER_PREFIX}-{self.slug}" + return f"{settings.DOCKER_CONTAINER_PREFIX}-{self.slug}" @property def volume_name(self) -> str: """ :return: The name given to the volume associated with this :class:`Notebook`. """ - return f"{settings.VOLUME_PREFIX}-{self.slug}" + return f"{settings.DOCKER_VOLUME_PREFIX}-{self.slug}" @property def network_name(self) -> str: """ :return: The name given to the network associated with this :class:`Notebook`. """ - return f"{settings.NETWORK_PREFIX}-{self.slug}" + return f"{settings.DOCKER_NETWORK_PREFIX}-{self.slug}" @property def external_domain(self) -> str: """ :return: The domain name where this :class:`Notebook` will be accessible on the Internet after its container is started. """ - return f"{self.slug}.{settings.PROXY_DOMAIN}" + return f"{self.slug}.{settings.PROXY_BASE_DOMAIN}" @property def lab_url(self) -> t.Optional[str]: @@ -322,7 +322,10 @@ class Notebook(SophonGroupModel): proxy = get_proxy_container() self.log.debug("Disconnecting proxy container from the network...") - network.disconnect(proxy) + try: + network.disconnect(proxy) + except docker.errors.APIError: + self.log.debug("Container was already disconnected.") else: self.log.debug("Unassigning port...") @@ -485,7 +488,7 @@ class Notebook(SophonGroupModel): name=self.container_name, ports={ "8888/tcp": (f"127.0.0.1", f"{self.port}/tcp") - }, + } if self.port else {}, environment={ "JUPYTER_ENABLE_LAB": "yes", "RESTARTABLE": "yes", @@ -498,7 +501,7 @@ class Notebook(SophonGroupModel): "mode": "rw", } }, - network=network, + network=network.name, ) self.log.debug("Storing container_id in the SQL database...") diff --git a/docker-compose.yml b/docker-compose.yml index e9c6b3b..ea4a3c3 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -3,7 +3,8 @@ version: "3.9" volumes: proxy-data: - static-data: + django-static: + react-static: db-data: @@ -43,9 +44,9 @@ services: # TODO: Configure your proxy details! - DJANGO_PROXY_BASE_DOMAIN=dev.sophon.steffo.eu - DJANGO_PROXY_PROTOCOL=http - - DJANGO_PROXY_CONTAINER_NAME=proxy + - DJANGO_PROXY_CONTAINER_NAME=sophon2-proxy-1 # The correct name probably is $DIRECTORYNAME-proxy-1 # TODO: Configure your static url! - - DJANGO_STATIC_URL=http://static.dev.sophon.steffo.eu/@django-static/ + - DJANGO_STATIC_URL=http://static.dev.sophon.steffo.eu/django-static/ # TODO: Set your language! - DJANGO_LANGUAGE_CODE=en-us # TODO: Set your timezone! @@ -69,7 +70,7 @@ services: - DJANGO_DOCKER_CERT_PATH= volumes: - proxy-data:/run/sophon/proxy - - static-data:/run/sophon/static + - django-static:/run/sophon/static - /var/run/docker.sock:/var/run/docker.sock depends_on: - db @@ -88,7 +89,8 @@ services: - SOPHON_FRONTEND_NAME=frontend:5000 volumes: - proxy-data:/run/sophon/proxy - - static-data:/usr/local/apache2/htdocs/django-static + - django-static:/usr/local/apache2/htdocs/django-static + - react-static:/usr/local/apache2/htdocs/react-static depends_on: - backend - frontend diff --git a/frontend/Dockerfile b/frontend/Dockerfile index 445b564..c0e2373 100644 --- a/frontend/Dockerfile +++ b/frontend/Dockerfile @@ -15,4 +15,5 @@ RUN yarn install COPY . . # Start the serve server -ENTRYPOINT ["yarn", "run", "serve"] +ENTRYPOINT ["yarn", "run"] +CMD ["serve"] \ No newline at end of file diff --git a/frontend/Frontend (React).iml b/frontend/Frontend (React).iml index 7626055..e1c660c 100644 --- a/frontend/Frontend (React).iml +++ b/frontend/Frontend (React).iml @@ -5,6 +5,7 @@ + diff --git a/frontend/src/components/elements/DescriptionBox.tsx b/frontend/src/components/elements/DescriptionBox.tsx index 0b49fd6..8bae9ee 100644 --- a/frontend/src/components/elements/DescriptionBox.tsx +++ b/frontend/src/components/elements/DescriptionBox.tsx @@ -3,12 +3,13 @@ import {FontAwesomeIcon} from "@fortawesome/react-fontawesome" import {Box, Heading, Idiomatic} from "@steffo/bluelib-react" import * as React from "react" import ReactMarkdown from "react-markdown" +import {Empty} from "./Empty" export interface DescriptionBoxProps { icon: IconDefinition, name: string, - description: string, + description?: string | null, } @@ -19,9 +20,16 @@ export function DescriptionBox({icon, name, description}: DescriptionBoxProps):  About {name} - - {description} - + { + description ? + + {description} + + : + + This resource has no about text. + + } ), [icon, name, description], diff --git a/frontend/src/components/instance/InstanceDescriptionBox.tsx b/frontend/src/components/instance/InstanceDescriptionBox.tsx index 51c535e..1eae5fa 100644 --- a/frontend/src/components/instance/InstanceDescriptionBox.tsx +++ b/frontend/src/components/instance/InstanceDescriptionBox.tsx @@ -16,10 +16,6 @@ export function InstanceDescriptionBox(): JSX.Element | null { return null } - if(!instance.state.details.description) { - return null - } - return (