Skip to content
Open
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
2 changes: 1 addition & 1 deletion src/copilot-cli/devcontainer-feature.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"id": "copilot-cli",
"version": "1.1.2",
"version": "1.1.3",
"name": "GitHub Copilot CLI",
"documentationURL": "https://github.com/devcontainers/features/tree/main/src/copilot-cli",
"description": "Installs the GitHub Copilot CLI.",
Expand Down
12 changes: 11 additions & 1 deletion src/copilot-cli/install.sh
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,16 @@ download_from_github() {
rm -rf /tmp/copilotcli
}

# Resolves the latest prerelease version tag from a remote repository.
# Filters to well-formed vX.Y.Z or vX.Y.Z-N tags and sorts by version.
resolve_prerelease_version() {
local repo_url="${1:?resolve_prerelease_version requires a repository URL}"
git ls-remote --tags "${repo_url}" \
| awk '{print $2}' | sed 's|refs/tags/||' \
| grep -E '^v[0-9]+\.[0-9]+\.[0-9]+(-[0-9]+)?$' \
| sort -V | tail -n1
}

install_using_github() {
check_packages wget tar ca-certificates git
echo "Finished setting up dependencies"
Expand All @@ -63,7 +73,7 @@ install_using_github() {
if [ "${CLI_VERSION}" = "latest" ]; then
download_from_github "https://github.com/github/copilot-cli/releases/latest/download/${cli_filename}"
elif [ "${CLI_VERSION}" = "prerelease" ]; then
prerelease_version="$(git ls-remote --tags https://github.com/github/copilot-cli | tail -1 | awk -F/ '{print $NF}')"
prerelease_version="$(resolve_prerelease_version "https://github.com/github/copilot-cli")"
download_from_github "https://github.com/github/copilot-cli/releases/download/${prerelease_version}/${cli_filename}"
else
# Install specific version
Expand Down
54 changes: 54 additions & 0 deletions test/copilot-cli/resolve_prerelease_version.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
#!/bin/bash

set -e

# Optional: Import test library
source dev-container-features-test-lib

# Define the function under test (matches src/copilot-cli/install.sh)
resolve_prerelease_version() {
local repo_url="${1:?resolve_prerelease_version requires a repository URL}"
git ls-remote --tags "${repo_url}" \
| awk '{print $2}' | sed 's|refs/tags/||' \
| grep -E '^v[0-9]+\.[0-9]+\.[0-9]+(-[0-9]+)?$' \
| sort -V | tail -n1
Comment on lines +12 to +14
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

My intention was that we test just this part (without the git part to simplify tests), and also without rewriting the function. Happy to approve to unblock this but would appreciate if we can have this as a follow-up.

}

# Create a mock git script that returns controlled output
MOCK_DIR="$(mktemp -d)"
cat > "${MOCK_DIR}/git" << 'SCRIPT'
#!/bin/bash
# Return mock ls-remote output based on the repo URL argument
repo="${*: -1}"
case "${repo}" in
"mock://basic")
printf 'abc1234\trefs/tags/v1.0.1\ndef5678\trefs/tags/v1.0.9\nghi9012\trefs/tags/v1.0.10\njkl3456\trefs/tags/v1.0.45\nmno7890\trefs/tags/v1.0.2\n'
;;
"mock://prerelease")
printf 'abc1234\trefs/tags/v1.0.44\ndef5678\trefs/tags/v1.0.45-1\nghi9012\trefs/tags/v1.0.45-10\njkl3456\trefs/tags/v1.0.45-2\nmno7890\trefs/tags/v1.0.45\n'
;;
"mock://stray")
printf 'abc1234\trefs/tags/latest\ndef5678\trefs/tags/v1.0.3\nghi9012\trefs/tags/nightly\njkl3456\trefs/tags/v1.0.20\n'
;;
esac
SCRIPT
chmod +x "${MOCK_DIR}/git"
export PATH="${MOCK_DIR}:${PATH}"

# Test: version sort picks v1.0.45, not v1.0.9
result="$(resolve_prerelease_version "mock://basic")"
check "picks highest version (v1.0.45)" bash -c "[ '${result}' = 'v1.0.45' ]"

# Test: prerelease numeric suffixes sort correctly
result2="$(resolve_prerelease_version "mock://prerelease")"
check "picks highest prerelease (v1.0.45-10)" bash -c "[ '${result2}' = 'v1.0.45-10' ]"

# Test: filters out non-version tags
result3="$(resolve_prerelease_version "mock://stray")"
check "ignores non-version tags" bash -c "[ '${result3}' = 'v1.0.20' ]"

# Cleanup
rm -rf "${MOCK_DIR}"

# Report result
reportResults
10 changes: 10 additions & 0 deletions test/copilot-cli/scenarios.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
{
"resolve_prerelease_version": {
"image": "ubuntu:noble",
"features": {
"copilot-cli": {
"version": "latest"
}
}
}
}
Loading