mirror of
https://github.com/actions/runner.git
synced 2025-12-11 12:57:05 +00:00
Compare commits
7 Commits
releases/m
...
add-mask-b
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
9c6857c60f | ||
|
|
2b7faad20d | ||
|
|
ae6eddbea9 | ||
|
|
088fb13563 | ||
|
|
bd79ba0be7 | ||
|
|
a4c57f2747 | ||
|
|
ce4e62c849 |
18
.github/workflows/close-bugs-bot.yml
vendored
Normal file
18
.github/workflows/close-bugs-bot.yml
vendored
Normal file
@@ -0,0 +1,18 @@
|
|||||||
|
name: Close Bugs Bot
|
||||||
|
on:
|
||||||
|
workflow_dispatch:
|
||||||
|
schedule:
|
||||||
|
- cron: '0 0 * * *' # every day at midnight
|
||||||
|
jobs:
|
||||||
|
stale:
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
steps:
|
||||||
|
- uses: actions/stale@v8
|
||||||
|
with:
|
||||||
|
close-issue-message: "This issue does not seem to be a problem with the runner application, it concerns the GitHub actions platform more generally. Could you please post your feedback on the [GitHub Community Support Forum](https://github.com/orgs/community/discussions/categories/actions) which is actively monitored. Using the forum ensures that we route your problem to the correct team. 😃"
|
||||||
|
exempt-issue-labels: "keep"
|
||||||
|
stale-issue-label: "actions-bug"
|
||||||
|
only-labels: "actions-bug"
|
||||||
|
days-before-stale: 0
|
||||||
|
days-before-close: 1
|
||||||
|
close-issue-reason: "completed"
|
||||||
18
.github/workflows/close-features-bot.yml
vendored
Normal file
18
.github/workflows/close-features-bot.yml
vendored
Normal file
@@ -0,0 +1,18 @@
|
|||||||
|
name: Close Features Bot
|
||||||
|
on:
|
||||||
|
workflow_dispatch:
|
||||||
|
schedule:
|
||||||
|
- cron: '0 0 * * *' # every day at midnight
|
||||||
|
jobs:
|
||||||
|
stale:
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
steps:
|
||||||
|
- uses: actions/stale@v8
|
||||||
|
with:
|
||||||
|
close-issue-message: "Thank you for your interest in the runner application and taking the time to provide your valuable feedback. We kindly ask you to redirect this feedback to the [GitHub Community Support Forum](https://github.com/orgs/community/discussions/categories/actions-and-packages) which our team actively monitors and would be a better place to start a discussion for new feature requests in GitHub Actions. For more information on this policy please [read our contribution guidelines](https://github.com/actions/runner#contribute). 😃"
|
||||||
|
exempt-issue-labels: "keep"
|
||||||
|
stale-issue-label: "actions-feature"
|
||||||
|
only-labels: "actions-feature"
|
||||||
|
days-before-stale: 0
|
||||||
|
days-before-close: 1
|
||||||
|
close-issue-reason: "completed"
|
||||||
@@ -54,6 +54,7 @@ RUN adduser --disabled-password --gecos "" --uid 1001 runner \
|
|||||||
WORKDIR /home/runner
|
WORKDIR /home/runner
|
||||||
|
|
||||||
COPY --chown=runner:docker --from=build /actions-runner .
|
COPY --chown=runner:docker --from=build /actions-runner .
|
||||||
|
COPY --from=build /usr/local/lib/docker/cli-plugins/docker-buildx /usr/local/lib/docker/cli-plugins/docker-buildx
|
||||||
|
|
||||||
RUN install -o root -g root -m 755 docker/* /usr/bin/ && rm -rf docker
|
RUN install -o root -g root -m 755 docker/* /usr/bin/ && rm -rf docker
|
||||||
|
|
||||||
|
|||||||
@@ -1 +1 @@
|
|||||||
2.311.0
|
<Update to ./src/runnerversion when creating release>
|
||||||
|
|||||||
@@ -1,4 +1,5 @@
|
|||||||
using GitHub.Runner.Sdk;
|
using GitHub.Runner.Sdk;
|
||||||
|
using GitHub.Runner.Common.Util;
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
|
||||||
@@ -6,29 +7,28 @@ namespace GitHub.Runner.Common
|
|||||||
{
|
{
|
||||||
public sealed class ActionCommand
|
public sealed class ActionCommand
|
||||||
{
|
{
|
||||||
private static readonly EscapeMapping[] _escapeMappings = new[]
|
private static readonly StringEscapingUtil.EscapeMapping[] _escapeMappings = new[]
|
||||||
{
|
{
|
||||||
new EscapeMapping(token: ";", replacement: "%3B"),
|
new StringEscapingUtil.EscapeMapping(token: ";", replacement: "%3B"),
|
||||||
new EscapeMapping(token: "\r", replacement: "%0D"),
|
new StringEscapingUtil.EscapeMapping(token: "\r", replacement: "%0D"),
|
||||||
new EscapeMapping(token: "\n", replacement: "%0A"),
|
new StringEscapingUtil.EscapeMapping(token: "\n", replacement: "%0A"),
|
||||||
new EscapeMapping(token: "]", replacement: "%5D"),
|
new StringEscapingUtil.EscapeMapping(token: "]", replacement: "%5D"),
|
||||||
new EscapeMapping(token: "%", replacement: "%25"),
|
new StringEscapingUtil.EscapeMapping(token: "%", replacement: "%25"),
|
||||||
};
|
};
|
||||||
|
|
||||||
private static readonly EscapeMapping[] _escapeDataMappings = new[]
|
private static readonly StringEscapingUtil.EscapeMapping[] _escapeDataMappings = new[]
|
||||||
{
|
{
|
||||||
new EscapeMapping(token: "\r", replacement: "%0D"),
|
new StringEscapingUtil.EscapeMapping(token: "\r", replacement: "%0D"),
|
||||||
new EscapeMapping(token: "\n", replacement: "%0A"),
|
new StringEscapingUtil.EscapeMapping(token: "\n", replacement: "%0A"),
|
||||||
new EscapeMapping(token: "%", replacement: "%25"),
|
|
||||||
};
|
};
|
||||||
|
|
||||||
private static readonly EscapeMapping[] _escapePropertyMappings = new[]
|
private static readonly StringEscapingUtil.EscapeMapping[] _escapePropertyMappings = new[]
|
||||||
{
|
{
|
||||||
new EscapeMapping(token: "\r", replacement: "%0D"),
|
new StringEscapingUtil.EscapeMapping(token: "\r", replacement: "%0D"),
|
||||||
new EscapeMapping(token: "\n", replacement: "%0A"),
|
new StringEscapingUtil.EscapeMapping(token: "\n", replacement: "%0A"),
|
||||||
new EscapeMapping(token: ":", replacement: "%3A"),
|
new StringEscapingUtil.EscapeMapping(token: ":", replacement: "%3A"),
|
||||||
new EscapeMapping(token: ",", replacement: "%2C"),
|
new StringEscapingUtil.EscapeMapping(token: ",", replacement: "%2C"),
|
||||||
new EscapeMapping(token: "%", replacement: "%25"),
|
new StringEscapingUtil.EscapeMapping(token: "%", replacement: "%25"),
|
||||||
};
|
};
|
||||||
|
|
||||||
private readonly Dictionary<string, string> _properties = new(StringComparer.OrdinalIgnoreCase);
|
private readonly Dictionary<string, string> _properties = new(StringComparer.OrdinalIgnoreCase);
|
||||||
@@ -103,12 +103,12 @@ namespace GitHub.Runner.Common
|
|||||||
string[] pair = propertyStr.Split(new[] { '=' }, count: 2, options: StringSplitOptions.RemoveEmptyEntries);
|
string[] pair = propertyStr.Split(new[] { '=' }, count: 2, options: StringSplitOptions.RemoveEmptyEntries);
|
||||||
if (pair.Length == 2)
|
if (pair.Length == 2)
|
||||||
{
|
{
|
||||||
command.Properties[pair[0]] = UnescapeProperty(pair[1]);
|
command.Properties[pair[0]] = StringEscapingUtil.UnescapeString(pair[1], _escapePropertyMappings);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
command.Data = UnescapeData(message.Substring(endIndex + _commandKey.Length));
|
command.Data = StringEscapingUtil.UnescapeString(message.Substring(endIndex + _commandKey.Length), _escapeDataMappings);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
catch
|
catch
|
||||||
@@ -173,12 +173,12 @@ namespace GitHub.Runner.Common
|
|||||||
string[] pair = propertyStr.Split(new[] { '=' }, count: 2, options: StringSplitOptions.RemoveEmptyEntries);
|
string[] pair = propertyStr.Split(new[] { '=' }, count: 2, options: StringSplitOptions.RemoveEmptyEntries);
|
||||||
if (pair.Length == 2)
|
if (pair.Length == 2)
|
||||||
{
|
{
|
||||||
command.Properties[pair[0]] = Unescape(pair[1]);
|
command.Properties[pair[0]] = StringEscapingUtil.UnescapeString(pair[1], _escapeMappings);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
command.Data = Unescape(message.Substring(rbIndex + 1));
|
command.Data = StringEscapingUtil.UnescapeString(message.Substring(rbIndex + 1), _escapeMappings);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
catch
|
catch
|
||||||
@@ -187,67 +187,5 @@ namespace GitHub.Runner.Common
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private static string Unescape(string escaped)
|
|
||||||
{
|
|
||||||
if (string.IsNullOrEmpty(escaped))
|
|
||||||
{
|
|
||||||
return string.Empty;
|
|
||||||
}
|
|
||||||
|
|
||||||
string unescaped = escaped;
|
|
||||||
foreach (EscapeMapping mapping in _escapeMappings)
|
|
||||||
{
|
|
||||||
unescaped = unescaped.Replace(mapping.Replacement, mapping.Token);
|
|
||||||
}
|
|
||||||
|
|
||||||
return unescaped;
|
|
||||||
}
|
|
||||||
|
|
||||||
private static string UnescapeProperty(string escaped)
|
|
||||||
{
|
|
||||||
if (string.IsNullOrEmpty(escaped))
|
|
||||||
{
|
|
||||||
return string.Empty;
|
|
||||||
}
|
|
||||||
|
|
||||||
string unescaped = escaped;
|
|
||||||
foreach (EscapeMapping mapping in _escapePropertyMappings)
|
|
||||||
{
|
|
||||||
unescaped = unescaped.Replace(mapping.Replacement, mapping.Token);
|
|
||||||
}
|
|
||||||
|
|
||||||
return unescaped;
|
|
||||||
}
|
|
||||||
|
|
||||||
private static string UnescapeData(string escaped)
|
|
||||||
{
|
|
||||||
if (string.IsNullOrEmpty(escaped))
|
|
||||||
{
|
|
||||||
return string.Empty;
|
|
||||||
}
|
|
||||||
|
|
||||||
string unescaped = escaped;
|
|
||||||
foreach (EscapeMapping mapping in _escapeDataMappings)
|
|
||||||
{
|
|
||||||
unescaped = unescaped.Replace(mapping.Replacement, mapping.Token);
|
|
||||||
}
|
|
||||||
|
|
||||||
return unescaped;
|
|
||||||
}
|
|
||||||
|
|
||||||
private sealed class EscapeMapping
|
|
||||||
{
|
|
||||||
public string Replacement { get; }
|
|
||||||
public string Token { get; }
|
|
||||||
|
|
||||||
public EscapeMapping(string token, string replacement)
|
|
||||||
{
|
|
||||||
ArgUtil.NotNullOrEmpty(token, nameof(token));
|
|
||||||
ArgUtil.NotNullOrEmpty(replacement, nameof(replacement));
|
|
||||||
Token = token;
|
|
||||||
Replacement = replacement;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
41
src/Runner.Common/Util/StringEscapingUtil.cs
Normal file
41
src/Runner.Common/Util/StringEscapingUtil.cs
Normal file
@@ -0,0 +1,41 @@
|
|||||||
|
using System;
|
||||||
|
using System.Threading;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
using GitHub.Runner.Sdk;
|
||||||
|
using GitHub.Runner.Common;
|
||||||
|
|
||||||
|
namespace GitHub.Runner.Common.Util
|
||||||
|
{
|
||||||
|
public static class StringEscapingUtil
|
||||||
|
{
|
||||||
|
|
||||||
|
public static string UnescapeString(string escaped, EscapeMapping[] _escapeDataMappings)
|
||||||
|
{
|
||||||
|
if (string.IsNullOrEmpty(escaped))
|
||||||
|
{
|
||||||
|
return string.Empty;
|
||||||
|
}
|
||||||
|
|
||||||
|
string unescaped = escaped;
|
||||||
|
foreach (EscapeMapping mapping in _escapeDataMappings)
|
||||||
|
{
|
||||||
|
unescaped = unescaped.Replace(mapping.Replacement, mapping.Token);
|
||||||
|
}
|
||||||
|
|
||||||
|
return unescaped;
|
||||||
|
}
|
||||||
|
public class EscapeMapping
|
||||||
|
{
|
||||||
|
public string Replacement { get; }
|
||||||
|
public string Token { get; }
|
||||||
|
|
||||||
|
public EscapeMapping(string token, string replacement)
|
||||||
|
{
|
||||||
|
ArgUtil.NotNullOrEmpty(token, nameof(token));
|
||||||
|
ArgUtil.NotNullOrEmpty(replacement, nameof(replacement));
|
||||||
|
Token = token;
|
||||||
|
Replacement = replacement;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -139,7 +139,7 @@ namespace GitHub.Runner.Common.Tests.Worker
|
|||||||
message = "::do-something k1=;=%252C=%250D=%250A=]=%253A,::;-%250D-%250A-]-:-,";
|
message = "::do-something k1=;=%252C=%250D=%250A=]=%253A,::;-%250D-%250A-]-:-,";
|
||||||
test = new ActionCommand("do-something")
|
test = new ActionCommand("do-something")
|
||||||
{
|
{
|
||||||
Data = ";-%0D-%0A-]-:-,",
|
Data = ";-%250D-%250A-]-:-,",
|
||||||
};
|
};
|
||||||
test.Properties.Add("k1", ";=%2C=%0D=%0A=]=%3A");
|
test.Properties.Add("k1", ";=%2C=%0D=%0A=]=%3A");
|
||||||
Assert.True(ActionCommand.TryParseV2(message, commands, out verify));
|
Assert.True(ActionCommand.TryParseV2(message, commands, out verify));
|
||||||
|
|||||||
@@ -443,6 +443,21 @@ namespace GitHub.Runner.Common.Tests.Worker
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
[Trait("Level", "L0")]
|
||||||
|
[Trait("Category", "Worker")]
|
||||||
|
public void AddMaskWithPercentEncodedString()
|
||||||
|
{
|
||||||
|
using (TestHostContext hc = CreateTestContext())
|
||||||
|
{
|
||||||
|
// Act
|
||||||
|
_commandManager.TryProcessCommand(_ec.Object, $"::add-mask::%252F%2F", null);
|
||||||
|
|
||||||
|
// Assert
|
||||||
|
Assert.Equal("***", hc.SecretMasker.MaskSecrets("%252F%2F"));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private TestHostContext CreateTestContext([CallerMemberName] string testName = "")
|
private TestHostContext CreateTestContext([CallerMemberName] string testName = "")
|
||||||
{
|
{
|
||||||
var hostContext = new TestHostContext(this, testName);
|
var hostContext = new TestHostContext(this, testName);
|
||||||
|
|||||||
Reference in New Issue
Block a user