Skip to main content

Overview

Ng is the background-job executable (ng.exe) for the NuGet Gallery infrastructure. It is a single .NET 4.7.2 console application that hosts a named-job dispatcher: at startup the caller passes a job name as the first argument, and NgJobFactory instantiates and runs the matching NgJob subclass. The project has no REST API surface. Its purpose is to run long-lived, looping or one-shot background workers that keep derived NuGet infrastructure (catalog, flat container, registration hives, monitoring queues, icon CDN) in sync with the gallery database.
ng.exe is the legacy job host. Newer NuGet jobs use NuGet.Jobs-based infrastructure with JSON configuration. Ng predates that pattern and uses its own key-value CLI argument convention (-argName value).

Catalog Feeds

db2catalog reads the Gallery SQL database and writes package create / edit / delete events into the V3 catalog JSON feed stored in Azure Blob Storage.

Flat Container (DNX)

catalog2dnx reads the catalog and populates the flat-container blob hierarchy used by NuGet restore.

Icon Pipeline

catalog2icon extracts embedded package icons and external icon URLs from catalog leaves and copies them into a CDN-backed icon storage container.

Monitoring

catalog2monitoring, monitoring2monitoring, and monitoringprocessor queue packages for endpoint validation and process the results.

Key Files and Classes

Dependencies

NuGet Package References

Internal Project References

Notable Patterns and Implementation Details

Cursor-based resumability. Every looping job tracks its position in the catalog via a DurableCursor written to blob storage (cursor.json). On restart the job resumes from the last committed position rather than replaying the entire catalog.
Reinitialization interval. LoopingNgJob separates the loop interval (-interval, default 3s) from the reinitialization interval (-ReinitializeIntervalSec, default 3600s). Expensive operations like creating storage clients and resolving Key Vault secrets only happen once per hour.
Lightning job is Azure-only. LightningJob.Init hard-codes arguments[Arguments.StorageType] = "azure". Attempting to point it at file storage will fail at runtime. It also requires three separate storage containers (legacy, gzipped, SemVer 2.0.0) to be configured.
Db2CatalogJob deduplicates deletes per commit. When multiple audit entries for the same package ID+version appear within one batch, SegmentPackageDeletes splits them into separate catalog commits. A Thread.Sleep(1s) is injected between segments to guarantee distinct commit timestamps.
KeyVault is optional. If -vaultName is not supplied, CommandHelpers substitutes an EmptySecretReader. This makes local development against file storage straightforward without Azure KeyVault credentials.
Managed Identity vs. certificate auth. CommandHelpers.GetSecretInjector selects between ManagedIdentityCredential (when -useManagedIdentity true) and certificate-based KeyVaultReader automatically, allowing the same job binary to run in both MSI-enabled pods and environments authenticated via storage account keys.