This repository was archived by the owner on Oct 27, 2025. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 94
Add julia testing skill #6
Open
ericphanson
wants to merge
7
commits into
obra:main
Choose a base branch
from
ericphanson:eph/julia
base: main
Could not load branches
Branch not found: {{ refName }}
Loading
Could not load tags
Nothing to show
Loading
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
Open
Changes from 5 commits
Commits
Show all changes
7 commits
Select commit
Hold shift + click to select a range
864eb29
add julia skill
ericphanson f8e3d9f
wip
ericphanson 81fa45a
Improve julia-tests skill following TDD methodology
ericphanson cf5330f
tweaks
ericphanson bd09ef0
Update scripts/julia-env-info
ericphanson f799fb0
get docs, test_args
ericphanson 64a5d17
Update scripts/julia-env-info
ericphanson File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,94 @@ | ||
| #!/usr/bin/env bash | ||
| set -euo pipefail | ||
| export LC_ALL=C | ||
|
|
||
| have() { command -v "$1" >/dev/null 2>&1; } | ||
|
|
||
| # -------- parse julia_version from Manifest.toml (BSD/GNU portable) -------- | ||
| read_manifest_version() { | ||
| awk -F= ' | ||
| /^[[:space:]]*julia_version[[:space:]]*=/ { | ||
| v=$2 | ||
| gsub(/^[[:space:]]+|[[:space:]]+$/, "", v) | ||
| gsub(/^"|"$/, "", v) | ||
| print v | ||
| exit | ||
| } | ||
| ' "$1" 2>/dev/null || true | ||
| } | ||
|
|
||
| # -------- parse juliaup api getconfig1 (no jq needed) -------- | ||
| read_juliaup_default() { | ||
| # Prints: "<channel_name>\t<version>\t<file>" OR nothing if unavailable | ||
| local cfg dc name ver file | ||
| cfg="$(juliaup api getconfig1 2>/dev/null || true)" || true | ||
| [ -z "${cfg:-}" ] && return 0 | ||
| # Extract the DefaultChannel object | ||
| dc="$(printf '%s' "$cfg" | awk 'match($0,/"DefaultChannel"[[:space:]]*:[[:space:]]*\{[^}]*\}/){print substr($0,RSTART,RLENGTH)}')" | ||
| [ -z "${dc:-}" ] && return 0 | ||
| # Pull fields (quoted strings) | ||
| name="$(printf '%s\n' "$dc" | grep -oE '"Name"[[:space:]]*:[[:space:]]*"[^"]*"' | sed -E 's/.*"Name"[[:space:]]*:[[:space:]]*"([^"]*)".*/\1/' || true)" | ||
| ver="$( printf '%s\n' "$dc" | grep -oE '"Version"[[:space:]]*:[[:space:]]*"[^"]*"' | sed -E 's/.*"Version"[[:space:]]*:[[:space:]]*"([^"]*)".*/\1/' || true)" | ||
| file="$(printf '%s\n' "$dc" | grep -oE '"File"[[:space:]]*:[[:space:]]*"[^"]*"' | sed -E 's/.*"File"[[:space:]]*:[[:space:]]*"([^"]*)".*/\1/' || true)" | ||
| [ -n "$name" ] && printf '%s\t%s\t%s\n' "$name" "$ver" "$file" | ||
| } | ||
|
|
||
| # ---------- ENV ---------- | ||
| ENV_TSV="$(mktemp)"; PROJ_TSV="$(mktemp)"; MAN_TSV="$(mktemp)" | ||
| trap 'rm -f "$ENV_TSV" "$PROJ_TSV" "$MAN_TSV"' EXIT | ||
|
|
||
| { | ||
| printf 'KEY\tVALUE\n' | ||
| jpath="$(command -v julia 2>/dev/null || true)" | ||
| julia_present="no"; julia_ver="unknown" | ||
| if [ -n "${jpath:-}" ]; then | ||
| julia_present="yes" | ||
| if "$jpath" -e 'print(VERSION)' >/dev/null 2>&1; then | ||
| julia_ver="$("$jpath" -e 'print(VERSION)' 2>/dev/null || printf 'unknown')" | ||
| fi | ||
| fi | ||
| printf 'julia_present\t%s\n' "$julia_present" | ||
| printf 'julia_path\t%s\n' "${jpath:-none}" | ||
| printf 'julia_version\t%s\n' "$julia_ver" | ||
|
|
||
| # juliaup details via API | ||
| juliaup_present="no"; uses_juliaup="no"; juliaup_default_channel="unknown"; juliaup_default_version="unknown"; juliaup_default_file="unknown" | ||
| if have juliaup; then | ||
| juliaup_present="yes" | ||
| case "${jpath:-}" in *".juliaup/"*) uses_juliaup="yes" ;; esac | ||
| if read -r ch ver file < <(read_juliaup_default); then | ||
| juliaup_default_channel="$ch" | ||
| [ -n "${ver:-}" ] && juliaup_default_version="$ver" | ||
| [ -n "${file:-}" ] && juliaup_default_file="$file" | ||
| fi | ||
| fi | ||
| printf 'juliaup_present\t%s\n' "$juliaup_present" | ||
| printf 'uses_juliaup\t%s\n' "$uses_juliaup" | ||
| printf 'juliaup_default_channel\t%s\n' "$juliaup_default_channel" | ||
| printf 'juliaup_default_version\t%s\n' "$juliaup_default_version" | ||
| printf 'juliaup_default_file\t%s\n' "$juliaup_default_file" | ||
| } >"$ENV_TSV" | ||
|
|
||
| # ---------- PROJECTS ---------- | ||
| { | ||
| printf 'PATH\n' | ||
| find . -type f -name 'Project.toml' -print0 2>/dev/null \ | ||
| | while IFS= read -r -d '' p; do printf '%s\n' "$p"; done | ||
| } >"$PROJ_TSV" | ||
|
|
||
| # ---------- MANIFESTS ---------- | ||
| { | ||
| printf 'PATH\tjulia_version\n' | ||
| find . -type f -name 'Manifest.toml' -print0 2>/dev/null \ | ||
| | while IFS= read -r -d '' m; do | ||
| v="$(read_manifest_version "$m")" | ||
| printf '%s\t%s\n' "$m" "${v:-unknown}" | ||
| done | ||
| } >"$MAN_TSV" | ||
|
|
||
| # ---------- PRINT (pretty if `column` exists) ---------- | ||
| print_table() { if have column; then column -t -s $'\t' "$1"; else cat "$1"; fi; } | ||
|
|
||
| printf 'ENV\n'; print_table "$ENV_TSV"; printf '\n' | ||
| printf 'PROJECTS\n'; print_table "$PROJ_TSV"; printf '\n' | ||
| printf 'MANIFESTS\n'; print_table "$MAN_TSV"; printf '\n' | ||
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,167 @@ | ||
| --- | ||
| name: Environments and tests in Julia | ||
| description: How to correctly activate environments and run tests in Julia | ||
| when_to_use: When running Julia tests, getting "LoadError" or package not found errors, seeing "Manifest out of date" warnings, struggling with --project flag, need to run specific test files, or want to add test-only dependencies. When working with Julia projects that have Project.toml/Manifest.toml files. | ||
| version: 2.0.0 | ||
| languages: julia | ||
| --- | ||
|
|
||
| # Environments and Tests in Julia | ||
|
|
||
| ## Overview | ||
|
|
||
| **Core principle:** Every Julia process needs `--project=DIR` to activate the correct environment. Tests need their own environment with test-specific dependencies. | ||
|
|
||
| **Julia projects:** Each has a `Project.toml` (dependencies) and optionally `Manifest.toml` (lockfile). | ||
|
|
||
| ## Quick Reference | ||
|
|
||
| | Task | Command | | ||
| |------|---------| | ||
| | Find all projects | `${SUPERPOWERS_SKILLS_ROOT}/scripts/julia-env-info` | | ||
| | Run all tests | `julia --project=. -e 'using Pkg; Pkg.test()'` | | ||
| | Run specific test file | `julia --project=. -e 'using TestEnv; TestEnv.activate(); include("test/file.jl")'` | | ||
| | Fix "Manifest out of date" | `julia --project=. -e 'using Pkg; Pkg.resolve()'` | | ||
| | Instantiate environment | `julia --project=. -e 'using Pkg; Pkg.instantiate()'` | | ||
| | Add test-only dependency | `julia --project=test -e 'using Pkg; Pkg.add("Dep")'` OR `Pkg.add("Dep"; target=:extras)` | | ||
|
|
||
| ## Starting a Julia Task | ||
|
|
||
| **1. Find all Julia projects in the repo:** | ||
| ```sh | ||
| ${SUPERPOWERS_SKILLS_ROOT}/scripts/julia-env-info | ||
| ``` | ||
|
|
||
| Shows: | ||
| - Julia version | ||
| - All Project.toml locations | ||
| - All Manifest.toml files with their Julia versions | ||
|
|
||
| **2. Activate the right project:** | ||
| ```sh | ||
| julia --project=subdir -e '...' # for subdir/Project.toml | ||
| julia --project=. -e '...' # for ./Project.toml | ||
| ``` | ||
|
|
||
| **Always use `--project` flag.** Without it, Julia uses the global environment. | ||
|
|
||
| ## Running Tests | ||
|
|
||
| ### Option 1: Run All Tests (Standard) | ||
|
|
||
| ```sh | ||
| julia --project=. -e 'using Pkg; Pkg.test()' | ||
| ``` | ||
|
|
||
| **Use this when:** | ||
| - Running full test suite | ||
| - CI/CD | ||
| - Not sure how tests are organized | ||
|
|
||
| Pkg finds the test environment automatically. | ||
|
|
||
| ### Option 2: Run Specific Test Files | ||
|
|
||
| **Requirements:** | ||
| - TestEnv.jl installed globally: `julia -e 'using Pkg; Pkg.add("TestEnv")'` | ||
|
|
||
| **Command:** | ||
| ```sh | ||
| julia --project=. -e 'using TestEnv; TestEnv.activate(); include("test/mytests.jl")' | ||
| ``` | ||
|
|
||
| **Use this when:** | ||
| - Full suite takes too long | ||
| - Only changed specific code | ||
| - Developing test-first | ||
|
|
||
| ### Option 3: Direct Test Environment Activation | ||
|
|
||
| If `test/Project.toml` exists: | ||
| ```sh | ||
| julia --project=test -e 'include("test/mytests.jl")' | ||
| ``` | ||
|
|
||
| Options 1 and 2 still work in this case. | ||
|
|
||
| ## Test-Only Dependencies | ||
|
|
||
| Julia has two patterns: | ||
|
|
||
| ### Pattern 1: test/Project.toml | ||
|
|
||
| **If `test/Project.toml` exists**, activate it: | ||
| ```sh | ||
| julia --project=test -e 'using Pkg; Pkg.add("BenchmarkTools")' | ||
| ``` | ||
|
|
||
| ### Pattern 2: [extras] in Main Project.toml | ||
|
|
||
| **If main Project.toml has `[extras]` section:** | ||
|
|
||
| **1. Add to [extras]:** | ||
| ```sh | ||
| julia --project=. -e 'using Pkg; Pkg.add("BenchmarkTools"; target=:extras)' | ||
| ``` | ||
|
|
||
| **2. Manually update [targets]:** | ||
| ```toml | ||
| [extras] | ||
| Test = "8dfed614-e22c-5e08-85e1-65c5234f0b40" | ||
| BenchmarkTools = "6e4b80f9-dd63-53aa-95a3-0cdb28fa8baf" | ||
|
|
||
| [targets] | ||
| test = ["Test", "BenchmarkTools"] # Add BenchmarkTools here | ||
| ``` | ||
|
|
||
| **Which to use:** Check what exists. Don't mix both. | ||
|
|
||
| ## Common Issues | ||
|
|
||
| ### "Manifest out of date" Warning | ||
|
|
||
| **Cause:** Project.toml changed (e.g., after `git pull`) | ||
|
|
||
| **Fix:** | ||
| ```sh | ||
| julia --project=. -e 'using Pkg; Pkg.resolve()' | ||
| ``` | ||
|
|
||
| ### Version Mismatches | ||
|
|
||
| **Cause:** Manifest.toml created with different Julia version | ||
|
|
||
| **Check versions:** | ||
| ```sh | ||
| ${SUPERPOWERS_SKILLS_ROOT}/scripts/julia-env-info | ||
| ``` | ||
|
|
||
| Shows your Julia version and each Manifest's Julia version. | ||
|
|
||
| **Fix:** Re-resolve manifest or delete it (ask user before deleting). | ||
|
|
||
| ### Tests Fail with LoadError | ||
|
|
||
| **Cause:** Wrong environment activated or dependencies not installed | ||
|
|
||
| **Fix:** | ||
| 1. Check `--project` flag points to correct directory | ||
| 2. Run `Pkg.instantiate()` to install dependencies | ||
| 3. For tests, use `Pkg.test()` not direct file execution | ||
|
|
||
| ## Common Mistakes | ||
|
|
||
| | Mistake | Fix | | ||
| |---------|-----| | ||
| | `julia test/runtests.jl` | `julia --project=. test/runtests.jl` | | ||
| | Deleting Manifest.toml carelessly | Ask user before deleting | | ||
| | Missing `--project` flag | Add `--project=.` or `--project=DIR` | | ||
| | Forgetting to resolve after pull | Run `Pkg.resolve()` | | ||
|
|
||
| ## Environment Types | ||
|
|
||
| **Global:** Used without `--project`. Install dev tools here (TestEnv.jl). | ||
|
|
||
| **Local:** Activated with `--project`. Package dependencies. | ||
|
|
||
| **Stacked:** Local environment can use global packages, but packages can't declare undeclared global deps. |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,121 @@ | ||
| # Test Scenarios for julia-tests Skill | ||
|
|
||
| ## Retrieval Scenarios | ||
|
|
||
| ### Scenario 1: First time running Julia tests | ||
| **Agent prompt:** | ||
| ``` | ||
| I need to run tests for this Julia project. I see there's a test/ directory with test files. How do I run them? | ||
|
|
||
| The project has: | ||
| - Project.toml in the root | ||
| - test/runtests.jl | ||
| - test/auth_tests.jl | ||
| ``` | ||
|
|
||
| **Success criteria:** | ||
| - Finds information about --project flag | ||
| - Discovers Pkg.test() as the standard approach | ||
| - Mentions this will run ALL tests | ||
|
|
||
| ### Scenario 2: Manifest out of date warning | ||
| **Agent prompt:** | ||
| ``` | ||
| I pulled the latest changes and now when I start Julia I get: | ||
|
|
||
| Warning: The project dependencies or compat requirements have changed since the manifest was last resolved. | ||
|
|
||
| What should I do? | ||
| ``` | ||
|
|
||
| **Success criteria:** | ||
| - Finds the Pkg.resolve() solution | ||
| - Understands this resolves manifest from Project.toml | ||
| - Knows to use --project flag | ||
|
|
||
| ### Scenario 3: Multiple Julia projects in monorepo | ||
| **Agent prompt:** | ||
| ``` | ||
| This repository seems to have Julia code in multiple directories: | ||
| - server/ | ||
| - client/ | ||
| - docs/ | ||
|
|
||
| How do I figure out which ones are Julia projects and run their tests? | ||
| ``` | ||
|
|
||
| **Success criteria:** | ||
| - Finds julia-env-info script | ||
| - Understands it locates all Project.toml files | ||
| - Knows each needs its own --project activation | ||
|
|
||
| ## Application Scenarios | ||
|
|
||
| ### Scenario 4: Run specific test file | ||
| **Agent prompt:** | ||
| ``` | ||
| The full test suite takes 10 minutes. I only changed authentication code. | ||
| Can you run just test/auth_tests.jl to verify my changes? | ||
|
|
||
| Project structure: | ||
| mypackage/ | ||
| src/ | ||
| test/ | ||
| runtests.jl | ||
| auth_tests.jl | ||
| Project.toml | ||
| ``` | ||
|
|
||
| **Success criteria:** | ||
| - Uses TestEnv.jl OR activates test environment correctly | ||
| - Uses include("test/auth_tests.jl") to run specific file | ||
| - Explains trade-off (TestEnv needs to be installed) | ||
|
|
||
| ### Scenario 5: Clean test environment setup | ||
| **Agent prompt:** | ||
| ``` | ||
| Tests are failing with weird dependency errors. Can you set up a fresh test environment from scratch? | ||
| ``` | ||
|
|
||
| **Success criteria:** | ||
| - Uses Pkg.test() approach (most reliable) | ||
| - Alternatively suggests checking if Manifest.toml can be deleted and re-resolved | ||
| - Asks user before deleting Manifest | ||
|
|
||
| ## Gap Testing | ||
|
|
||
| ### Scenario 6: Julia version mismatch | ||
| **Agent prompt:** | ||
| ``` | ||
| I just upgraded from Julia 1.10 to Julia 1.11. Now when I try to run tests I get errors about package versions. What's wrong? | ||
| ``` | ||
|
|
||
| **Success criteria:** | ||
| - Explains Manifest.toml is version-specific | ||
| - Mentions julia-env-info shows both system version and manifest versions | ||
| - Suggests re-resolving manifest | ||
|
|
||
| ### Scenario 7: Adding test-only dependency | ||
| **Agent prompt:** | ||
| ``` | ||
| I want to use BenchmarkTools.jl in my tests but not as a regular dependency. How do I add it as a test-only dependency? | ||
|
|
||
| My project has a test/Project.toml file. | ||
| ``` | ||
|
|
||
| **Success criteria:** | ||
| - Finds the Test-Only Dependencies section | ||
| - Identifies Pattern 1 (test/Project.toml) is correct for this project | ||
| - Provides command: julia --project=test -e 'using Pkg; Pkg.add("BenchmarkTools")' | ||
| - Does NOT suggest [extras] approach for this project | ||
|
|
||
| ### Scenario 8: Global vs local package installation | ||
| **Agent prompt:** | ||
| ``` | ||
| I want to install TestEnv.jl for development. Should I add it to my project or install it globally? | ||
| ``` | ||
|
|
||
| **Success criteria:** | ||
| - Explains stacked environments (covered briefly) | ||
| - Shows global install without --project flag | ||
| - Explains when to use global vs local |
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.