Skip to content

NazDocker Lab - Containerized dev environment with SSH & multi-user support

License

Notifications You must be signed in to change notification settings

nazdridoy/nazdocker-lab

Folders and files

NameName
Last commit message
Last commit date

Latest commit

Β 

History

17 Commits
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 

Repository files navigation

NazDocker Lab

License: GPL v3 Docker Ubuntu Alpine Documentation

A secure, containerized development environment for educational and development purposes. This project provides a Docker-based lab environment with SSH access, multiple user accounts, and development tools, designed for learning, testing, and development workflows.

πŸš€ Features

  • πŸ” Multi-User Environment: 6 pre-configured user accounts (admin + 5 regular users)
  • 🌐 Public SSH Access: Secure remote access via playit.gg tunneling
  • πŸ› οΈ Development Tools: Python 3.x, Node.js, Git, and essential utilities
  • πŸ’Ύ Persistent Storage: User data persists across container restarts with separate volumes for Alpine and Ubuntu
  • βš™οΈ Runtime Configuration: Environment-based configuration management
  • πŸ”’ Security Focused: Proper user isolation and SSH key support
  • πŸ”‘ SSH Key Synchronization: Shared SSH host keys between Alpine and Ubuntu containers
  • πŸ₯ Health Monitoring: Built-in health checks for SSH service availability
  • πŸ”οΈ Alpine & Ubuntu Support: Choose between lightweight Alpine (173MB) or full Ubuntu (968MB)

πŸ“‹ Prerequisites

πŸƒβ€β™‚οΈ Quick Start

1. Clone the Repository

git clone https://github.com/nazdridoy/nazdocker-lab.git
cd nazdocker-lab

2. Set Up Environment

# Create separate data directories for Alpine and Ubuntu
mkdir -p data/{alpine,ubuntu}/{admin,user1,user2,user3,user4,user5}
mkdir -p logs/{alpine,ubuntu}

# Generate SSH host keys (optional - will be auto-generated if missing)
./scripts/manage-ssh-keys.sh generate

# Configure environment variables
cp .env.example .env
# Edit .env with your configuration

3. Start the Environment

Choose your preferred version:

Ubuntu Version (Recommended for Development):

docker-compose -f docker-compose.ubuntu.yml up -d

Alpine Version (Recommended for Production - 82% smaller):

docker-compose -f docker-compose.alpine.yml up -d

4. Access the Lab

# Local SSH access
ssh admin@localhost -p 2222
# Password: admin123

πŸ‘₯ User Accounts

Username Default Password Sudo Access Purpose
admin admin123 βœ… Yes Administrative tasks
user1 user123 ❌ No Regular development
user2 user123 ❌ No Regular development
user3 user123 ❌ No Regular development
user4 user123 ❌ No Regular development
user5 user123 ❌ No Regular development
root root123 βœ… Yes System administration

πŸ”§ Configuration

SSH Key Management

The lab environment uses shared SSH host keys between Alpine and Ubuntu containers to ensure consistent SSH connections:

# Generate new SSH host keys
./scripts/manage-ssh-keys.sh generate

# Check SSH key fingerprints
./scripts/manage-ssh-keys.sh check

# Backup SSH keys
./scripts/manage-ssh-keys.sh backup

# Restore SSH keys from backup
./scripts/manage-ssh-keys.sh restore backup/ssh-20231201-143022

Benefits:

  • βœ… Same SSH host keys across both containers
  • βœ… No SSH host key warnings when switching containers
  • βœ… Centralized key management
  • βœ… Easy key rotation and backup

Environment Variables

The lab uses environment variables for secure configuration. Copy .env.example to .env and customize:

# Required: Playit.gg secret key for public access
PLAYIT_SECRET_KEY=your_playit_secret_key_here

# User passwords (change these!)
ADMIN_PASSWORD=your_admin_password_here
USER_PASSWORD=your_user_password_here
ROOT_PASSWORD=your_root_password_here

# Optional: SSH port mapping
SSH_PORT=2222

Security Best Practices

  • Change default passwords immediately after first login
  • Use SSH keys instead of password authentication when possible
  • Never commit your .env file to version control
  • SSH host keys are automatically ignored by .gitignore for security
  • Regular updates of the base image and installed packages

🌐 Remote Access

Local Access

# SSH to any user
ssh admin@localhost -p 2222
ssh user1@localhost -p 2222
# ... etc

Public Access via Playit.gg

The environment includes playit.gg tunneling for public SSH access:

  1. Configure playit.gg: Set your secret key in .env
  2. Check tunnel status: Monitor container logs for tunnel URL
  3. Connect remotely: Use the provided public URL
# Check tunnel status
docker-compose -f docker-compose.ubuntu.yml logs lab-environment-ubuntu | grep -i "playit\|tunnel"

# Connect via public URL (example)
ssh admin@your-tunnel-url.playit.gg -p 12345

πŸ› οΈ Available Tools

Development Tools

  • Python 3.x with pip package manager
  • uv - Fast Python package manager (replaces pip, pip-tools, pipx, poetry, pyenv, virtualenv)
  • uvx - Run Python tools in ephemeral environments
  • Node.js with npm package manager
  • Git for version control
  • SSH server for remote access

System Utilities

  • curl for HTTP requests
  • jq for JSON processing
  • ping for network testing
  • ifconfig for network configuration
  • apt package manager (Ubuntu) / apk package manager (Alpine)

πŸ“ Project Structure

nazdocker-lab/
β”œβ”€β”€ Dockerfile.ubuntu       # Ubuntu container definition with health checks
β”œβ”€β”€ Dockerfile.alpine       # Alpine container definition (189MB)
β”œβ”€β”€ start.sh               # Cross-platform startup script
β”œβ”€β”€ docker-compose.ubuntu.yml # Ubuntu Docker Compose orchestration
β”œβ”€β”€ docker-compose.alpine.yml # Alpine Docker Compose orchestration
β”œβ”€β”€ .env.example           # Environment variables template
β”œβ”€β”€ README.md              # This file
β”œβ”€β”€ docs/                 # Modular documentation
β”œβ”€β”€ LICENSE                # GPL v3 license
β”œβ”€β”€ config/               # Configuration files
β”‚   └── ssh/              # Shared SSH host keys (gitignored)
β”‚       β”œβ”€β”€ ssh_host_rsa_key
β”‚       β”œβ”€β”€ ssh_host_rsa_key.pub
β”‚       β”œβ”€β”€ ssh_host_ecdsa_key
β”‚       β”œβ”€β”€ ssh_host_ecdsa_key.pub
β”‚       β”œβ”€β”€ ssh_host_ed25519_key
β”‚       └── ssh_host_ed25519_key.pub
β”œβ”€β”€ scripts/              # Utility scripts
β”‚   └── manage-ssh-keys.sh # SSH key management script
β”œβ”€β”€ data/                  # Persistent user data (separated by container type)
β”‚   β”œβ”€β”€ alpine/           # Alpine container data
β”‚   β”‚   β”œβ”€β”€ admin/        # Admin home directory (Alpine)
β”‚   β”‚   β”œβ”€β”€ user1/        # User1 home directory (Alpine)
β”‚   β”‚   β”œβ”€β”€ user2/        # User2 home directory (Alpine)
β”‚   β”‚   β”œβ”€β”€ user3/        # User3 home directory (Alpine)
β”‚   β”‚   β”œβ”€β”€ user4/        # User4 home directory (Alpine)
β”‚   β”‚   └── user5/        # User5 home directory (Alpine)
β”‚   └── ubuntu/           # Ubuntu container data
β”‚       β”œβ”€β”€ admin/        # Admin home directory (Ubuntu)
β”‚       β”œβ”€β”€ user1/        # User1 home directory (Ubuntu)
β”‚       β”œβ”€β”€ user2/        # User2 home directory (Ubuntu)
β”‚       β”œβ”€β”€ user3/        # User3 home directory (Ubuntu)
β”‚       β”œβ”€β”€ user4/        # User4 home directory (Ubuntu)
β”‚       └── user5/        # User5 home directory (Ubuntu)
└── logs/                 # Application logs (separated by container type)
    β”œβ”€β”€ alpine/           # Alpine container logs
    └── ubuntu/           # Ubuntu container logs

πŸ”„ Development Workflow

Ubuntu Version (Recommended for Development)

# Start Ubuntu environment
docker-compose -f docker-compose.ubuntu.yml up -d

# SSH into lab
ssh admin@localhost -p 2222

# Develop in your persistent home directory
# Install packages: sudo apt-get install (admin only)

# Use uv for Python development
uv init myproject          # Create new Python project
uv add requests            # Add dependency
uv run myproject/main.py   # Run Python script
uvx ruff check            # Run linter in ephemeral environment

# Stop when done
docker-compose -f docker-compose.ubuntu.yml down

Alpine Version (Recommended for Production)

# Start Alpine environment (82% smaller)
docker-compose -f docker-compose.alpine.yml up -d

# SSH into lab (same commands)
ssh admin@localhost -p 2222

# Develop in your persistent home directory
# Install packages: sudo apk add (admin only)

# Use uv for Python development
uv init myproject          # Create new Python project
uv add requests            # Add dependency
uv run myproject/main.py   # Run Python script
uvx ruff check            # Run linter in ephemeral environment

# Stop when done
docker-compose -f docker-compose.alpine.yml down

Building Images

# Build Ubuntu image
docker-compose -f docker-compose.ubuntu.yml build

# Build Alpine image
docker-compose -f docker-compose.alpine.yml build

# Build both images
docker-compose -f docker-compose.ubuntu.yml build && docker-compose -f docker-compose.alpine.yml build

Running Both Containers Simultaneously

With separate volumes, you can run both Alpine and Ubuntu containers at the same time:

# Start both environments
docker-compose -f docker-compose.ubuntu.yml up -d
docker-compose -f docker-compose.alpine.yml up -d

# Access Ubuntu lab (port 2222)
ssh admin@localhost -p 2222

# Access Alpine lab (port 2223 - you'll need to modify SSH_PORT in .env)
ssh admin@localhost -p 2223

# Both containers use the same SSH host keys, so no key warnings when switching
# Stop both environments
docker-compose -f docker-compose.ubuntu.yml down
docker-compose -f docker-compose.alpine.yml down

πŸ›‘οΈ Security Considerations

Default Configuration

  • All users have password authentication enabled
  • SSH keys are not configured by default
  • Default passwords should be changed immediately

Recommended Security Measures

  1. Change all default passwords after first login
  2. Configure SSH key authentication for better security
  3. Use strong, unique passwords for each user
  4. Regular security updates of the base image
  5. Monitor access logs for suspicious activity

πŸ₯ Health Monitoring

Both Ubuntu and Alpine versions include built-in health checks that monitor SSH service availability:

  • Health Check Interval: 30 seconds
  • Timeout: 10 seconds per check
  • Start Period: 40 seconds grace period after container startup
  • Retries: 3 consecutive failures before marking as unhealthy

Health Status

  • Healthy: SSH service is running and accepting connections
  • Unhealthy: SSH service is stopped or not responding
  • Starting: Container is in the grace period after startup

Monitoring Health Status

# Check container health status
docker ps

# View detailed health information
docker inspect student-lab-ubuntu | grep -A 20 "Health"

# Monitor health check logs
docker inspect student-lab-ubuntu | grep -A 10 "Healthcheck"

πŸ’Ύ Volume Management

Separate Volume Structure

The lab environment uses separate volumes for Alpine and Ubuntu containers to ensure complete isolation and prevent data conflicts:

data/
β”œβ”€β”€ alpine/           # Alpine container data
β”‚   β”œβ”€β”€ admin/        # Admin user data (Alpine)
β”‚   β”œβ”€β”€ user1/        # User1 data (Alpine)
β”‚   β”œβ”€β”€ user2/        # User2 data (Alpine)
β”‚   β”œβ”€β”€ user3/        # User3 data (Alpine)
β”‚   β”œβ”€β”€ user4/        # User4 data (Alpine)
β”‚   └── user5/        # User5 data (Alpine)
└── ubuntu/           # Ubuntu container data
    β”œβ”€β”€ admin/        # Admin user data (Ubuntu)
    β”œβ”€β”€ user1/        # User1 data (Ubuntu)
    β”œβ”€β”€ user2/        # User2 data (Ubuntu)
    β”œβ”€β”€ user3/        # User3 data (Ubuntu)
    β”œβ”€β”€ user4/        # User4 data (Ubuntu)
    └── user5/        # User5 data (Ubuntu)

logs/
β”œβ”€β”€ alpine/           # Alpine container logs
└── ubuntu/           # Ubuntu container logs

Benefits of Separate Volumes

  • πŸ”’ Complete Isolation: Alpine and Ubuntu containers have completely separate data storage
  • πŸš€ Concurrent Operation: Both container types can run simultaneously without conflicts
  • πŸ“¦ Easy Management: Backup, restore, or manage data for each container type separately
  • 🧹 Clean Organization: Clear separation makes it obvious which data belongs to which container
  • πŸ”„ Independent Scaling: Scale Alpine and Ubuntu environments independently

Volume Usage

  • Alpine Container: Stores data in ./data/alpine/ and logs in ./logs/alpine/
  • Ubuntu Container: Stores data in ./data/ubuntu/ and logs in ./logs/ubuntu/

πŸ”οΈ Alpine vs Ubuntu Comparison

Image Size Comparison

Version Base Image Final Size Size Reduction
Ubuntu ubuntu:24.04 1.05GB -
Alpine alpine:3.22 189MB 82% smaller

When to Use Each Version

Use Alpine When:

  • Resource constraints are a concern
  • Fast deployments are needed
  • Security is a priority
  • Production environments where size matters

Use Ubuntu When:

  • Maximum compatibility is needed
  • Familiar environment is preferred
  • Specific Ubuntu packages are required
  • Development/testing environments

Key Differences

  • Package Management: apt (Ubuntu) vs apk (Alpine)
  • Service Management: service (Ubuntu) vs direct commands (Alpine)
  • User Groups: sudo (Ubuntu) vs wheel (Alpine)
  • Build Time: Alpine builds ~50% faster
  • Startup Time: Alpine starts ~30% faster
  • SSH Keys: Both containers use identical SSH host keys for consistency

Resource Limits

Both versions are configured with optimized resource limits:

  • CPU: Maximum 2 cores, minimum 1 core reserved
  • Memory: Maximum 2GB, minimum 1GB reserved
  • Network: Standard bridge networking
  • Storage: Persistent volumes for user data

πŸ“š Documentation

🀝 Contributing

We welcome contributions! Please see our contributing guidelines:

  1. Fork the repository
  2. Create a feature branch (git checkout -b feature/amazing-feature)
  3. Commit your changes (git commit -m 'Add amazing feature')
  4. Push to the branch (git push origin feature/amazing-feature)
  5. Open a Pull Request

Development Setup

# Clone your fork
git clone https://github.com/your-username/nazdocker-lab.git
cd nazdocker-lab

# Add upstream remote
git remote add upstream https://github.com/nazdridoy/nazdocker-lab.git

# Create feature branch
git checkout -b feature/your-feature-name

πŸ› Troubleshooting

Common Issues

Container won't start:

# Check logs
docker-compose logs

# Validate configuration
docker-compose config

SSH connection refused:

# Check container status
docker-compose ps

# Check SSH service
docker-compose -f docker-compose.ubuntu.yml exec lab-environment-ubuntu service ssh status

Environment variables not loading:

# Verify .env file exists
ls -la .env

# Check variable resolution
docker-compose config | grep -E "(PLAYIT_SECRET_KEY|ADMIN_PASSWORD)"

For more detailed troubleshooting, see Troubleshooting Guide.

πŸ“„ License

This project is licensed under the GNU General Public License v3.0 - see the LICENSE file for details.

πŸ™ Acknowledgments

  • Docker for containerization technology
  • Ubuntu for the base operating system
  • Playit.gg for tunneling services
  • OpenSSH for secure shell access

πŸ“ž Support


Note: This is a development and educational tool. Always follow security best practices and change default credentials before use in production environments.

About

NazDocker Lab - Containerized dev environment with SSH & multi-user support

Topics

Resources

License

Security policy

Stars

Watchers

Forks

Packages

No packages published

Languages