mirror of
https://github.com/actions/runner.git
synced 2025-12-12 15:13:30 +00:00
Compare commits
3 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
4d17f77f5e | ||
|
|
3e46f55ac9 | ||
|
|
ed15c5389b |
@@ -26,23 +26,6 @@ Run as a one-liner. NOTE: replace with yourorg/yourrepo (repo level) or just you
|
|||||||
curl -s https://raw.githubusercontent.com/actions/runner/main/scripts/create-latest-svc.sh | bash -s yourorg/yourrepo
|
curl -s https://raw.githubusercontent.com/actions/runner/main/scripts/create-latest-svc.sh | bash -s yourorg/yourrepo
|
||||||
```
|
```
|
||||||
|
|
||||||
You can call the script with additional arguments:
|
|
||||||
```bash
|
|
||||||
# Usage:
|
|
||||||
# export RUNNER_CFG_PAT=<yourPAT>
|
|
||||||
# ./create-latest-svc -s scope -g [ghe_domain] -n [name] -u [user] -l [labels]
|
|
||||||
# -s required scope: repo (:owner/:repo) or org (:organization)
|
|
||||||
# -g optional ghe_hostname: the fully qualified domain name of your GitHub Enterprise Server deployment
|
|
||||||
# -n optional name of the runner, defaults to hostname
|
|
||||||
# -u optional user svc will run as, defaults to current
|
|
||||||
# -l optional list of labels (split by comma) applied on the runner"
|
|
||||||
```
|
|
||||||
|
|
||||||
Use `--` to pass any number of optional named parameters:
|
|
||||||
|
|
||||||
```
|
|
||||||
curl -s https://raw.githubusercontent.com/actions/runner/main/scripts/create-latest-svc.sh | bash -s -- -s myorg/myrepo -n myname -l label1,label2
|
|
||||||
```
|
|
||||||
### Why can't I use a container?
|
### Why can't I use a container?
|
||||||
|
|
||||||
The runner is installed as a service using `systemd` and `systemctl`. Docker does not support `systemd` for service configuration on a container.
|
The runner is installed as a service using `systemd` and `systemctl`. Docker does not support `systemd` for service configuration on a container.
|
||||||
|
|||||||
@@ -2,10 +2,14 @@
|
|||||||
|
|
||||||
## Bugs
|
## Bugs
|
||||||
|
|
||||||
- Fixed an issue where GHES runners fail to download public docker images (#1199)
|
- Fixed a bug where composite actions did not respect `continue-on-error` (#1238)
|
||||||
|
- Fixed a bug where composite actions post steps did not have the correct step context (#1243)
|
||||||
|
|
||||||
|
|
||||||
## Misc
|
## Misc
|
||||||
|
|
||||||
|
- Correctly finish Job when worker crashes with IO Exceptions (#1239)
|
||||||
|
|
||||||
## Windows x64
|
## Windows x64
|
||||||
We recommend configuring the runner in a root folder of the Windows drive (e.g. "C:\actions-runner"). This will help avoid issues related to service identity folder permissions and long file path restrictions on Windows.
|
We recommend configuring the runner in a root folder of the Windows drive (e.g. "C:\actions-runner"). This will help avoid issues related to service identity folder permissions and long file path restrictions on Windows.
|
||||||
|
|
||||||
|
|||||||
@@ -1 +1 @@
|
|||||||
2.281.0
|
2.280.1
|
||||||
|
|||||||
@@ -2,68 +2,36 @@
|
|||||||
|
|
||||||
set -e
|
set -e
|
||||||
|
|
||||||
|
#
|
||||||
|
# Downloads latest releases (not pre-release) runner
|
||||||
|
# Configures as a service
|
||||||
|
#
|
||||||
|
# Examples:
|
||||||
|
# RUNNER_CFG_PAT=<yourPAT> ./create-latest-svc.sh myuser/myrepo my.ghe.deployment.net
|
||||||
|
# RUNNER_CFG_PAT=<yourPAT> ./create-latest-svc.sh myorg my.ghe.deployment.net
|
||||||
|
#
|
||||||
|
# Usage:
|
||||||
|
# export RUNNER_CFG_PAT=<yourPAT>
|
||||||
|
# ./create-latest-svc scope [ghe_domain] [name] [user] [labels]
|
||||||
|
#
|
||||||
|
# scope required repo (:owner/:repo) or org (:organization)
|
||||||
|
# ghe_domain optional the fully qualified domain name of your GitHub Enterprise Server deployment
|
||||||
|
# name optional defaults to hostname
|
||||||
|
# user optional user svc will run as. defaults to current
|
||||||
|
# labels optional list of labels (split by comma) applied on the runner
|
||||||
|
#
|
||||||
# Notes:
|
# Notes:
|
||||||
# PATS over envvars are more secure
|
# PATS over envvars are more secure
|
||||||
# Downloads latest runner release (not pre-release)
|
|
||||||
# Configures it as a service more secure
|
|
||||||
# Should be used on VMs and not containers
|
# Should be used on VMs and not containers
|
||||||
# Works on OSX and Linux
|
# Works on OSX and Linux
|
||||||
# Assumes x64 arch
|
# Assumes x64 arch
|
||||||
# See EXAMPLES below
|
#
|
||||||
|
|
||||||
flags_found=false
|
runner_scope=${1}
|
||||||
|
ghe_hostname=${2}
|
||||||
while getopts 's:g:n:u:l:' opt; do
|
runner_name=${3:-$(hostname)}
|
||||||
flags_found=true
|
svc_user=${4:-$USER}
|
||||||
|
labels=${5}
|
||||||
case $opt in
|
|
||||||
s)
|
|
||||||
runner_scope=$OPTARG
|
|
||||||
;;
|
|
||||||
g)
|
|
||||||
ghe_hostname=$OPTARG
|
|
||||||
;;
|
|
||||||
n)
|
|
||||||
runner_name=$OPTARG
|
|
||||||
;;
|
|
||||||
u)
|
|
||||||
svc_user=$OPTARG
|
|
||||||
;;
|
|
||||||
l)
|
|
||||||
labels=$OPTARG
|
|
||||||
;;
|
|
||||||
*)
|
|
||||||
echo "
|
|
||||||
Runner Service Installer
|
|
||||||
Examples:
|
|
||||||
RUNNER_CFG_PAT=<yourPAT> ./create-latest-svc.sh myuser/myrepo my.ghe.deployment.net
|
|
||||||
RUNNER_CFG_PAT=<yourPAT> ./create-latest-svc.sh -s myorg -u user_name -l label1,label2
|
|
||||||
Usage:
|
|
||||||
export RUNNER_CFG_PAT=<yourPAT>
|
|
||||||
./create-latest-svc scope [ghe_domain] [name] [user] [labels]
|
|
||||||
-s required scope: repo (:owner/:repo) or org (:organization)
|
|
||||||
-g optional ghe_hostname: the fully qualified domain name of your GitHub Enterprise Server deployment
|
|
||||||
-n optional name of the runner, defaults to hostname
|
|
||||||
-u optional user svc will run as, defaults to current
|
|
||||||
-l optional list of labels (split by comma) applied on the runner"
|
|
||||||
exit 0
|
|
||||||
;;
|
|
||||||
esac
|
|
||||||
done
|
|
||||||
|
|
||||||
shift "$((OPTIND - 1))"
|
|
||||||
|
|
||||||
if ! "$flags_found"; then
|
|
||||||
runner_scope=${1}
|
|
||||||
ghe_hostname=${2}
|
|
||||||
runner_name=${3:-$(hostname)}
|
|
||||||
svc_user=${4:-$USER}
|
|
||||||
labels=${5}
|
|
||||||
fi
|
|
||||||
|
|
||||||
# apply defaults
|
|
||||||
runner_name=${runner_name:-$(hostname)}
|
|
||||||
svc_user=${svc_user:-$USER}
|
|
||||||
|
|
||||||
echo "Configuring runner @ ${runner_scope}"
|
echo "Configuring runner @ ${runner_scope}"
|
||||||
sudo echo
|
sudo echo
|
||||||
@@ -174,7 +142,7 @@ echo
|
|||||||
echo "Configuring as a service ..."
|
echo "Configuring as a service ..."
|
||||||
prefix=""
|
prefix=""
|
||||||
if [ "${runner_plat}" == "linux" ]; then
|
if [ "${runner_plat}" == "linux" ]; then
|
||||||
prefix="sudo "
|
prefix="sudo "
|
||||||
fi
|
fi
|
||||||
|
|
||||||
${prefix}./svc.sh install ${svc_user}
|
${prefix}./svc.sh install ${svc_user}
|
||||||
|
|||||||
@@ -90,8 +90,6 @@ namespace GitHub.Runner.Common
|
|||||||
this.SecretMasker.AddValueEncoder(ValueEncoders.UriDataEscape);
|
this.SecretMasker.AddValueEncoder(ValueEncoders.UriDataEscape);
|
||||||
this.SecretMasker.AddValueEncoder(ValueEncoders.XmlDataEscape);
|
this.SecretMasker.AddValueEncoder(ValueEncoders.XmlDataEscape);
|
||||||
this.SecretMasker.AddValueEncoder(ValueEncoders.TrimDoubleQuotes);
|
this.SecretMasker.AddValueEncoder(ValueEncoders.TrimDoubleQuotes);
|
||||||
this.SecretMasker.AddValueEncoder(ValueEncoders.PowerShellPreAmpersandEscape);
|
|
||||||
this.SecretMasker.AddValueEncoder(ValueEncoders.PowerShellPostAmpersandEscape);
|
|
||||||
|
|
||||||
// Create the trace manager.
|
// Create the trace manager.
|
||||||
if (string.IsNullOrEmpty(logFile))
|
if (string.IsNullOrEmpty(logFile))
|
||||||
|
|||||||
@@ -117,7 +117,6 @@ namespace GitHub.Runner.Listener.Configuration
|
|||||||
try
|
try
|
||||||
{
|
{
|
||||||
// Determine the service deployment type based on connection data. (Hosted/OnPremises)
|
// Determine the service deployment type based on connection data. (Hosted/OnPremises)
|
||||||
// Hosted usually means github.com or localhost, while OnPremises means GHES or GHAE
|
|
||||||
runnerSettings.IsHostedServer = runnerSettings.GitHubUrl == null || UrlUtil.IsHostedServer(new UriBuilder(runnerSettings.GitHubUrl));
|
runnerSettings.IsHostedServer = runnerSettings.GitHubUrl == null || UrlUtil.IsHostedServer(new UriBuilder(runnerSettings.GitHubUrl));
|
||||||
|
|
||||||
// Warn if the Actions server url and GHES server url has different Host
|
// Warn if the Actions server url and GHES server url has different Host
|
||||||
|
|||||||
@@ -610,7 +610,6 @@ namespace GitHub.Runner.Worker
|
|||||||
{
|
{
|
||||||
NameWithOwner = repositoryReference.Name,
|
NameWithOwner = repositoryReference.Name,
|
||||||
Ref = repositoryReference.Ref,
|
Ref = repositoryReference.Ref,
|
||||||
Path = repositoryReference.Path,
|
|
||||||
};
|
};
|
||||||
})
|
})
|
||||||
.ToList();
|
.ToList();
|
||||||
|
|||||||
@@ -494,8 +494,7 @@ namespace GitHub.Runner.Worker
|
|||||||
private void UpdateRegistryAuthForGitHubToken(IExecutionContext executionContext, ContainerInfo container)
|
private void UpdateRegistryAuthForGitHubToken(IExecutionContext executionContext, ContainerInfo container)
|
||||||
{
|
{
|
||||||
var registryIsTokenCompatible = container.RegistryServer.Equals("ghcr.io", StringComparison.OrdinalIgnoreCase) || container.RegistryServer.Equals("containers.pkg.github.com", StringComparison.OrdinalIgnoreCase);
|
var registryIsTokenCompatible = container.RegistryServer.Equals("ghcr.io", StringComparison.OrdinalIgnoreCase) || container.RegistryServer.Equals("containers.pkg.github.com", StringComparison.OrdinalIgnoreCase);
|
||||||
var isFallbackTokenFromHostedGithub = HostContext.GetService<IConfigurationStore>().GetSettings().IsHostedServer;
|
if (!registryIsTokenCompatible)
|
||||||
if (!registryIsTokenCompatible || !isFallbackTokenFromHostedGithub)
|
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -295,108 +295,99 @@ namespace GitHub.Runner.Worker.Handlers
|
|||||||
CancellationTokenRegistration? jobCancelRegister = null;
|
CancellationTokenRegistration? jobCancelRegister = null;
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
// For main steps just run the action
|
// Register job cancellation call back only if job cancellation token not been fire before each step run
|
||||||
if (stage == ActionRunStage.Main)
|
if (!ExecutionContext.Root.CancellationToken.IsCancellationRequested)
|
||||||
{
|
{
|
||||||
await RunStepAsync(step);
|
// Test the condition again. The job was canceled after the condition was originally evaluated.
|
||||||
|
jobCancelRegister = ExecutionContext.Root.CancellationToken.Register(() =>
|
||||||
|
{
|
||||||
|
// Mark job as cancelled
|
||||||
|
ExecutionContext.Root.Result = TaskResult.Canceled;
|
||||||
|
ExecutionContext.Root.JobContext.Status = ExecutionContext.Root.Result?.ToActionResult();
|
||||||
|
|
||||||
|
step.ExecutionContext.Debug($"Re-evaluate condition on job cancellation for step: '{step.DisplayName}'.");
|
||||||
|
var conditionReTestTraceWriter = new ConditionTraceWriter(Trace, null); // host tracing only
|
||||||
|
var conditionReTestResult = false;
|
||||||
|
if (HostContext.RunnerShutdownToken.IsCancellationRequested)
|
||||||
|
{
|
||||||
|
step.ExecutionContext.Debug($"Skip Re-evaluate condition on runner shutdown.");
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
var templateEvaluator = step.ExecutionContext.ToPipelineTemplateEvaluator(conditionReTestTraceWriter);
|
||||||
|
var condition = new BasicExpressionToken(null, null, null, step.Condition);
|
||||||
|
conditionReTestResult = templateEvaluator.EvaluateStepIf(condition, step.ExecutionContext.ExpressionValues, step.ExecutionContext.ExpressionFunctions, step.ExecutionContext.ToExpressionState());
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
// Cancel the step since we get exception while re-evaluate step condition
|
||||||
|
Trace.Info("Caught exception from expression when re-test condition on job cancellation.");
|
||||||
|
step.ExecutionContext.Error(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!conditionReTestResult)
|
||||||
|
{
|
||||||
|
// Cancel the step
|
||||||
|
Trace.Info("Cancel current running step.");
|
||||||
|
step.ExecutionContext.CancelToken();
|
||||||
|
}
|
||||||
|
});
|
||||||
}
|
}
|
||||||
// We need to evaluate conditions for pre/post steps
|
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
// Register job cancellation call back only if job cancellation token not been fire before each step run
|
if (ExecutionContext.Root.Result != TaskResult.Canceled)
|
||||||
if (!ExecutionContext.Root.CancellationToken.IsCancellationRequested)
|
|
||||||
{
|
{
|
||||||
// Test the condition again. The job was canceled after the condition was originally evaluated.
|
// Mark job as cancelled
|
||||||
jobCancelRegister = ExecutionContext.Root.CancellationToken.Register(() =>
|
ExecutionContext.Root.Result = TaskResult.Canceled;
|
||||||
{
|
ExecutionContext.Root.JobContext.Status = ExecutionContext.Root.Result?.ToActionResult();
|
||||||
// Mark job as cancelled
|
|
||||||
ExecutionContext.Root.Result = TaskResult.Canceled;
|
|
||||||
ExecutionContext.Root.JobContext.Status = ExecutionContext.Root.Result?.ToActionResult();
|
|
||||||
|
|
||||||
step.ExecutionContext.Debug($"Re-evaluate condition on job cancellation for step: '{step.DisplayName}'.");
|
|
||||||
var conditionReTestTraceWriter = new ConditionTraceWriter(Trace, null); // host tracing only
|
|
||||||
var conditionReTestResult = false;
|
|
||||||
if (HostContext.RunnerShutdownToken.IsCancellationRequested)
|
|
||||||
{
|
|
||||||
step.ExecutionContext.Debug($"Skip Re-evaluate condition on runner shutdown.");
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
var templateEvaluator = step.ExecutionContext.ToPipelineTemplateEvaluator(conditionReTestTraceWriter);
|
|
||||||
var condition = new BasicExpressionToken(null, null, null, step.Condition);
|
|
||||||
conditionReTestResult = templateEvaluator.EvaluateStepIf(condition, step.ExecutionContext.ExpressionValues, step.ExecutionContext.ExpressionFunctions, step.ExecutionContext.ToExpressionState());
|
|
||||||
}
|
|
||||||
catch (Exception ex)
|
|
||||||
{
|
|
||||||
// Cancel the step since we get exception while re-evaluate step condition
|
|
||||||
Trace.Info("Caught exception from expression when re-test condition on job cancellation.");
|
|
||||||
step.ExecutionContext.Error(ex);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!conditionReTestResult)
|
|
||||||
{
|
|
||||||
// Cancel the step
|
|
||||||
Trace.Info("Cancel current running step.");
|
|
||||||
step.ExecutionContext.CancelToken();
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
else
|
}
|
||||||
|
// Evaluate condition
|
||||||
|
step.ExecutionContext.Debug($"Evaluating condition for step: '{step.DisplayName}'");
|
||||||
|
var conditionTraceWriter = new ConditionTraceWriter(Trace, step.ExecutionContext);
|
||||||
|
var conditionResult = false;
|
||||||
|
var conditionEvaluateError = default(Exception);
|
||||||
|
if (HostContext.RunnerShutdownToken.IsCancellationRequested)
|
||||||
|
{
|
||||||
|
step.ExecutionContext.Debug($"Skip evaluate condition on runner shutdown.");
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
try
|
||||||
{
|
{
|
||||||
if (ExecutionContext.Root.Result != TaskResult.Canceled)
|
var templateEvaluator = step.ExecutionContext.ToPipelineTemplateEvaluator(conditionTraceWriter);
|
||||||
{
|
var condition = new BasicExpressionToken(null, null, null, step.Condition);
|
||||||
// Mark job as cancelled
|
conditionResult = templateEvaluator.EvaluateStepIf(condition, step.ExecutionContext.ExpressionValues, step.ExecutionContext.ExpressionFunctions, step.ExecutionContext.ToExpressionState());
|
||||||
ExecutionContext.Root.Result = TaskResult.Canceled;
|
|
||||||
ExecutionContext.Root.JobContext.Status = ExecutionContext.Root.Result?.ToActionResult();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
// Evaluate condition
|
catch (Exception ex)
|
||||||
step.ExecutionContext.Debug($"Evaluating condition for step: '{step.DisplayName}'");
|
|
||||||
var conditionTraceWriter = new ConditionTraceWriter(Trace, step.ExecutionContext);
|
|
||||||
var conditionResult = false;
|
|
||||||
var conditionEvaluateError = default(Exception);
|
|
||||||
if (HostContext.RunnerShutdownToken.IsCancellationRequested)
|
|
||||||
{
|
{
|
||||||
step.ExecutionContext.Debug($"Skip evaluate condition on runner shutdown.");
|
Trace.Info("Caught exception from expression.");
|
||||||
}
|
Trace.Error(ex);
|
||||||
else
|
conditionEvaluateError = ex;
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
var templateEvaluator = step.ExecutionContext.ToPipelineTemplateEvaluator(conditionTraceWriter);
|
|
||||||
var condition = new BasicExpressionToken(null, null, null, step.Condition);
|
|
||||||
conditionResult = templateEvaluator.EvaluateStepIf(condition, step.ExecutionContext.ExpressionValues, step.ExecutionContext.ExpressionFunctions, step.ExecutionContext.ToExpressionState());
|
|
||||||
}
|
|
||||||
catch (Exception ex)
|
|
||||||
{
|
|
||||||
Trace.Info("Caught exception from expression.");
|
|
||||||
Trace.Error(ex);
|
|
||||||
conditionEvaluateError = ex;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (!conditionResult && conditionEvaluateError == null)
|
|
||||||
{
|
|
||||||
// Condition is false
|
|
||||||
Trace.Info("Skipping step due to condition evaluation.");
|
|
||||||
step.ExecutionContext.Result = TaskResult.Skipped;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
else if (conditionEvaluateError != null)
|
|
||||||
{
|
|
||||||
// Condition error
|
|
||||||
step.ExecutionContext.Error(conditionEvaluateError);
|
|
||||||
step.ExecutionContext.Result = TaskResult.Failed;
|
|
||||||
ExecutionContext.Result = TaskResult.Failed;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
await RunStepAsync(step);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
if (!conditionResult && conditionEvaluateError == null)
|
||||||
|
{
|
||||||
|
// Condition is false
|
||||||
|
Trace.Info("Skipping step due to condition evaluation.");
|
||||||
|
step.ExecutionContext.Result = TaskResult.Skipped;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
else if (conditionEvaluateError != null)
|
||||||
|
{
|
||||||
|
// Condition error
|
||||||
|
step.ExecutionContext.Error(conditionEvaluateError);
|
||||||
|
step.ExecutionContext.Result = TaskResult.Failed;
|
||||||
|
ExecutionContext.Result = TaskResult.Failed;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
await RunStepAsync(step);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
finally
|
finally
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -217,7 +217,6 @@ namespace GitHub.Runner.Worker.Handlers
|
|||||||
if (systemConnection.Data.TryGetValue("GenerateIdTokenUrl", out var generateIdTokenUrl) && !string.IsNullOrEmpty(generateIdTokenUrl))
|
if (systemConnection.Data.TryGetValue("GenerateIdTokenUrl", out var generateIdTokenUrl) && !string.IsNullOrEmpty(generateIdTokenUrl))
|
||||||
{
|
{
|
||||||
Environment["ACTIONS_ID_TOKEN_REQUEST_URL"] = generateIdTokenUrl;
|
Environment["ACTIONS_ID_TOKEN_REQUEST_URL"] = generateIdTokenUrl;
|
||||||
Environment["ACTIONS_ID_TOKEN_REQUEST_TOKEN"] = systemConnection.Authorization.Parameters[EndpointAuthorizationParameters.AccessToken];
|
|
||||||
}
|
}
|
||||||
|
|
||||||
foreach (var variable in this.Environment)
|
foreach (var variable in this.Environment)
|
||||||
|
|||||||
@@ -56,7 +56,6 @@ namespace GitHub.Runner.Worker.Handlers
|
|||||||
if (systemConnection.Data.TryGetValue("GenerateIdTokenUrl", out var generateIdTokenUrl) && !string.IsNullOrEmpty(generateIdTokenUrl))
|
if (systemConnection.Data.TryGetValue("GenerateIdTokenUrl", out var generateIdTokenUrl) && !string.IsNullOrEmpty(generateIdTokenUrl))
|
||||||
{
|
{
|
||||||
Environment["ACTIONS_ID_TOKEN_REQUEST_URL"] = generateIdTokenUrl;
|
Environment["ACTIONS_ID_TOKEN_REQUEST_URL"] = generateIdTokenUrl;
|
||||||
Environment["ACTIONS_ID_TOKEN_REQUEST_TOKEN"] = systemConnection.Authorization.Parameters[EndpointAuthorizationParameters.AccessToken];
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Resolve the target script.
|
// Resolve the target script.
|
||||||
|
|||||||
@@ -147,8 +147,7 @@ namespace GitHub.Runner.Worker.Handlers
|
|||||||
// Add Telemetry to JobContext to send with JobCompleteMessage
|
// Add Telemetry to JobContext to send with JobCompleteMessage
|
||||||
if (stage == ActionRunStage.Main)
|
if (stage == ActionRunStage.Main)
|
||||||
{
|
{
|
||||||
var telemetry = new ActionsStepTelemetry
|
var telemetry = new ActionsStepTelemetry {
|
||||||
{
|
|
||||||
IsEmbedded = ExecutionContext.IsEmbedded,
|
IsEmbedded = ExecutionContext.IsEmbedded,
|
||||||
Type = "run",
|
Type = "run",
|
||||||
};
|
};
|
||||||
@@ -277,13 +276,6 @@ namespace GitHub.Runner.Worker.Handlers
|
|||||||
fileName = node12;
|
fileName = node12;
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
var systemConnection = ExecutionContext.Global.Endpoints.Single(x => string.Equals(x.Name, WellKnownServiceEndpointNames.SystemVssConnection, StringComparison.OrdinalIgnoreCase));
|
|
||||||
if (systemConnection.Data.TryGetValue("GenerateIdTokenUrl", out var generateIdTokenUrl) && !string.IsNullOrEmpty(generateIdTokenUrl))
|
|
||||||
{
|
|
||||||
Environment["ACTIONS_ID_TOKEN_REQUEST_URL"] = generateIdTokenUrl;
|
|
||||||
Environment["ACTIONS_ID_TOKEN_REQUEST_TOKEN"] = systemConnection.Authorization.Parameters[EndpointAuthorizationParameters.AccessToken];
|
|
||||||
}
|
|
||||||
|
|
||||||
ExecutionContext.Debug($"{fileName} {arguments}");
|
ExecutionContext.Debug($"{fileName} {arguments}");
|
||||||
|
|
||||||
using (var stdoutManager = new OutputManager(ExecutionContext, ActionCommandManager))
|
using (var stdoutManager = new OutputManager(ExecutionContext, ActionCommandManager))
|
||||||
|
|||||||
@@ -2,7 +2,6 @@
|
|||||||
using System.ComponentModel;
|
using System.ComponentModel;
|
||||||
using System.Security;
|
using System.Security;
|
||||||
using System.Text;
|
using System.Text;
|
||||||
using System.Text.RegularExpressions;
|
|
||||||
using Newtonsoft.Json;
|
using Newtonsoft.Json;
|
||||||
|
|
||||||
namespace GitHub.DistributedTask.Logging
|
namespace GitHub.DistributedTask.Logging
|
||||||
@@ -81,65 +80,6 @@ namespace GitHub.DistributedTask.Logging
|
|||||||
return trimmed;
|
return trimmed;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static String PowerShellPreAmpersandEscape(String value)
|
|
||||||
{
|
|
||||||
// if the secret is passed to PS as a command and it causes an error, sections of it can be surrounded by color codes
|
|
||||||
// or printed individually.
|
|
||||||
|
|
||||||
// The secret secretpart1&secretpart2&secretpart3 would be split into 2 sections:
|
|
||||||
// 'secretpart1&secretpart2&' and 'secretpart3'. This method masks for the first section.
|
|
||||||
|
|
||||||
// The secret secretpart1&+secretpart2&secretpart3 would be split into 2 sections:
|
|
||||||
// 'secretpart1&+' and (no 's') 'ecretpart2&secretpart3'. This method masks for the first section.
|
|
||||||
|
|
||||||
var trimmed = string.Empty;
|
|
||||||
if (!string.IsNullOrEmpty(value) && value.Contains("&"))
|
|
||||||
{
|
|
||||||
var secretSection = string.Empty;
|
|
||||||
if (value.Contains("&+"))
|
|
||||||
{
|
|
||||||
secretSection = value.Substring(0, value.IndexOf("&+") + "&+".Length);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
secretSection = value.Substring(0, value.LastIndexOf("&") + "&".Length);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Don't mask short secrets
|
|
||||||
if (secretSection.Length >= 6)
|
|
||||||
{
|
|
||||||
trimmed = secretSection;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return trimmed;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String PowerShellPostAmpersandEscape(String value)
|
|
||||||
{
|
|
||||||
var trimmed = string.Empty;
|
|
||||||
if (!string.IsNullOrEmpty(value) && value.Contains("&"))
|
|
||||||
{
|
|
||||||
var secretSection = string.Empty;
|
|
||||||
if (value.Contains("&+"))
|
|
||||||
{
|
|
||||||
// +1 to skip the letter that got colored
|
|
||||||
secretSection = value.Substring(value.IndexOf("&+") + "&+".Length + 1);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
secretSection = value.Substring(value.LastIndexOf("&") + "&".Length);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (secretSection.Length >= 6)
|
|
||||||
{
|
|
||||||
trimmed = secretSection;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return trimmed;
|
|
||||||
}
|
|
||||||
|
|
||||||
private static string Base64StringEscapeShift(String value, int shift)
|
private static string Base64StringEscapeShift(String value, int shift)
|
||||||
{
|
{
|
||||||
var bytes = Encoding.UTF8.GetBytes(value);
|
var bytes = Encoding.UTF8.GetBytes(value);
|
||||||
|
|||||||
@@ -18,12 +18,5 @@ namespace GitHub.DistributedTask.WebApi
|
|||||||
get;
|
get;
|
||||||
set;
|
set;
|
||||||
}
|
}
|
||||||
|
|
||||||
[DataMember]
|
|
||||||
public string Path
|
|
||||||
{
|
|
||||||
get;
|
|
||||||
set;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -112,36 +112,6 @@ namespace GitHub.Runner.Common.Tests
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
[Theory]
|
|
||||||
[InlineData("secret&secret&secret", "secret&secret&\x0033[96msecret\x0033[0m", "***\x0033[96m***\x0033[0m")]
|
|
||||||
[InlineData("secret&secret+secret", "secret&\x0033[96msecret+secret\x0033[0m", "***\x0033[96m***\x0033[0m")]
|
|
||||||
[InlineData("secret+secret&secret", "secret+secret&\x0033[96msecret\x0033[0m", "***\x0033[96m***\x0033[0m")]
|
|
||||||
[InlineData("secret&secret&+secretsecret", "secret&secret&+\x0033[96ms\x0033[0mecretsecret", "***\x0033[96ms\x0033[0m***")]
|
|
||||||
[InlineData("secret&+secret&secret", "secret&+\x0033[96ms\x0033[0mecret&secret", "***\x0033[96ms\x0033[0m***")]
|
|
||||||
[InlineData("secret&+secret&+secret", "secret&+\x0033[96ms\x0033[0mecret&+secret", "***\x0033[96ms\x0033[0m***")]
|
|
||||||
[InlineData("secret&+secret&secret&+secret", "secret&+\x0033[96ms\x0033[0mecret&secret&+secret", "***\x0033[96ms\x0033[0m***")]
|
|
||||||
[Trait("Level", "L0")]
|
|
||||||
[Trait("Category", "Common")]
|
|
||||||
public void SecretSectionMasking(string secret, string rawOutput, string maskedOutput)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
// Arrange.
|
|
||||||
Setup();
|
|
||||||
|
|
||||||
// Act.
|
|
||||||
_hc.SecretMasker.AddValue(secret);
|
|
||||||
|
|
||||||
// Assert.
|
|
||||||
Assert.Equal(maskedOutput, _hc.SecretMasker.MaskSecrets(rawOutput));
|
|
||||||
}
|
|
||||||
finally
|
|
||||||
{
|
|
||||||
// Cleanup.
|
|
||||||
Teardown();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
[Fact]
|
[Fact]
|
||||||
[Trait("Level", "L0")]
|
[Trait("Level", "L0")]
|
||||||
[Trait("Category", "Common")]
|
[Trait("Category", "Common")]
|
||||||
|
|||||||
@@ -1 +1 @@
|
|||||||
2.281.0
|
2.280.1
|
||||||
|
|||||||
Reference in New Issue
Block a user