microsoft/ailab · error · DirectoryNotFoundException
Container does not exist
Error message
Container {folderId} does not exist What it means
GetPredictionAsync reads a previously saved prediction (groups.json, original.png, etc.) from an Azure Blob container named after the folderId. It first checks whether the container exists and throws DirectoryNotFoundException('Container {folderId} does not exist') when it does not, since results for an unknown folder id cannot be fetched.
Solutions
- Verify the folderId corresponds to an existing container in the storage account (check with Azure Storage Explorer or az storage container list)
- Re-run the image analysis to generate results before calling GetPredictionAsync
- Confirm the service is pointed at the same storage account/connection string that saved the results
- Check container cleanup/lifecycle policies that may have deleted old prediction containers
- Validate the folderId from the request (no truncation/typos) before calling
Example fix
// before
var detail = await service.GetPredictionAsync(id);
// after
var container = cloudBlobClient.GetContainerReference(id);
if (!await container.ExistsAsync()) {
throw new ApplicationException($"Prediction {id} not found or expired; run the analysis again");
}
var detail = await service.GetPredictionAsync(id); Defensive patterns
Strategy: try-catch
Validate before calling
var container = cloudBlobClient.GetContainerReference(folderId);
if (!await container.ExistsAsync())
throw new ApplicationException($"Prediction {folderId} not found or expired"); Try / catch
try
{
var detail = await service.GetPredictionAsync(folderId);
}
catch (DirectoryNotFoundException ex)
{
logger.LogWarning(ex, "Prediction container missing for {FolderId}", folderId);
return NotFound($"Prediction {folderId} not found or expired; re-run the analysis.");
} Prevention
- Map DirectoryNotFoundException to HTTP 404/410 in the API layer
- Re-check folder ids from URLs before lookup
- Account for storage lifecycle cleanup when retaining results
- Ensure the same storage account is used for save and read paths
When it happens
Trigger: Calling GetPredictionAsync(folderId) with a folderId for which no blob container was ever created — e.g. a stale id, a typo, or querying before the image-processing Run completed and saved the results.
Common situations: Sharing a prediction URL whose blob container was deleted or expired (storage lifecycle/cleanup rules); typos in the folder id taken from a URL; hitting the API before the Sketch2Code run finished writing results; using a different storage account than the one that stored the results.
Related errors
- container does not exist
- blobClient is null
- Invalid image dimensions
- A subscription key is required
- BotFrameworkOptions must be configured prior to setting up…
AI-assisted analysis of microsoft/ailab@89fe2fc620 (2026-09-13).
Data as JSON: /api/errors/b97001f7314827a3.
Report an issue: GitHub.
Appendix: source
Thrown at Sketch2Code/Sketch2Code.Core/Services/ObjectDetectionAppService.cs:268
var permission = new BlobContainerPermissions();
permission.PublicAccess = BlobContainerPublicAccessType.Blob;
await theContainer.SetPermissionsAsync(permission);
if (relativePath != rootContainerPath)
{
fileName = Path.Combine(relativePath, fileName);
}
var blob = theContainer.GetBlockBlobReference(fileName);
await blob.UploadTextAsync(html);
}
public async Task<PredictionDetail> GetPredictionAsync(string folderId)
{
if (String.IsNullOrWhiteSpace(folderId))
throw new ArgumentNullException("folderId");
var blobContainer = _cloudBlobClient.GetContainerReference(folderId);
bool exists = await blobContainer.ExistsAsync();
if (!exists)
throw new DirectoryNotFoundException($"Container {folderId} does not exist");
var groupsBlob = blobContainer.GetBlockBlobReference("groups.json");
var detail = new PredictionDetail();
detail.OriginalImage = await this.GetFile(folderId, "original.png");
detail.PredictionImage = await this.GetFile(folderId, "predicted.png");
detail.PredictedObjects = await this.GetFile<IList<PredictedObject>>(folderId, "results.json");
var groupBox = await this.GetFile<GroupBox>(folderId, "groups.json");
detail.GroupBox = new List<GroupBox> { groupBox };
return detail;
}
public async Task<IList<CloudBlobContainer>> GetPredictionsAsync()
{
return await Task.Run(() => _cloudBlobClient.ListContainers().Where(l => l.Name != "azure-webjobs-hosts")
.OrderByDescending(c => c.Properties.LastModified).ToList());
}View on GitHub (pinned to 89fe2fc620)