abpframework/abp · error · ArgumentException
Unknown BLOB encryption key source: {source}!
Error message
Unknown BLOB encryption key source: {source}! What it means
BlobEncryptionKey's constructor validates that source is within the defined BlobEncryptionKeySource range (Container..Global). The source is persisted in the BLOB header, so an out-of-range value would make the BLOB permanently unreadable; the ctor rejects it with an ArgumentException.
Source
Thrown at framework/src/Volo.Abp.BlobStoring/Volo/Abp/BlobStoring/BlobEncryptionKey.cs:33
public BlobEncryptionKeySource Source { get; }
/// <summary>
/// The passphrase the encryption key of the BLOB is derived from.
/// </summary>
[NotNull]
public string PassPhrase { get; }
/// <summary>
/// Creates the resolved key; <paramref name="source"/> must be a defined
/// <see cref="BlobEncryptionKeySource"/> value and the passphrase non-empty.
/// </summary>
public BlobEncryptionKey(BlobEncryptionKeySource source, [NotNull] string passPhrase)
{
if (source < BlobEncryptionKeySource.Container || source > BlobEncryptionKeySource.Global)
{
// The source is stored in the BLOB header and validated while reading;
// an unknown value would make the BLOB permanently unreadable.
throw new ArgumentException($"Unknown BLOB encryption key source: {source}!", nameof(source));
}
Source = source;
PassPhrase = Check.NotNullOrWhiteSpace(passPhrase, nameof(passPhrase));
}
}
View on GitHub (pinned to 7ed43b1931)
Solutions
- Validate the enum with Enum.IsDefined before constructing BlobEncryptionKey.
- On decrypt, treat an unknown source as a version mismatch and surface a clear 'BLOB written by a newer version' error.
- Re-encrypt the BLOB with a known-valid source value.
- Do not cast raw ints to BlobEncryptionKeySource without range-checking.
Example fix
// before
var key = new BlobEncryptionKey((BlobEncryptionKeySource)rawHeaderByte, pass);
// after
if (!Enum.IsDefined(typeof(BlobEncryptionKeySource), rawHeaderByte))
throw new InvalidOperationException(
$"BLOB written by a newer/incompatible version (source={rawHeaderByte}).");
var key = new BlobEncryptionKey((BlobEncryptionKeySource)rawHeaderByte, pass); Defensive patterns
Strategy: validation
Validate before calling
// Validate the source byte before constructing a BlobEncryptionKey.
static BlobEncryptionKey BuildKey(int rawSource, string pass)
{
if (!Enum.IsDefined(typeof(BlobEncryptionKeySource), rawSource))
throw new InvalidDataException(
$"BLOB header references unknown key source {rawSource}; written by a newer/incompatible version.");
return new BlobEncryptionKey((BlobEncryptionKeySource)rawSource, pass);
} Type guard
public static bool IsDefinedSource(int raw) =>
Enum.IsDefined(typeof(BlobEncryptionKeySource), raw);
// usage before construct:
if (!IsDefinedSource(rawHeaderByte)) return Result.UnknownVersion; Try / catch
try
{
var key = new BlobEncryptionKey((BlobEncryptionKeySource)rawHeaderByte, pass);
}
catch (ArgumentException ex) when (ex.Message.Contains("Unknown BLOB encryption key source"))
{
logger.LogError(ex, "BLOB header is corrupt or from an incompatible version (source={Source}).", rawHeaderByte);
// Surface a version-mismatch error to the user; not retryable.
throw;
} Prevention
- Never cast raw ints to BlobEncryptionKeySource without Enum.IsDefined.
- Treat unknown source bytes as version mismatches and surface a clear error.
- Keep writer and reader codec versions aligned across deployments.
- Validate headers defensively when reading externally produced BLOBs.
When it happens
Trigger: Constructing BlobEncryptionKey with an undefined BlobEncryptionKeySource value — typically by casting an invalid integer to the enum, or deserializing a BLOB header whose source byte is outside the known range.
Common situations: A future ABP version writes a new source value that an older reader casts to an undefined enum; a corrupted/tampered header byte; manual/reflective code that casts arbitrary ints to BlobEncryptionKeySource.
Related errors
- Invalid background job name filter mode: {mode}
- Job names must be empty when the filter mode is None.
- Job names cannot be empty when the filter mode is Include or
- Container name contains invalid characters: {containerName}.
- Container name must be between {MinLength} and {MaxLength} c
AI-assisted analysis of abpframework/abp@7ed43b1931 (2026-08-13).
Data as JSON: /api/errors/d175e187507e3707.
Report an issue: GitHub.