From e41b14f10855a060ebfb927aac2e30aa76ed3545 Mon Sep 17 00:00:00 2001 From: phorcys420 <57866459+phorcys420@users.noreply.github.com> Date: Mon, 5 Aug 2024 21:21:18 +0000 Subject: [PATCH] feat: initiate migration to devcontainer prebuilds --- .devcontainer/devcontainer.json | 21 + .../base/.devcontainer}/Dockerfile | 0 .../supervisor/conf.d/code-server.conf | 0 .../basic-env/supervisor/conf.d/vnc.conf | 0 .../basic-env/supervisor/logs/.gitkeep | 0 .../basic-env/supervisor/supervisord.conf | 0 .../base/.devcontainer/devcontainer.json | 9 + .../base/.devcontainer}/user-dirs.dirs | 0 .../devcontainer/base/.devcontainer}/xstartup | 0 .../dart/.devcontainer}/Dockerfile | 2 +- .../dart/.devcontainer/devcontainer.json | 10 + .../java/.devcontainer}/Dockerfile | 20 +- .../java/.devcontainer/devcontainer.json | 10 + .../javascript/.devcontainer}/Dockerfile | 2 +- .../.devcontainer/devcontainer.json | 10 + .github/workflows/_build-and-push.yml | 32 + .github/workflows/build-and-push-base.yml | 16 + .github/workflows/build-and-push-others.yml | 19 + main.tf | 905 +++++++++--------- 19 files changed, 578 insertions(+), 478 deletions(-) create mode 100644 .devcontainer/devcontainer.json rename {docker/base => .github/devcontainer/base/.devcontainer}/Dockerfile (100%) rename {docker/base => .github/devcontainer/base/.devcontainer}/basic-env/supervisor/conf.d/code-server.conf (100%) rename {docker/base => .github/devcontainer/base/.devcontainer}/basic-env/supervisor/conf.d/vnc.conf (100%) rename {docker/base => .github/devcontainer/base/.devcontainer}/basic-env/supervisor/logs/.gitkeep (100%) rename {docker/base => .github/devcontainer/base/.devcontainer}/basic-env/supervisor/supervisord.conf (100%) create mode 100644 .github/devcontainer/base/.devcontainer/devcontainer.json rename {docker/base => .github/devcontainer/base/.devcontainer}/user-dirs.dirs (100%) rename {docker/base => .github/devcontainer/base/.devcontainer}/xstartup (100%) rename {docker/dart => .github/devcontainer/dart/.devcontainer}/Dockerfile (92%) create mode 100644 .github/devcontainer/dart/.devcontainer/devcontainer.json rename {docker/java => .github/devcontainer/java/.devcontainer}/Dockerfile (77%) create mode 100644 .github/devcontainer/java/.devcontainer/devcontainer.json rename {docker/javascript => .github/devcontainer/javascript/.devcontainer}/Dockerfile (87%) create mode 100644 .github/devcontainer/javascript/.devcontainer/devcontainer.json create mode 100644 .github/workflows/_build-and-push.yml create mode 100644 .github/workflows/build-and-push-base.yml create mode 100644 .github/workflows/build-and-push-others.yml diff --git a/.devcontainer/devcontainer.json b/.devcontainer/devcontainer.json new file mode 100644 index 0000000..24e2254 --- /dev/null +++ b/.devcontainer/devcontainer.json @@ -0,0 +1,21 @@ +{ + "image": "mcr.microsoft.com/devcontainers/javascript-node:1-20-bookworm", + "customizations": { + "vscode": { + "settings": { + "json.schemas": [ + { + "fileMatch": ["*/devcontainer-feature.json"], + "url": "https://raw.githubusercontent.com/devcontainers/spec/main/schemas/devContainerFeature.schema.json" + } + ] + }, + "extensions": ["mads-hartmann.bash-ide-vscode"] + } + }, + "features": { + "ghcr.io/devcontainers/features/docker-in-docker:2": {} + }, + "remoteUser": "node", + "updateContentCommand": "npm install -g @devcontainers/cli" +} diff --git a/docker/base/Dockerfile b/.github/devcontainer/base/.devcontainer/Dockerfile similarity index 100% rename from docker/base/Dockerfile rename to .github/devcontainer/base/.devcontainer/Dockerfile diff --git a/docker/base/basic-env/supervisor/conf.d/code-server.conf b/.github/devcontainer/base/.devcontainer/basic-env/supervisor/conf.d/code-server.conf similarity index 100% rename from docker/base/basic-env/supervisor/conf.d/code-server.conf rename to .github/devcontainer/base/.devcontainer/basic-env/supervisor/conf.d/code-server.conf diff --git a/docker/base/basic-env/supervisor/conf.d/vnc.conf b/.github/devcontainer/base/.devcontainer/basic-env/supervisor/conf.d/vnc.conf similarity index 100% rename from docker/base/basic-env/supervisor/conf.d/vnc.conf rename to .github/devcontainer/base/.devcontainer/basic-env/supervisor/conf.d/vnc.conf diff --git a/docker/base/basic-env/supervisor/logs/.gitkeep b/.github/devcontainer/base/.devcontainer/basic-env/supervisor/logs/.gitkeep similarity index 100% rename from docker/base/basic-env/supervisor/logs/.gitkeep rename to .github/devcontainer/base/.devcontainer/basic-env/supervisor/logs/.gitkeep diff --git a/docker/base/basic-env/supervisor/supervisord.conf b/.github/devcontainer/base/.devcontainer/basic-env/supervisor/supervisord.conf similarity index 100% rename from docker/base/basic-env/supervisor/supervisord.conf rename to .github/devcontainer/base/.devcontainer/basic-env/supervisor/supervisord.conf diff --git a/.github/devcontainer/base/.devcontainer/devcontainer.json b/.github/devcontainer/base/.devcontainer/devcontainer.json new file mode 100644 index 0000000..1c17a2f --- /dev/null +++ b/.github/devcontainer/base/.devcontainer/devcontainer.json @@ -0,0 +1,9 @@ +{ + "name": "uwu/basic-env - Base", + + "build": { + "dockerfile": "Dockerfile" + }, + + "remoteUser": "coder" +} diff --git a/docker/base/user-dirs.dirs b/.github/devcontainer/base/.devcontainer/user-dirs.dirs similarity index 100% rename from docker/base/user-dirs.dirs rename to .github/devcontainer/base/.devcontainer/user-dirs.dirs diff --git a/docker/base/xstartup b/.github/devcontainer/base/.devcontainer/xstartup similarity index 100% rename from docker/base/xstartup rename to .github/devcontainer/base/.devcontainer/xstartup diff --git a/docker/dart/Dockerfile b/.github/devcontainer/dart/.devcontainer/Dockerfile similarity index 92% rename from docker/dart/Dockerfile rename to .github/devcontainer/dart/.devcontainer/Dockerfile index 7e49b3c..125c15b 100644 --- a/docker/dart/Dockerfile +++ b/.github/devcontainer/dart/.devcontainer/Dockerfile @@ -1,4 +1,4 @@ -FROM uwunet/basic-env-base:latest +FROM ghcr.io/uwu/basic-env/base:latest USER root diff --git a/.github/devcontainer/dart/.devcontainer/devcontainer.json b/.github/devcontainer/dart/.devcontainer/devcontainer.json new file mode 100644 index 0000000..0cf6fd8 --- /dev/null +++ b/.github/devcontainer/dart/.devcontainer/devcontainer.json @@ -0,0 +1,10 @@ +{ + "name": "uwu/basic-env - Dart", + + "build": { + "dockerfile": "Dockerfile" + }, + + "remoteUser": "coder" + } + \ No newline at end of file diff --git a/docker/java/Dockerfile b/.github/devcontainer/java/.devcontainer/Dockerfile similarity index 77% rename from docker/java/Dockerfile rename to .github/devcontainer/java/.devcontainer/Dockerfile index 1b39ce1..7f5fc65 100644 --- a/docker/java/Dockerfile +++ b/.github/devcontainer/java/.devcontainer/Dockerfile @@ -1,11 +1,11 @@ -FROM uwunet/basic-env-base:latest - -USER root - -# Install requirements -RUN DEBIAN_FRONTEND="noninteractive" apt install -y zip unzip - -USER coder - -# Install sdkman +FROM ghcr.io/uwu/basic-env/base:latest + +USER root + +# Install requirements +RUN DEBIAN_FRONTEND="noninteractive" apt install -y zip unzip + +USER coder + +# Install sdkman RUN curl -s "https://get.sdkman.io" | bash \ No newline at end of file diff --git a/.github/devcontainer/java/.devcontainer/devcontainer.json b/.github/devcontainer/java/.devcontainer/devcontainer.json new file mode 100644 index 0000000..af738ca --- /dev/null +++ b/.github/devcontainer/java/.devcontainer/devcontainer.json @@ -0,0 +1,10 @@ +{ + "name": "uwu/basic-env - Java", + + "build": { + "dockerfile": "Dockerfile" + }, + + "remoteUser": "coder" + } + \ No newline at end of file diff --git a/docker/javascript/Dockerfile b/.github/devcontainer/javascript/.devcontainer/Dockerfile similarity index 87% rename from docker/javascript/Dockerfile rename to .github/devcontainer/javascript/.devcontainer/Dockerfile index f804ed1..dca76b3 100644 --- a/docker/javascript/Dockerfile +++ b/.github/devcontainer/javascript/.devcontainer/Dockerfile @@ -1,4 +1,4 @@ -FROM uwunet/basic-env-base:latest +FROM ghcr.io/uwu/basic-env/base:latest # nvm + node + pnpm RUN curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/master/install.sh | bash diff --git a/.github/devcontainer/javascript/.devcontainer/devcontainer.json b/.github/devcontainer/javascript/.devcontainer/devcontainer.json new file mode 100644 index 0000000..39573b2 --- /dev/null +++ b/.github/devcontainer/javascript/.devcontainer/devcontainer.json @@ -0,0 +1,10 @@ +{ + "name": "uwu/basic-env - JavaScript", + + "build": { + "dockerfile": "Dockerfile" + }, + + "remoteUser": "coder" + } + \ No newline at end of file diff --git a/.github/workflows/_build-and-push.yml b/.github/workflows/_build-and-push.yml new file mode 100644 index 0000000..45a7501 --- /dev/null +++ b/.github/workflows/_build-and-push.yml @@ -0,0 +1,32 @@ +name: (reusable) Dev Container Build and Push images + +on: + workflow_call: + inputs: + image: + required: true + type: string + +jobs: + build: + runs-on: ubuntu-latest + steps: + - name: Checkout + id: checkout + uses: actions/checkout@v4 + + - name: Login to GitHub Container Registry + uses: docker/login-action@v2 + with: + registry: ghcr.io + username: ${{ github.actor }} + password: ${{ secrets.GITHUB_TOKEN }} + if: github.event_name != 'pull_request' + + - name: "Pre-build '${{ inputs.image }}' image" + uses: devcontainers/ci@v0.3 + with: + subFolder: .github/devcontainer/${{ inputs.image }} + imageName: ghcr.io/${{ github.repository }}/${{ inputs.image }} + cacheFrom: ghcr.io/${{ github.repository }}/${{ inputs.image }} + push: ${{ github.event_name != 'pull_request' && 'always' || 'never' }} diff --git a/.github/workflows/build-and-push-base.yml b/.github/workflows/build-and-push-base.yml new file mode 100644 index 0000000..3a6b7c5 --- /dev/null +++ b/.github/workflows/build-and-push-base.yml @@ -0,0 +1,16 @@ +name: Build & push base image + +on: + workflow_dispatch: + push: + branches: + - "main" + pull_requests: + branches: + - "main" + +jobs: + build: + uses: uwu/basic-env/.github/workflows/_build-and-push.yml@main + with: + image: base \ No newline at end of file diff --git a/.github/workflows/build-and-push-others.yml b/.github/workflows/build-and-push-others.yml new file mode 100644 index 0000000..5d45152 --- /dev/null +++ b/.github/workflows/build-and-push-others.yml @@ -0,0 +1,19 @@ +name: Build & push other images + +on: + workflow_dispatch: + push: + branches: + - "main" + pull_requests: + branches: + - "main" + +jobs: + build: + uses: uwu/basic-env/.github/workflows/_build-and-push.yml@main + strategy: + matrix: + image: [dart, java, javascript] + with: + image: ${{ matrix.image }} \ No newline at end of file diff --git a/main.tf b/main.tf index 8bc9b7c..dab69a6 100644 --- a/main.tf +++ b/main.tf @@ -1,466 +1,439 @@ -terraform { - required_providers { - coder = { - source = "coder/coder" - version = "0.21.0" - } - - docker = { - source = "kreuzwerker/docker" - version = "3.0.2" - } - } -} - -locals { - enable_subdomains = true - - workspace_name = lower(data.coder_workspace.me.name) - user_name = lower(data.coder_workspace.me.owner) - - images = { - javascript = docker_image.javascript_image - dart = docker_image.dart_image - java = docker_image.java_image - - base = docker_image.base_image - } -} - -provider "docker" { - host = "unix:///var/run/docker.sock" -} - -provider "coder" {} -data "coder_workspace" "me" {} - -resource "random_string" "vnc_password" { - count = data.coder_parameter.vnc.value == "true" ? 1 : 0 - length = 6 - special = false -} - -resource "coder_metadata" "vnc_password" { - count = data.coder_parameter.vnc.value == "true" ? 1 : 0 - resource_id = random_string.vnc_password[0].id - - hide = true - - item { - key = "description" - value = "VNC Password" - } -} - -resource "coder_agent" "dev" { - arch = "amd64" - os = "linux" - - display_apps { - vscode = true - vscode_insiders = true - web_terminal = true - ssh_helper = true - } - - env = { - "VNC_ENABLED" = data.coder_parameter.vnc.value, - "SHELL" = data.coder_parameter.shell.value, - - "VSCODE_BINARY" = data.coder_parameter.vscode_binary.value, - - "SUPERVISOR_DIR" = "/usr/share/basic-env/supervisor" - } - - startup_script = < $HOME/.vnc/passwd - - supervisorctl start vnc:* -fi -EOT -} - -data "coder_parameter" "docker_image" { - name = "Docker Image" - description = "Which Docker image do you want to use?" - - type = "string" - default = "javascript" - - order = 1 - - mutable = true - - option { - name = "JavaScript" - value = "javascript" - } - - option { - name = "Dart" - value = "dart" - } - - option { - name = "Java" - value = "java" - } - - option { - name = "Base" - value = "base" - } -} - -data "coder_parameter" "shell" { - name = "Shell" - description = "Which shell do you want to be your default shell?" - - type = "string" - default = "bash" - - order = 2 - - mutable = true - - option { - name = "Bash" - value = "bash" - } - - option { - name = "ZSH" - value = "zsh" - } - - option { - name = "sh" - value = "sh" - } -} - -data "coder_parameter" "vnc" { - name = "VNC" - description = "Do you want to enable VNC?" - - order = 3 - - type = "bool" - default = "true" - - mutable = true -} - -data "coder_parameter" "vscode_binary" { - name = "VS Code Channel" - description = "Which VS Code channel do you want to use?" - - type = "string" - default = "code" - - order = 4 - - mutable = true - - option { - name = "Stable" - value = "code" - } - - option { - name = "Insiders" - value = "code-insiders" - } -} - -module "dotfiles" { - source = "registry.coder.com/modules/dotfiles/coder" - version = "1.0.14" - - coder_parameter_order = 5 - - agent_id = coder_agent.dev.id -} - -module "dotfiles-root" { - source = "registry.coder.com/modules/dotfiles/coder" - version = "1.0.14" - - user = "root" - dotfiles_uri = module.dotfiles.dotfiles_uri - - agent_id = coder_agent.dev.id -} - -module "git-config" { - source = "registry.coder.com/modules/git-config/coder" - version = "1.0.12" - - allow_username_change = true - allow_email_change = true - - coder_parameter_order = 6 - - agent_id = coder_agent.dev.id -} - -module "coder-login" { - source = "registry.coder.com/modules/coder-login/coder" - version = "1.0.2" - - agent_id = coder_agent.dev.id -} - -module "personalize" { - source = "registry.coder.com/modules/personalize/coder" - version = "1.0.2" - - agent_id = coder_agent.dev.id -} - -resource "coder_app" "code-server" { - agent_id = coder_agent.dev.id - - display_name = "VS Code Web" - slug = "code-server" - - order = 1 - - url = "http://localhost:8000/?folder=/home/coder/projects" - icon = "/icon/code.svg" - - subdomain = local.enable_subdomains -} - -resource "coder_app" "novnc" { - count = data.coder_parameter.vnc.value == "true" ? 1 : 0 - agent_id = coder_agent.dev.id - - display_name = "noVNC" - slug = "novnc" - - order = 2 - - url = "http://localhost:8081?autoconnect=1&resize=scale&path=@${data.coder_workspace.me.owner}/${data.coder_workspace.me.name}.dev/apps/noVNC/websockify&password=${random_string.vnc_password[0].result}" - icon = "/icon/novnc.svg" - - subdomain = local.enable_subdomains -} - -resource "coder_app" "supervisor" { - agent_id = coder_agent.dev.id - - display_name = "Supervisor" - slug = "supervisor" - - order = 3 - - url = "http://localhost:8079" - icon = "/icon/widgets.svg" - - subdomain = local.enable_subdomains -} - -resource "docker_volume" "home" { - name = "coder-${data.coder_workspace.me.id}-home" - - # Protect the volume from being deleted due to changes in attributes. - lifecycle { - ignore_changes = all - } - - # Add labels in Docker to keep track of orphan resources. - labels { - label = "coder.owner" - value = local.user_name - } - - labels { - label = "coder.owner_id" - value = data.coder_workspace.me.owner_id - } - - labels { - label = "coder.workspace_id" - value = data.coder_workspace.me.id - } -} - -resource "coder_metadata" "home" { - resource_id = docker_volume.home.id - - hide = true - - item { - key = "description" - value = "Home volume" - } -} - -resource "docker_image" "base_image" { - count = 1 - name = "uwunet/basic-env-base:latest" - - build { - context = "./docker/base" - - tag = ["uwunet/basic-env-base", "uwunet/basic-env-base:latest", "uwunet/basic-env-base:v0.6"] - } - - keep_locally = true -} - -resource "docker_image" "javascript_image" { - count = data.coder_parameter.docker_image.value == "javascript" ? 1 : 0 - - name = "uwunet/basic-env-javascript:latest" - - build { - context = "./docker/javascript" - - tag = ["uwunet/basic-env-javascript", "uwunet/basic-env-javascript:latest", "uwunet/basic-env-javascript:v0.1"] - } - - depends_on = [ docker_image.base_image[0] ] - - keep_locally = true -} - -resource "docker_image" "dart_image" { - count = data.coder_parameter.docker_image.value == "dart" ? 1 : 0 - - name = "uwunet/basic-env-dart:latest" - - build { - context = "./docker/dart" - - tag = ["uwunet/basic-env-dart", "uwunet/basic-env-dart:latest", "uwunet/basic-env-dart:v0.1"] - } - - depends_on = [ docker_image.base_image[0] ] - - keep_locally = true -} - -resource "docker_image" "java_image" { - count = data.coder_parameter.docker_image.value == "java" ? 1 : 0 - - name = "uwunet/basic-env-java:latest" - - build { - context = "./docker/java" - - tag = ["uwunet/basic-env-java", "uwunet/basic-env-java:latest", "uwunet/basic-env-java:v0.1"] - } - - depends_on = [ docker_image.base_image[0] ] - - keep_locally = true -} - -resource "coder_metadata" "base_image" { - resource_id = docker_image.base_image[0].id - - hide = true - - item { - key = "description" - value = "Base container image" - } -} - -resource "coder_metadata" "javascript_image" { - count = data.coder_parameter.docker_image.value == "javascript" ? 1 : 0 - - resource_id = docker_image.javascript_image[0].id - - hide = true - - item { - key = "description" - value = "JavaScript container image" - } -} - -resource "coder_metadata" "dart_image" { - count = data.coder_parameter.docker_image.value == "dart" ? 1 : 0 - - resource_id = docker_image.dart_image[0].id - - hide = true - - item { - key = "description" - value = "Dart container image" - } -} - -resource "coder_metadata" "java_image" { - count = data.coder_parameter.docker_image.value == "java" ? 1 : 0 - - resource_id = docker_image.java_image[0].id - - hide = true - - item { - key = "description" - value = "Java container image" - } -} - -resource "docker_container" "workspace" { - count = data.coder_workspace.me.start_count - - # we need to define a relation table in locals because we can't simply access resources like this: docker_image["javascript_image"] - # we need to access [0] because we define a count in the docker_image's definition - image = local.images[data.coder_parameter.docker_image.value][0].image_id - - name = "coder-${local.user_name}-${local.workspace_name}" - hostname = local.workspace_name - - dns = ["1.1.1.1"] - - entrypoint = ["sh", "-c", replace(coder_agent.dev.init_script, "127.0.0.1", "host.docker.internal")] - env = ["CODER_AGENT_TOKEN=${coder_agent.dev.token}"] - - volumes { - volume_name = docker_volume.home.name - container_path = "/home/coder/" - read_only = false - } - - host { - host = "host.docker.internal" - ip = "host-gateway" - } - - # Add labels in Docker to keep track of orphan resources. - labels { - label = "coder.owner" - value = local.user_name - } - - labels { - label = "coder.owner_id" - value = data.coder_workspace.me.owner_id - } - - labels { - label = "coder.workspace_id" - value = data.coder_workspace.me.id - } -} +terraform { + required_providers { + coder = { + source = "coder/coder" + version = "0.21.0" + } + + docker = { + source = "kreuzwerker/docker" + version = "3.0.2" + } + } +} + +locals { + enable_subdomains = true + + workspace_name = lower(data.coder_workspace.me.name) + user_name = lower(data.coder_workspace.me.owner) + + images = { + javascript = docker_image.javascript_image + dart = docker_image.dart_image + java = docker_image.java_image + + base = docker_image.base_image + } +} + +provider "docker" { + host = "unix:///var/run/docker.sock" +} + +provider "coder" {} +data "coder_workspace" "me" {} + +resource "random_string" "vnc_password" { + count = data.coder_parameter.vnc.value == "true" ? 1 : 0 + length = 6 + special = false +} + +resource "coder_metadata" "vnc_password" { + count = data.coder_parameter.vnc.value == "true" ? 1 : 0 + resource_id = random_string.vnc_password[0].id + + hide = true + + item { + key = "description" + value = "VNC Password" + } +} + +resource "coder_agent" "dev" { + arch = "amd64" + os = "linux" + + display_apps { + vscode = true + vscode_insiders = true + web_terminal = true + ssh_helper = true + } + + env = { + "VNC_ENABLED" = data.coder_parameter.vnc.value, + "SHELL" = data.coder_parameter.shell.value, + + "VSCODE_BINARY" = data.coder_parameter.vscode_binary.value, + + "SUPERVISOR_DIR" = "/usr/share/basic-env/supervisor" + } + + startup_script = < $HOME/.vnc/passwd + + supervisorctl start vnc:* +fi +EOT +} + +data "coder_parameter" "docker_image" { + name = "Docker Image" + description = "Which Docker image do you want to use?" + + type = "string" + default = "javascript" + + order = 1 + + mutable = true + + option { + name = "JavaScript" + value = "javascript" + } + + option { + name = "Dart" + value = "dart" + } + + option { + name = "Java" + value = "java" + } + + option { + name = "Base" + value = "base" + } +} + +data "coder_parameter" "shell" { + name = "Shell" + description = "Which shell do you want to be your default shell?" + + type = "string" + default = "bash" + + order = 2 + + mutable = true + + option { + name = "Bash" + value = "bash" + } + + option { + name = "ZSH" + value = "zsh" + } + + option { + name = "sh" + value = "sh" + } +} + +data "coder_parameter" "vnc" { + name = "VNC" + description = "Do you want to enable VNC?" + + order = 3 + + type = "bool" + default = "true" + + mutable = true +} + +data "coder_parameter" "vscode_binary" { + name = "VS Code Channel" + description = "Which VS Code channel do you want to use?" + + type = "string" + default = "code" + + order = 4 + + mutable = true + + option { + name = "Stable" + value = "code" + } + + option { + name = "Insiders" + value = "code-insiders" + } +} + +module "dotfiles" { + source = "registry.coder.com/modules/dotfiles/coder" + version = "1.0.14" + + coder_parameter_order = 5 + + agent_id = coder_agent.dev.id +} + +module "dotfiles-root" { + source = "registry.coder.com/modules/dotfiles/coder" + version = "1.0.14" + + user = "root" + dotfiles_uri = module.dotfiles.dotfiles_uri + + agent_id = coder_agent.dev.id +} + +module "git-config" { + source = "registry.coder.com/modules/git-config/coder" + version = "1.0.12" + + allow_username_change = true + allow_email_change = true + + coder_parameter_order = 6 + + agent_id = coder_agent.dev.id +} + +module "coder-login" { + source = "registry.coder.com/modules/coder-login/coder" + version = "1.0.2" + + agent_id = coder_agent.dev.id +} + +module "personalize" { + source = "registry.coder.com/modules/personalize/coder" + version = "1.0.2" + + agent_id = coder_agent.dev.id +} + +resource "coder_app" "code-server" { + agent_id = coder_agent.dev.id + + display_name = "VS Code Web" + slug = "code-server" + + order = 1 + + url = "http://localhost:8000/?folder=/home/coder/projects" + icon = "/icon/code.svg" + + subdomain = local.enable_subdomains +} + +resource "coder_app" "novnc" { + count = data.coder_parameter.vnc.value == "true" ? 1 : 0 + agent_id = coder_agent.dev.id + + display_name = "noVNC" + slug = "novnc" + + order = 2 + + url = "http://localhost:8081?autoconnect=1&resize=scale&path=@${data.coder_workspace.me.owner}/${data.coder_workspace.me.name}.dev/apps/noVNC/websockify&password=${random_string.vnc_password[0].result}" + icon = "/icon/novnc.svg" + + subdomain = local.enable_subdomains +} + +resource "coder_app" "supervisor" { + agent_id = coder_agent.dev.id + + display_name = "Supervisor" + slug = "supervisor" + + order = 3 + + url = "http://localhost:8079" + icon = "/icon/widgets.svg" + + subdomain = local.enable_subdomains +} + +resource "docker_volume" "home" { + name = "coder-${data.coder_workspace.me.id}-home" + + # Protect the volume from being deleted due to changes in attributes. + lifecycle { + ignore_changes = all + } + + # Add labels in Docker to keep track of orphan resources. + labels { + label = "coder.owner" + value = local.user_name + } + + labels { + label = "coder.owner_id" + value = data.coder_workspace.me.owner_id + } + + labels { + label = "coder.workspace_id" + value = data.coder_workspace.me.id + } +} + +resource "coder_metadata" "home" { + resource_id = docker_volume.home.id + + hide = true + + item { + key = "description" + value = "Home volume" + } +} + +resource "docker_image" "base_image" { + count = 1 + name = "ghcr.io/uwu/basic-env/base:latest" + + keep_locally = true +} + +resource "docker_image" "javascript_image" { + count = data.coder_parameter.docker_image.value == "javascript" ? 1 : 0 + + name = "ghcr.io/uwu/basic-env/javascript:latest" + + depends_on = [ docker_image.base_image[0] ] + keep_locally = true +} + +resource "docker_image" "dart_image" { + count = data.coder_parameter.docker_image.value == "dart" ? 1 : 0 + + name = "ghcr.io/uwu/basic-env/dart:latest" + + depends_on = [ docker_image.base_image[0] ] + keep_locally = true +} + +resource "docker_image" "java_image" { + count = data.coder_parameter.docker_image.value == "java" ? 1 : 0 + + name = "ghcr.io/uwu/basic-env/java:latest" + + depends_on = [ docker_image.base_image[0] ] + keep_locally = true +} + +resource "coder_metadata" "base_image" { + resource_id = docker_image.base_image[0].id + + hide = true + + item { + key = "description" + value = "Base container image" + } +} + +resource "coder_metadata" "javascript_image" { + count = data.coder_parameter.docker_image.value == "javascript" ? 1 : 0 + + resource_id = docker_image.javascript_image[0].id + + hide = true + + item { + key = "description" + value = "JavaScript container image" + } +} + +resource "coder_metadata" "dart_image" { + count = data.coder_parameter.docker_image.value == "dart" ? 1 : 0 + + resource_id = docker_image.dart_image[0].id + + hide = true + + item { + key = "description" + value = "Dart container image" + } +} + +resource "coder_metadata" "java_image" { + count = data.coder_parameter.docker_image.value == "java" ? 1 : 0 + + resource_id = docker_image.java_image[0].id + + hide = true + + item { + key = "description" + value = "Java container image" + } +} + +resource "docker_container" "workspace" { + count = data.coder_workspace.me.start_count + + # we need to define a relation table in locals because we can't simply access resources like this: docker_image["javascript_image"] + # we need to access [0] because we define a count in the docker_image's definition + image = local.images[data.coder_parameter.docker_image.value][0].image_id + + name = "coder-${local.user_name}-${local.workspace_name}" + hostname = local.workspace_name + + dns = ["1.1.1.1"] + + entrypoint = ["sh", "-c", replace(coder_agent.dev.init_script, "127.0.0.1", "host.docker.internal")] + env = ["CODER_AGENT_TOKEN=${coder_agent.dev.token}"] + + volumes { + volume_name = docker_volume.home.name + container_path = "/home/coder/" + read_only = false + } + + host { + host = "host.docker.internal" + ip = "host-gateway" + } + + # Add labels in Docker to keep track of orphan resources. + labels { + label = "coder.owner" + value = local.user_name + } + + labels { + label = "coder.owner_id" + value = data.coder_workspace.me.owner_id + } + + labels { + label = "coder.workspace_id" + value = data.coder_workspace.me.id + } +}