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
14 changes: 13 additions & 1 deletion src/run/runner/wall_time/executor.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ use crate::run::runner::executor::Executor;
use crate::run::runner::helpers::env::{get_base_injected_env, is_codspeed_debug_enabled};
use crate::run::runner::helpers::get_bench_command::get_bench_command;
use crate::run::runner::helpers::run_command_with_log_pipe::run_command_with_log_pipe;
use crate::run::runner::wall_time::introspected_golang::setup_introspected_go;
use crate::run::runner::{ExecutorName, RunData};
use crate::run::{check_system::SystemInfo, config::Config};
use async_trait::async_trait;
Expand Down Expand Up @@ -106,7 +107,18 @@ impl WallTimeExecutor {
.map(|(k, v)| format!("export {k}={v}",))
.collect::<Vec<_>>()
.join("\n");
let combined_env = format!("{system_env}\n{base_injected_env}");

// We need to intercept the `go` command to ensure we can run it with our custom runner.
let path_env = std::env::var("PATH").unwrap_or_default();
let path_env = format!(
"export PATH={}:{}",
setup_introspected_go()
.map_err(|e| anyhow!("failed to setup Go introspection. {}", e))?
.to_string_lossy(),
path_env
);

let combined_env = format!("{system_env}\n{base_injected_env}\n{path_env}");

let mut env_file = NamedTempFile::new()?;
env_file.write_all(combined_env.as_bytes())?;
Expand Down
47 changes: 47 additions & 0 deletions src/run/runner/wall_time/introspected_golang/go.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
#!/usr/bin/env bash

set -euo pipefail

debug_log() {
if [ "${CODSPEED_LOG:-}" = "debug" ]; then
echo "[DEBUG go.sh] $*" >&2
fi
}

debug_log "Called with arguments: $*"
debug_log "Number of arguments: $#"

# Find the real go binary, so that we don't end up in infinite recursion
REAL_GO=$(which -a go | grep -v "$(realpath "$0")" | head -1)
if [ -z "$REAL_GO" ]; then
echo "ERROR: Could not find real go binary" >&2
exit 1
fi

# Check if we have any arguments
if [ $# -eq 0 ]; then
debug_log "No arguments provided, using standard go binary"
"$REAL_GO"
exit $?
fi

# Check if first argument is "test"
if [ "$1" = "test" ]; then
debug_log "Detected 'test' command, routing to go-runner"

# Find go-runner or install if not found
GO_RUNNER=$(which go-runner 2>/dev/null || true)
if [ -z "$GO_RUNNER" ]; then
curl -fsSL http://github.com/CodSpeedHQ/runner/releases/latest/download/go-runner-installer.sh | bash -s -- --quiet
GO_RUNNER=$(which go-runner 2>/dev/null || true)
fi

debug_log "Using go-runner at: $GO_RUNNER"
debug_log "Full command: RUST_LOG=info $GO_RUNNER $*"

"$GO_RUNNER" "$@"
else
debug_log "Detected non-test command ('$1'), routing to standard go binary"
debug_log "Full command: $REAL_GO $*"
"$REAL_GO" "$@"
fi
19 changes: 19 additions & 0 deletions src/run/runner/wall_time/introspected_golang/mod.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
use crate::prelude::*;
use std::{env, fs::File, io::Write, os::unix::fs::PermissionsExt, path::PathBuf};

const INTROSPECTED_GO_SCRIPT: &str = include_str!("go.sh");

/// Creates the `go` script that will replace the `go` binary while running
/// Returns the path to the script folder, which should be added to the PATH environment variable
pub fn setup_introspected_go() -> Result<PathBuf> {
let script_folder = env::temp_dir().join("codspeed_introspected_go");
std::fs::create_dir_all(&script_folder)?;
let script_path = script_folder.join("go");
let mut script_file = File::create(script_path)?;
script_file.write_all(INTROSPECTED_GO_SCRIPT.as_bytes())?;
// Make the script executable
let mut perms = script_file.metadata()?.permissions();
perms.set_mode(0o755);
script_file.set_permissions(perms)?;
Ok(script_folder)
}
1 change: 1 addition & 0 deletions src/run/runner/wall_time/mod.rs
Original file line number Diff line number Diff line change
@@ -1,2 +1,3 @@
pub mod executor;
pub mod introspected_golang;
pub mod perf;