Ajout des obitools
This commit is contained in:
20
Dockerfile
20
Dockerfile
@@ -9,6 +9,9 @@ RUN apt-get update && apt-get install -y \
|
|||||||
libcurl4-openssl-dev \
|
libcurl4-openssl-dev \
|
||||||
libssl-dev \
|
libssl-dev \
|
||||||
libxml2-dev \
|
libxml2-dev \
|
||||||
|
git \
|
||||||
|
build-essential \
|
||||||
|
curl \
|
||||||
&& apt-get clean && rm -rf /var/lib/apt/lists/*
|
&& apt-get clean && rm -rf /var/lib/apt/lists/*
|
||||||
|
|
||||||
# Install R kernel for Jupyter (as root)
|
# Install R kernel for Jupyter (as root)
|
||||||
@@ -16,16 +19,29 @@ RUN R -e "install.packages('IRkernel', repos='http://cran.rstudio.com/')" && \
|
|||||||
R -e "IRkernel::installspec(user = FALSE)"
|
R -e "IRkernel::installspec(user = FALSE)"
|
||||||
|
|
||||||
# Install some useful R packages for labs
|
# Install some useful R packages for labs
|
||||||
RUN R -e "install.packages(c('ggplot2', 'dplyr', 'tidyr', 'readr'), repos='http://cran.rstudio.com/')"
|
RUN R -e "install.packages(c('tidyverse', 'vegan', 'ade4'), repos='http://cran.rstudio.com/')"
|
||||||
|
|
||||||
# Install bash kernel (as root also)
|
# Install bash kernel (as root also)
|
||||||
RUN pip install bash_kernel && \
|
RUN pip install bash_kernel && \
|
||||||
python -m bash_kernel.install --sys-prefix
|
python -m bash_kernel.install --sys-prefix
|
||||||
|
|
||||||
|
# Install obitools4 (written in Go)
|
||||||
|
RUN curl -L https://raw.githubusercontent.com/metabarcoding/obitools4/master/install_obitools.sh | bash
|
||||||
|
|
||||||
|
# Install csvkit
|
||||||
|
RUN pip install csvkit
|
||||||
|
|
||||||
|
# Install csvlens
|
||||||
|
RUN curl https://sh.rustup.rs -sSf | bash -s -- -y \
|
||||||
|
&& . $HOME/.cargo/env \
|
||||||
|
&& cargo install csvlens \
|
||||||
|
&& mv $HOME/.cargo/bin/csvlens /usr/local/bin/ \
|
||||||
|
&& rm -rf $HOME/.cargo $HOME/.rustup
|
||||||
|
|
||||||
# Create necessary directories with proper permissions
|
# Create necessary directories with proper permissions
|
||||||
RUN mkdir -p /home/${NB_USER}/.local/share/jupyter && \
|
RUN mkdir -p /home/${NB_USER}/.local/share/jupyter && \
|
||||||
chown -R ${NB_UID}:${NB_GID} /home/${NB_USER}
|
chown -R ${NB_UID}:${NB_GID} /home/${NB_USER}
|
||||||
|
|
||||||
USER ${NB_UID}
|
USER ${NB_UID}
|
||||||
|
|
||||||
WORKDIR /home/${NB_USER}
|
WORKDIR /home/${NB_USER}
|
||||||
|
|||||||
67
Readme.md
67
Readme.md
@@ -113,6 +113,71 @@ Each student will see these directories in their JupyterLab:
|
|||||||
- **`work/`** : Personal workspace (persistent, private)
|
- **`work/`** : Personal workspace (persistent, private)
|
||||||
- **`shared/`** : Shared workspace between all students (read/write)
|
- **`shared/`** : Shared workspace between all students (read/write)
|
||||||
- **`course/`** : Course files (read-only, you deposit files)
|
- **`course/`** : Course files (read-only, you deposit files)
|
||||||
|
- **`course/R_packages/`** : Shared R packages (read-only for students, only admin can install)
|
||||||
|
|
||||||
|
### User Accounts
|
||||||
|
|
||||||
|
**Admin Account:**
|
||||||
|
- Username: `admin`
|
||||||
|
- Password: `admin2025` (change in docker-compose.yml: `JUPYTERHUB_ADMIN_PASSWORD`)
|
||||||
|
- Can write to `course/` directory
|
||||||
|
|
||||||
|
**Student Accounts:**
|
||||||
|
- Username: any name
|
||||||
|
- Password: `metabar2025` (change in docker-compose.yml: `JUPYTERHUB_PASSWORD`)
|
||||||
|
- Read-only access to `course/` directory
|
||||||
|
|
||||||
|
### Installing R Packages (Admin Only)
|
||||||
|
|
||||||
|
**From your Mac (recommended):**
|
||||||
|
|
||||||
|
```bash
|
||||||
|
chmod +x install-r-packages-admin.sh
|
||||||
|
|
||||||
|
# Install packages
|
||||||
|
./install-r-packages-admin.sh reshape2 plotly knitr
|
||||||
|
```
|
||||||
|
|
||||||
|
This script:
|
||||||
|
- Installs packages in the `course/R_packages/` directory
|
||||||
|
- All students can use them (read-only)
|
||||||
|
- No need to rebuild the image
|
||||||
|
|
||||||
|
**From admin notebook:**
|
||||||
|
|
||||||
|
Login as `admin` and create an R notebook:
|
||||||
|
|
||||||
|
```r
|
||||||
|
# Install packages in course directory (admin only)
|
||||||
|
course_lib <- "/home/jovyan/course/R_packages"
|
||||||
|
dir.create(course_lib, recursive = TRUE, showWarnings = FALSE)
|
||||||
|
|
||||||
|
install.packages(c('reshape2', 'plotly', 'knitr'),
|
||||||
|
lib = course_lib,
|
||||||
|
repos = 'http://cran.rstudio.com/')
|
||||||
|
```
|
||||||
|
|
||||||
|
Note: Admin account has write access to the course directory.
|
||||||
|
|
||||||
|
### Using R Packages (Students)
|
||||||
|
|
||||||
|
Students simply load packages normally:
|
||||||
|
```r
|
||||||
|
library(reshape2) # Loads from course/R_packages/ automatically
|
||||||
|
library(plotly)
|
||||||
|
```
|
||||||
|
|
||||||
|
R automatically finds packages in `/home/jovyan/course/R_packages/` thanks to the `R_LIBS_USER` environment variable.
|
||||||
|
|
||||||
|
### List Available Packages
|
||||||
|
|
||||||
|
```r
|
||||||
|
# List all available packages
|
||||||
|
installed.packages()[,"Package"]
|
||||||
|
|
||||||
|
# Or check course packages specifically
|
||||||
|
list.files("/home/jovyan/course/R_packages")
|
||||||
|
```
|
||||||
|
|
||||||
### Deposit Files for Course
|
### Deposit Files for Course
|
||||||
|
|
||||||
@@ -254,4 +319,4 @@ docker-compose down -v
|
|||||||
docker rmi jupyterhub-hub jupyterhub-student
|
docker rmi jupyterhub-hub jupyterhub-student
|
||||||
# Then rebuild everything
|
# Then rebuild everything
|
||||||
./start-jupyterhub.sh
|
./start-jupyterhub.sh
|
||||||
```
|
```
|
||||||
@@ -6,7 +6,7 @@ services:
|
|||||||
container_name: jupyterhub
|
container_name: jupyterhub
|
||||||
image: jupyterhub-hub:latest
|
image: jupyterhub-hub:latest
|
||||||
ports:
|
ports:
|
||||||
- "8000:8000"
|
- "8888:8000"
|
||||||
volumes:
|
volumes:
|
||||||
# Access to Docker socket to spawn student containers
|
# Access to Docker socket to spawn student containers
|
||||||
- /var/run/docker.sock:/var/run/docker.sock
|
- /var/run/docker.sock:/var/run/docker.sock
|
||||||
@@ -20,6 +20,8 @@ services:
|
|||||||
environment:
|
environment:
|
||||||
# Shared password for all students
|
# Shared password for all students
|
||||||
JUPYTERHUB_PASSWORD: metabar2025
|
JUPYTERHUB_PASSWORD: metabar2025
|
||||||
|
# Admin password (for installing R packages)
|
||||||
|
JUPYTERHUB_ADMIN_PASSWORD: admin2025
|
||||||
# Optional environment variables
|
# Optional environment variables
|
||||||
DOCKER_NOTEBOOK_DIR: /home/jovyan/work
|
DOCKER_NOTEBOOK_DIR: /home/jovyan/work
|
||||||
|
|
||||||
74
install_packages.sh
Normal file
74
install_packages.sh
Normal file
@@ -0,0 +1,74 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
# Script to install R packages in the course directory (admin only)
|
||||||
|
# Usage: ./install-r-packages.sh package1 package2 package3
|
||||||
|
|
||||||
|
set -e
|
||||||
|
|
||||||
|
GREEN='\033[0;32m'
|
||||||
|
BLUE='\033[0;34m'
|
||||||
|
YELLOW='\033[1;33m'
|
||||||
|
RED='\033[0;31m'
|
||||||
|
NC='\033[0m'
|
||||||
|
|
||||||
|
echo -e "${BLUE}📦 R Package Installer (Admin)${NC}"
|
||||||
|
echo "================================"
|
||||||
|
echo ""
|
||||||
|
|
||||||
|
# Check if packages are provided
|
||||||
|
if [ $# -eq 0 ]; then
|
||||||
|
echo -e "${RED}❌ Error: No packages specified${NC}"
|
||||||
|
echo ""
|
||||||
|
echo "Usage:"
|
||||||
|
echo " ./install-r-packages.sh package1 package2 package3"
|
||||||
|
echo ""
|
||||||
|
echo "Example:"
|
||||||
|
echo " ./install-r-packages.sh reshape2 plotly knitr"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Build package list
|
||||||
|
PACKAGES=$(IFS=,; echo "$*")
|
||||||
|
R_PACKAGES=$(echo "$PACKAGES" | sed "s/,/', '/g")
|
||||||
|
|
||||||
|
echo -e "${YELLOW}📋 Packages to install: ${R_PACKAGES}${NC}"
|
||||||
|
echo ""
|
||||||
|
|
||||||
|
# Create a temporary directory for installation
|
||||||
|
TEMP_DIR=$(mktemp -d)
|
||||||
|
echo -e "${BLUE}📁 Creating temporary directory: ${TEMP_DIR}${NC}"
|
||||||
|
|
||||||
|
# Install packages in temporary directory
|
||||||
|
echo -e "${BLUE}🔨 Installing R packages...${NC}"
|
||||||
|
docker run --rm \
|
||||||
|
--user root \
|
||||||
|
-v "${TEMP_DIR}:/temp_packages" \
|
||||||
|
jupyterhub-student:latest \
|
||||||
|
R -e "install.packages(c('${R_PACKAGES}'), lib='/temp_packages', repos='http://cran.rstudio.com/')" || {
|
||||||
|
echo -e "${RED}❌ Failed to install packages${NC}"
|
||||||
|
rm -rf "${TEMP_DIR}"
|
||||||
|
exit 1
|
||||||
|
}
|
||||||
|
|
||||||
|
# Copy to course volume
|
||||||
|
echo ""
|
||||||
|
echo -e "${BLUE}💾 Copying to course volume...${NC}"
|
||||||
|
docker run --rm \
|
||||||
|
-v jupyterhub-course:/target \
|
||||||
|
-v "${TEMP_DIR}:/source" \
|
||||||
|
alpine sh -c "mkdir -p /target/R_packages && cp -r /source/* /target/R_packages/"
|
||||||
|
|
||||||
|
# Clean up
|
||||||
|
rm -rf "${TEMP_DIR}"
|
||||||
|
|
||||||
|
# List installed packages
|
||||||
|
echo ""
|
||||||
|
echo -e "${GREEN}✅ Installation complete!${NC}"
|
||||||
|
echo ""
|
||||||
|
echo -e "${BLUE}📦 Installed packages in course/R_packages:${NC}"
|
||||||
|
docker run --rm \
|
||||||
|
-v jupyterhub-course:/course \
|
||||||
|
alpine ls -1 /course/R_packages/
|
||||||
|
|
||||||
|
echo ""
|
||||||
|
echo -e "${YELLOW}ℹ️ Students need to restart their R kernels to use new packages.${NC}"
|
||||||
@@ -33,19 +33,19 @@ c.DockerSpawner.remove = True
|
|||||||
c.DockerSpawner.name_template = "jupyter-{username}"
|
c.DockerSpawner.name_template = "jupyter-{username}"
|
||||||
|
|
||||||
# Volume mounting to persist student data
|
# Volume mounting to persist student data
|
||||||
# Set root to /home/jovyan to see all directories
|
# Set root to work/ - everything is persistent
|
||||||
notebook_dir = '/home/jovyan'
|
notebook_dir = '/home/jovyan/work'
|
||||||
c.DockerSpawner.notebook_dir = notebook_dir
|
c.DockerSpawner.notebook_dir = notebook_dir
|
||||||
|
|
||||||
# Personal volume for each student + shared volume
|
# Personal volume for each student + shared volumes under work/
|
||||||
c.DockerSpawner.volumes = {
|
c.DockerSpawner.volumes = {
|
||||||
# Personal volume (persistent) - mounted in work/
|
# Personal volume (persistent) - root directory
|
||||||
'jupyterhub-user-{username}': '/home/jovyan/work',
|
'jupyterhub-user-{username}': '/home/jovyan/work',
|
||||||
# Shared volume between all students
|
# Shared volume between all students - under work/
|
||||||
'jupyterhub-shared': '/home/jovyan/shared',
|
'jupyterhub-shared': '/home/jovyan/work/shared',
|
||||||
# Shared read-only volume for course files (optional)
|
# Shared read-only volume for course files - under work/
|
||||||
'jupyterhub-course': {
|
'jupyterhub-course': {
|
||||||
'bind': '/home/jovyan/course',
|
'bind': '/home/jovyan/work/course',
|
||||||
'mode': 'ro' # read-only
|
'mode': 'ro' # read-only
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -54,6 +54,23 @@ c.DockerSpawner.volumes = {
|
|||||||
c.DockerSpawner.mem_limit = '2G'
|
c.DockerSpawner.mem_limit = '2G'
|
||||||
c.DockerSpawner.cpu_limit = 1.0
|
c.DockerSpawner.cpu_limit = 1.0
|
||||||
|
|
||||||
|
# Environment variables for student containers
|
||||||
|
c.DockerSpawner.environment = {
|
||||||
|
# R package library in read-only course directory under work/
|
||||||
|
'R_LIBS_USER': '/home/jovyan/work/R_packages',
|
||||||
|
'R_LIBS_SITE': '/home/jovyan/work/course/R_packages',
|
||||||
|
# Path to R packages in read-only
|
||||||
|
'PATH': '/home/jovyan/work/course/bin:${PATH}'
|
||||||
|
}
|
||||||
|
|
||||||
|
# Create user R lib directory
|
||||||
|
#async def create_user_hierarchy(spawner):
|
||||||
|
# cmd = "mkdir -p /home/jovyan/work/R_packages && chown jovyan:jovyan /home/jovyan/work/R_packages"
|
||||||
|
# spawner.extra_create_kwargs.update({'command': f"/bin/bash -c '{cmd} && start-notebook.sh'"})
|
||||||
|
|
||||||
|
#c.Spawner.pre_spawn_hook = create_user_r_libs
|
||||||
|
|
||||||
|
|
||||||
# User configuration - Simple password authentication for lab
|
# User configuration - Simple password authentication for lab
|
||||||
from jupyterhub.auth import DummyAuthenticator
|
from jupyterhub.auth import DummyAuthenticator
|
||||||
|
|
||||||
@@ -65,12 +82,16 @@ class SimplePasswordAuthenticator(DummyAuthenticator):
|
|||||||
if authentication is None:
|
if authentication is None:
|
||||||
return False
|
return False
|
||||||
|
|
||||||
# Get password from environment variable
|
|
||||||
expected_password = os.environ.get('JUPYTERHUB_PASSWORD', 'metabar2025')
|
|
||||||
provided_password = authentication.get('password', '')
|
provided_password = authentication.get('password', '')
|
||||||
|
|
||||||
# Check password
|
# Admin user with special password
|
||||||
return provided_password == expected_password
|
if username == 'admin':
|
||||||
|
admin_password = os.environ.get('JUPYTERHUB_ADMIN_PASSWORD', 'admin2025')
|
||||||
|
return provided_password == admin_password
|
||||||
|
|
||||||
|
# Regular students with shared password
|
||||||
|
student_password = os.environ.get('JUPYTERHUB_PASSWORD', 'metabar2025')
|
||||||
|
return provided_password == student_password
|
||||||
|
|
||||||
c.JupyterHub.authenticator_class = SimplePasswordAuthenticator
|
c.JupyterHub.authenticator_class = SimplePasswordAuthenticator
|
||||||
|
|
||||||
@@ -125,7 +146,7 @@ c.DockerSpawner.name_template = "jupyter-{username}"
|
|||||||
|
|
||||||
# Montage de volumes pour persister les données des étudiants
|
# Montage de volumes pour persister les données des étudiants
|
||||||
# Définir la racine à /home/jovyan pour voir tous les dossiers
|
# Définir la racine à /home/jovyan pour voir tous les dossiers
|
||||||
notebook_dir = '/home/jovyan'
|
notebook_dir = '/home/jovyan/work'
|
||||||
c.DockerSpawner.notebook_dir = notebook_dir
|
c.DockerSpawner.notebook_dir = notebook_dir
|
||||||
|
|
||||||
# Volume personnel pour chaque étudiant + volume partagé
|
# Volume personnel pour chaque étudiant + volume partagé
|
||||||
@@ -133,10 +154,10 @@ c.DockerSpawner.volumes = {
|
|||||||
# Volume personnel (persistant) - monté dans work/
|
# Volume personnel (persistant) - monté dans work/
|
||||||
'jupyterhub-user-{username}': '/home/jovyan/work',
|
'jupyterhub-user-{username}': '/home/jovyan/work',
|
||||||
# Volume partagé entre tous les étudiants
|
# Volume partagé entre tous les étudiants
|
||||||
'jupyterhub-shared': '/home/jovyan/shared',
|
'jupyterhub-shared': '/home/jovyan/work/shared',
|
||||||
# Volume partagé en lecture seule pour les fichiers du cours (optionnel)
|
# Volume partagé en lecture seule pour les fichiers du cours (optionnel)
|
||||||
'jupyterhub-course': {
|
'jupyterhub-course': {
|
||||||
'bind': '/home/jovyan/course',
|
'bind': '/home/jovyan/work/course',
|
||||||
'mode': 'ro' # read-only
|
'mode': 'ro' # read-only
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
12
setup.sh
Normal file → Executable file
12
setup.sh
Normal file → Executable file
@@ -61,16 +61,20 @@ if docker ps | grep -q jupyterhub; then
|
|||||||
echo -e "${GREEN}✅ JupyterHub is running!${NC}"
|
echo -e "${GREEN}✅ JupyterHub is running!${NC}"
|
||||||
echo ""
|
echo ""
|
||||||
echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
|
echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
|
||||||
echo -e "${GREEN}🌐 JupyterHub available at: http://localhost:8000${NC}"
|
echo -e "${GREEN}🌐 JupyterHub available at: http://localhost:8888${NC}"
|
||||||
echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
|
echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
|
||||||
echo ""
|
echo ""
|
||||||
echo "📝 Password: metabar2025"
|
echo "📝 Password: metabar2025"
|
||||||
echo "👥 Students can connect with any username"
|
echo "👥 Students can connect with any username"
|
||||||
echo ""
|
echo ""
|
||||||
|
echo "🔑 Admin account:"
|
||||||
|
echo " Username: admin"
|
||||||
|
echo " Password: admin2025"
|
||||||
|
echo ""
|
||||||
echo "📂 Each student will have access to:"
|
echo "📂 Each student will have access to:"
|
||||||
echo " - work/ : personal workspace"
|
echo " - work/ : personal workspace (everything here is saved)"
|
||||||
echo " - shared/ : shared workspace"
|
echo " - work/shared/ : shared workspace"
|
||||||
echo " - course/ : course files (read-only)"
|
echo " - work/course/ : course files (read-only)"
|
||||||
echo ""
|
echo ""
|
||||||
echo "🔍 To view logs: docker-compose logs -f jupyterhub"
|
echo "🔍 To view logs: docker-compose logs -f jupyterhub"
|
||||||
echo "🛑 To stop: docker-compose down"
|
echo "🛑 To stop: docker-compose down"
|
||||||
|
|||||||
Reference in New Issue
Block a user