feat: add security sink detection patterns for JavaScript/TypeScript
- Introduced `sink-detect.js` with various security sink detection patterns categorized by type (e.g., command injection, SQL injection, file operations). - Implemented functions to build a lookup map for fast sink detection and to match sink calls against known patterns. - Added `package-lock.json` for dependency management.
This commit is contained in:
@@ -3,7 +3,6 @@ using System.Security.Cryptography;
|
||||
using System.Text;
|
||||
using System.Text.Json;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using StellaOps.Scanner.Reachability.Slices;
|
||||
|
||||
namespace StellaOps.Scanner.Storage.Oci;
|
||||
|
||||
@@ -39,7 +38,11 @@ public sealed record SlicePullOptions
|
||||
public sealed record SlicePullResult
|
||||
{
|
||||
public required bool Success { get; init; }
|
||||
public ReachabilitySlice? Slice { get; init; }
|
||||
/// <summary>
|
||||
/// Raw slice data as JSON element (decoupled from ReachabilitySlice type).
|
||||
/// Consumer should deserialize to appropriate type.
|
||||
/// </summary>
|
||||
public JsonElement? SliceData { get; init; }
|
||||
public string? SliceDigest { get; init; }
|
||||
public byte[]? DsseEnvelope { get; init; }
|
||||
public string? Error { get; init; }
|
||||
@@ -96,7 +99,7 @@ public sealed class SlicePullService : IDisposable
|
||||
return new SlicePullResult
|
||||
{
|
||||
Success = true,
|
||||
Slice = cached!.Slice,
|
||||
SliceData = cached!.SliceData,
|
||||
SliceDigest = digest,
|
||||
DsseEnvelope = cached.DsseEnvelope,
|
||||
FromCache = true,
|
||||
@@ -185,9 +188,14 @@ public sealed class SlicePullService : IDisposable
|
||||
};
|
||||
}
|
||||
|
||||
// Parse slice
|
||||
var slice = JsonSerializer.Deserialize<ReachabilitySlice>(sliceBytes, JsonOptions);
|
||||
if (slice == null)
|
||||
// Parse slice as raw JSON element (decoupled from ReachabilitySlice type)
|
||||
JsonElement sliceData;
|
||||
try
|
||||
{
|
||||
using var doc = JsonDocument.Parse(sliceBytes);
|
||||
sliceData = doc.RootElement.Clone();
|
||||
}
|
||||
catch (JsonException)
|
||||
{
|
||||
return new SlicePullResult
|
||||
{
|
||||
@@ -216,7 +224,7 @@ public sealed class SlicePullService : IDisposable
|
||||
{
|
||||
AddToCache(cacheKey, new CachedSlice
|
||||
{
|
||||
Slice = slice,
|
||||
SliceData = sliceData,
|
||||
DsseEnvelope = dsseEnvelope,
|
||||
SignatureVerified = signatureVerified,
|
||||
ExpiresAt = DateTimeOffset.UtcNow.Add(_options.CacheTtl)
|
||||
@@ -230,7 +238,7 @@ public sealed class SlicePullService : IDisposable
|
||||
return new SlicePullResult
|
||||
{
|
||||
Success = true,
|
||||
Slice = slice,
|
||||
SliceData = sliceData,
|
||||
SliceDigest = digest,
|
||||
DsseEnvelope = dsseEnvelope,
|
||||
FromCache = false,
|
||||
@@ -346,7 +354,7 @@ public sealed class SlicePullService : IDisposable
|
||||
var index = await response.Content.ReadFromJsonAsync<OciReferrersIndex>(JsonOptions, cancellationToken)
|
||||
.ConfigureAwait(false);
|
||||
|
||||
return index?.Manifests ?? Array.Empty<OciReferrer>();
|
||||
return (IReadOnlyList<OciReferrer>?)index?.Manifests ?? Array.Empty<OciReferrer>();
|
||||
}
|
||||
catch (Exception ex) when (ex is HttpRequestException or TaskCanceledException)
|
||||
{
|
||||
@@ -430,7 +438,7 @@ public sealed class SlicePullService : IDisposable
|
||||
|
||||
private sealed record CachedSlice
|
||||
{
|
||||
public required ReachabilitySlice Slice { get; init; }
|
||||
public required JsonElement SliceData { get; init; }
|
||||
public byte[]? DsseEnvelope { get; init; }
|
||||
public bool SignatureVerified { get; init; }
|
||||
public required DateTimeOffset ExpiresAt { get; init; }
|
||||
|
||||
Reference in New Issue
Block a user