Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
125 changes: 30 additions & 95 deletions .devcontainer/continue-config.yaml
Original file line number Diff line number Diff line change
@@ -1,101 +1,36 @@
name: Local Assistant
name: Local Config
version: 1.0.0
schema: v1
models:
# - name: Llama 3.1 8B
# model: llama3.1:8b
# provider: openai
# apiBase: ${{ secrets.OPENWEB_BASE_URL }}
# apiKey: ${{ secrets.OPENWEB_API_KEY }}
# roles:
# - chat
# - edit
# - apply

- name: gemma3 4B
model: gemma3:4b
provider: openai
apiBase: ${{ secrets.OPENWEB_BASE_URL }}
apiKey: ${{ secrets.OPENWEB_API_KEY }}
roles:
- chat
- edit
- apply
- autocomplete
- name: Qwen3-Coder-30B-A3B-Instruct
provider: openai
apiBase: ${{ secrets.OPENAI_BASE_URL }}
apiKey: ${{ secrets.OPENAI_API_KEY }}
model: qwen3-coder:30b
roles:
- chat
- edit
- apply
- autocomplete
capabilities:
- tool use

- name: deepseek-r1 8b
model: deepseek-r1:8b
provider: openai
apiBase: ${{ secrets.OPENWEB_BASE_URL }}
apiKey: ${{ secrets.OPENWEB_API_KEY }}
roles:
- chat
- edit
- apply
- name: nomic-embed-text
provider: openai
apiBase: ${{ secrets.OPENAI_BASE_URL }}
apiKey: ${{ secrets.OPENAI_API_KEY }}
model: nomic-embed-text:v1.5
roles:
- embed

- name: qwen3 8B
model: qwen3:8b
provider: openai
apiBase: ${{ secrets.OPENWEB_BASE_URL }}
apiKey: ${{ secrets.OPENWEB_API_KEY }}
roles:
- chat
- edit
- apply
- autocomplete

- name: Nomic Embed
model: nomic-embed-text:latest
provider: openai
apiBase: ${{ secrets.OPENWEB_BASE_URL }}
apiKey: ${{ secrets.OPENWEB_API_KEY }}
embedOptions:
maxChunkSize: 8192
roles:
- embed

- name: Qwen 2.5b Autocomplete Model
model: qwen2.5-coder:1.5b
provider: openai
apiBase: ${{ secrets.OPENWEB_BASE_URL }}
apiKey: ${{ secrets.OPENWEB_API_KEY }}
roles:
- chat
- edit
- apply
- autocomplete
defaultCompletionOptions:
contextLength: 32768
maxTokens: 8192

- name: gpt-oss-20b
provider: openai
model: gpt-oss:20b
apiBase: ${{ secrets.OPENWEB_BASE_URL }}
apiKey: ${{ secrets.OPENWEB_API_KEY }}
roles:
- chat
- edit
- apply

# - name: Qwen3-Coder-30B-A3B-Instruct
# provider: openai
# model: qwen3-coder:30b
# apiBase: ${{ secrets.OPENWEB_BASE_URL }}
# apiKey: ${{ secrets.OPENWEB_API_KEY }}
# roles:
# - chat
# - edit
# - apply

context:
- provider: code
- provider: currentFile
- provider: codebase
- provider: docs
- provider: diff
- provider: file
- provider: problems
- provider: repo-map
- provider: terminal
- provider: tree
# - name: Autodetect
# provider: ollama
# apiBase: http://localhost:11434
# model: AUTODETECT
# roles:
# - chat
# - edit
# - apply
# - rerank
# - autocomplete
4 changes: 3 additions & 1 deletion .devcontainer/continue.env
Original file line number Diff line number Diff line change
@@ -1,2 +1,4 @@
# Open WebUI
OPENWEB_BASE_URL=http://host.containers.internal:11434/v1
OPENAI_BASE_URL="https://host.containers.internal:8080/api"
# WARNING: Replace the value below with your actual OpenAI API key before use.
OPENAI_API_KEY="REPLACE_ME"
30 changes: 15 additions & 15 deletions .devcontainer/devcontainer.json
Original file line number Diff line number Diff line change
Expand Up @@ -27,21 +27,21 @@
"userUid": "automatic",
"userGid": "automatic"
},
"ghcr.io/rocker-org/devcontainer-features/quarto-cli:1": {
"installTinyTex": true,
"installChromium": true,
"version": "latest"
},
// R language support, https://github.com/rocker-org/devcontainer-features/tree/main/src/r-apt
"ghcr.io/rocker-org/devcontainer-features/r-apt:0": {
"installDevTools": true,
"installREnv": true,
"installRMarkdown": true,
"installRadian": true,
"installVscDebugger": true,
"useTesting": true,
"vscodeRSupport": "full"
},
// "ghcr.io/rocker-org/devcontainer-features/quarto-cli:1": {
// "installTinyTex": true,
// "installChromium": true,
// "version": "latest"
// },
// // R language support, https://github.com/rocker-org/devcontainer-features/tree/main/src/r-apt
// "ghcr.io/rocker-org/devcontainer-features/r-apt:0": {
// "installDevTools": true,
// "installREnv": true,
// "installRMarkdown": true,
// "installRadian": true,
// "installVscDebugger": true,
// "useTesting": true,
// "vscodeRSupport": "full"
// },
"ghcr.io/devcontainers-extra/features/npm-packages:1": {
"packages": "@continuedev/cli@latest,@openai/codex@latest,@qwen-code/qwen-code@latest"
},
Expand Down
14 changes: 14 additions & 0 deletions .devcontainer/qwen-settings.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
{
"security": {
"auth": {
Comment thread
DevNiall marked this conversation as resolved.
// WARNING: Replace the placeholder API key below with your actual API key before use.
"selectedType": "openai",
"apiKey": "sk-<YOUR-API-KEY-HERE>",
"baseUrl": "http://host.containers.internal:8080/api"
}
},
"model": {
"name": "qwen3-coder:30b"
},
"$version": 2
}
9 changes: 7 additions & 2 deletions .devcontainer/vscode-init/02-download-extensions.sh
Original file line number Diff line number Diff line change
Expand Up @@ -10,9 +10,11 @@ set -e
# of the extension and its functionality gets inherited by devcontainers.

EXTENSIONS_FILE="extensions-to-download.txt"
DOWNLOAD_DIR="/opt"
DOWNLOAD_DIR="/opt/vscode-extensions"
SUCCESSFUL_DOWNLOADS=()

mkdir -p "${DOWNLOAD_DIR}"

if [ ! -f "${EXTENSIONS_FILE}" ]; then
echo "Error: Extensions file not found at ${EXTENSIONS_FILE}"
exit 1
Expand Down Expand Up @@ -41,7 +43,10 @@ download_extension() {
local extension_name="${extension_id#*.}"

local extension_filepath="${DOWNLOAD_DIR}/${extension_id}.vsix"
local download_url="https://${publisher}.gallery.vsassets.io/_apis/public/gallery/publisher/${publisher}/extension/${extension_name}/latest/assetbyname/Microsoft.VisualStudio.Services.VSIXPackage"

# We first need to lookup releases to find the latest version and architecture to download URL
local download_url="$(curl -sSL https://marketplace.visualstudio.com/_apis/public/gallery/vscode/${publisher}/${extension_name}/latest \
| jq -r '.versions[] | select(.targetPlatform == "linux-x64" or .targetPlatform == null) | select(.flags | contains("prerelease") | not) | .files[] | select(.assetType == "Microsoft.VisualStudio.Services.VSIXPackage") | .source' | head -n1)"

Comment on lines +49 to 50

Copilot AI Nov 23, 2025

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The download URL construction logic may fail or produce incorrect URLs. The jq command filters for non-prerelease versions (select(.flags | contains("prerelease") | not)), but the flags field may not always be a string or array that supports the contains() function. Additionally, if no matching version is found, download_url will be empty, leading to a curl failure without a clear error message.

Consider adding validation to check if download_url is non-empty before proceeding with the download, and handle the case where the jq filter returns no results more gracefully.

Suggested change
| jq -r '.versions[] | select(.targetPlatform == "linux-x64" or .targetPlatform == null) | select(.flags | contains("prerelease") | not) | .files[] | select(.assetType == "Microsoft.VisualStudio.Services.VSIXPackage") | .source' | head -n1)"
| jq -r '.versions[] | select(.targetPlatform == "linux-x64" or .targetPlatform == null) | select((has("flags") and (.flags | type == "string" or type == "array") and (.flags | contains("prerelease") | not)) or (has("flags") | not)) | .files[] | select(.assetType == "Microsoft.VisualStudio.Services.VSIXPackage") | .source' | head -n1)"
if [[ -z "${download_url}" ]]; then
echo " ✗ No suitable version found for ${extension_id} (no download URL)"
exit 1
fi

Copilot uses AI. Check for mistakes.
echo "Downloading ${extension_id}..."

Expand Down
1 change: 1 addition & 0 deletions .devcontainer/vscode-init/extensions-to-download.txt
Original file line number Diff line number Diff line change
Expand Up @@ -9,4 +9,5 @@ vscodevim.vim
Continue.continue
ms-toolsai.jupyter-keymap
openai.chatgpt
qwenlm.qwen-code-vscode-ide-companion
REditorSupport.r-syntax
5 changes: 3 additions & 2 deletions .devcontainer/vscode-init/extensions-to-install.txt
Original file line number Diff line number Diff line change
Expand Up @@ -2,17 +2,18 @@
# These extensions will be enabled for all users of the devcontainer.
# One extension ID per line.
charliermarsh.ruff
#Continue.continue
Continue.continue --pre-release
DavidAnson.vscode-markdownlint
eamodio.gitlens
# The marimo extension has been removed from the marketplace whilst it is being rewritten.
# marimo-team.vscode-marimo
marimo-team.vscode-marimo

Copilot AI Nov 23, 2025

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The marimo extension is being installed on line 9 despite the comment on line 8 stating that "The marimo extension has been removed from the marketplace whilst it is being rewritten." This inconsistency suggests that either the extension has been re-added to the marketplace (in which case the comment should be updated or removed), or the extension should remain commented out.

Suggested change
marimo-team.vscode-marimo
# marimo-team.vscode-marimo

Copilot uses AI. Check for mistakes.
mechatroner.rainbow-csv
ms-ossdata.vscode-pgsql --pre-release
ms-python.black-formatter
ms-toolsai.datawrangler
ms-toolsai.jupyter
#openai.chatgpt
qwenlm.qwen-code-vscode-ide-companion
REditorSupport.r
REditorSupport.r-syntax
Comment on lines 17 to 18

Copilot AI Nov 23, 2025

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

R-related VS Code extensions are still configured for installation (lines 17-18) even though the R language support feature has been commented out (lines 36-44). The extensions REditorSupport.r and REditorSupport.r-syntax will be installed but may not function properly without the underlying R language support. Consider either:

  1. Commenting out these R extensions as well, or
  2. Uncommenting the R language support feature if R functionality is still needed
Suggested change
REditorSupport.r
REditorSupport.r-syntax
# REditorSupport.r
# REditorSupport.r-syntax

Copilot uses AI. Check for mistakes.
yzhang.markdown-all-in-one
1 change: 1 addition & 0 deletions .github/workflows/build-devcontainer.yml
Original file line number Diff line number Diff line change
Expand Up @@ -117,6 +117,7 @@ jobs:
imageTag: ${{ steps.tags.outputs.tags }}
cacheFrom: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}
push: always
platform: linux/amd64
# Test the container with a simple validation
runCmd: |
echo "=== Testing dev container ==="
Expand Down
7 changes: 5 additions & 2 deletions Dockerfile
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
FROM mcr.microsoft.com/devcontainers/base:noble
FROM --platform=linux/amd64 mcr.microsoft.com/devcontainers/base:noble

# VS Code commit ID for devcontainer compatibility. Can be overridden at build time via build args.
# Default chosen for current stable VS Code Server version used in this repository.
Expand All @@ -9,14 +9,17 @@ ENV VSCODE_COMMIT=${VSCODE_COMMIT}
# Copy and run VS Code installation files
COPY .devcontainer/vscode-init /opt/vscode-init

# Copy Qwen settings
COPY .devcontainer/qwen-settings.json /root/.qwen/settings.json

# Copy Codex config
COPY .devcontainer/codex-config.toml /root/.codex/config.toml

# Copy Continue Dev config
COPY .devcontainer/continue-config.yaml /root/.continue/config.yaml
COPY .devcontainer/continue.env /root/.continue/.env

# Copy scripts folder
# Copy scripts folder to /opt/scripts (accessible at runtime)
COPY scripts /opt/scripts

RUN cd /opt/vscode-init \
Expand Down
8 changes: 4 additions & 4 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -66,7 +66,7 @@ ces-pull a a ghcr.io/smartdatafoundry/devcontainer:latest
# 2. Extract the setup scripts
podman run --rm -v $HOME:$HOME -w $HOME \
ghcr.io/smartdatafoundry/devcontainer:latest \
cp -r /workspace/scripts $HOME/devcontainer-scripts
cp -r /opt/scripts $HOME/devcontainer-scripts

# 3. Run the setup script (one-time setup)
cd $HOME/devcontainer-scripts
Expand All @@ -79,10 +79,10 @@ devcontainerctl start
The setup script will:
- Create a symlink to `devcontainerctl` in `~/bin`
- Add `~/bin` to your PATH
- Configure a daily cron job to keep the image updated
- Configure a daily cron job (8:00 AM) to update your container with the latest version

Available `devcontainerctl` commands:
- `devcontainerctl start` - Pull latest image and start container
- `devcontainerctl start` - Start container with existing image
- `devcontainerctl stop` - Stop the container
- `devcontainerctl restart` - Restart the container
- `devcontainerctl status` - Check container status
Expand Down Expand Up @@ -147,7 +147,7 @@ This dev container includes comprehensive R language support through the [Rocker

## ⚙️ VS Code Server

Pre-installed. Pin a version using the tag families described above or via build arg `VSCODE_COMMIT`. For environment-specific considerations (e.g. TRE) see [`docs/SDF_TRE_SETUP.md`](docs/SDF_TRE_SETUP.md).
Pre-installed. Pin a version using the tag families described above or via build arg `VSCODE_COMMIT` (default: `7d842fb85a0275a4a8e4d7e040d2625abbf7f084`). For environment-specific considerations (e.g. TRE) see [`docs/SDF_TRE_SETUP.md`](docs/SDF_TRE_SETUP.md).

## Adding New Extensions
To add new VS Code extensions to the container, follow these steps:
Expand Down
19 changes: 11 additions & 8 deletions docs/DEVCONTAINER.md
Original file line number Diff line number Diff line change
Expand Up @@ -75,11 +75,11 @@ This dev container includes:
* **Marimo**: Alternative interactive notebook/presentation tool
* **VS Code Server**: Pre-installed (pin via tag families)
* **VS Code Extensions**: Curated list (see [`.devcontainer/vscode-init/extensions-to-install.txt`](.devcontainer/vscode-init/extensions-to-install.txt))
* **User Setup Scripts**: Automated deployment and management tools
* **User Setup Scripts**: Automated deployment and management tools (at `/opt/scripts/` in container)

### User Setup Scripts

The container includes scripts in [`/workspace/scripts/`](scripts/) to simplify deployment and management:
The container includes scripts in [`/opt/scripts/`](../scripts/) to simplify deployment and management:

#### [`scripts/devcontainerctl`](scripts/devcontainerctl)
A comprehensive container lifecycle management script that provides:
Expand All @@ -103,10 +103,13 @@ A comprehensive container lifecycle management script that provides:

**Usage:**
```bash
devcontainerctl start # Start with auto-detected VS Code version
devcontainerctl start vscode-abc123 # Start with specific tag
devcontainerctl status # Check status
devcontainerctl sync # Update image (used by daily cron)
devcontainerctl start # Start with auto-detected VS Code version (image must already be pulled; run 'update' or 'sync' first if needed)
devcontainerctl start vscode-abc123 # Start with specific tag (image must already be pulled)
devcontainerctl status # Check status
devcontainerctl sync # Update image (used by daily cron)
devcontainerctl update # Update and restart
devcontainerctl stop # Stop container
devcontainerctl remove # Remove container
```

#### [`scripts/setup.sh`](scripts/setup.sh)
Expand All @@ -116,14 +119,14 @@ One-time setup script that configures your environment:
- Creates `~/bin` directory if needed
- Creates symlink to `devcontainerctl` in `~/bin`
- Adds `~/bin` to PATH in `~/.bashrc`
- Configures daily cron job (8:00 AM) to sync images
- Configures daily cron job (8:00 AM) to sync images using `devcontainerctl sync`

**Usage:**
```bash
# Extract scripts from container first
podman run --rm -v $HOME:$HOME -w $HOME \
ghcr.io/smartdatafoundry/devcontainer:latest \
cp -r /workspace/scripts $HOME/devcontainer-scripts
cp -r /opt/scripts $HOME/devcontainer-scripts

# Run setup
cd $HOME/devcontainer-scripts
Expand Down
Loading