# Private versions

A **private version** is a sealed version whose fix is not a perfect drop-in replacement for the origin version. Most sealed packages preserve the origin version's behavior exactly: a private version is the exception, used when a vulnerability cannot be remediated without changing something the origin version's users may have been depending on.

The [Partial fixes & open vulnerabilities](/new-documentation/new-docs/partial-fixes.md) chapter is the canonical home for the case that produces private versions: a vulnerability that can only be removed by removing a feature, changing a default, or otherwise altering observable behavior. A private version is what Seal can offer when a customer is willing to accept the impact in exchange for the fix.

## What a private version is

A private version is built from the same origin version as a regular sealed version, with a closely related but distinct version-string suffix. Where a regular sealed version uses `-sp[N]` or `+sp[N]` (depending on the ecosystem), a private version uses `-sp[N]p[M]` or `+sp[N]p[M]`. `[N]` matches the public sealed iteration the private version is built on top of; `[M]` is a running count of private fixes within that iteration. So `ejs@2.7.4-sp1p1` is the first private version sitting on top of the public `ejs@2.7.4-sp1`.

When Seal releases a new public sealed version for a package that already has private versions, the private versions are rebuilt to keep up. A customer using `ejs@2.7.4-sp1p1` will be offered `ejs@2.7.4-sp2p1` once `ejs@2.7.4-sp2` ships, with the private fix re-applied on top of the newer public sealed iteration. Private versions do not fall behind public sealed versions.

In the Seal UI, where a private version is shown alongside other sealed versions, it also carries a **`-custom`** marker so you can tell the two apart visually.

## Why a private version makes sense

A private version's compatibility caveat is real, but the breaking change usually affects features most customers do not use. Removing support for a deprecated, insecure cryptographic algorithm only breaks code paths that still call that algorithm; flipping a permissive default to a strict one usually only affects deployments that depended on the old default. The customers most likely to adopt a private version are the ones who can confirm their code does not use the changing behavior at all.

Even when the changing feature is not in use, the vulnerability is often still worth fixing:

* The vulnerable code may be reachable through another call path, independent of the feature the private version changes.
* The vulnerable code may not be reachable at all, but compliance frameworks or a downstream customer's policy may require remediation regardless.

If the changing feature is not used, the private version delivers the fix at no behavioral cost. Compared to the alternative when there is no public sealed version for the CVE, which is usually upgrading to a major new release of the package or of the framework that bundles it, a private version is far cheaper: enabling it for a Seal Project takes the time of one conversation and one CLI run, rather than the weeks of testing and migration a major upgrade would need.

## When Seal builds a private version

Seal does not build a private version unless a customer asks for one. The trigger is always a customer request: a vulnerability that matters to the customer, that has no clean backport because the only fix involves a behavior change, and that the customer is willing to accept the impact of.

Examples:

* A package's only fix removes support for a deprecated, insecure cryptographic algorithm. Customers whose code does not use the algorithm can adopt the private version safely. Customers whose code does use it would silently break and have to migrate first.
* A package's only fix changes a default that was permissive to a stricter setting. Customers whose deployments rely on the permissive default would behave differently after the change.

In both cases, Seal could not ship the fix as a public sealed version: its compatibility contract would no longer hold for every customer of that package. Building it as a private version, only enabled for customers who have evaluated the impact, preserves the contract.

## Why usage is per Seal Project

Private versions are enabled per Seal Project, not tenant-wide and not platform-wide. Each Seal Project has its own list of allowed private versions; only versions on the list are served to that project's builds.

The reason is that the breaking-change impact depends on the customer's code in that specific project. A customer with two Seal Projects, one that uses the affected behavior and one that does not, may want the private version for the second project but not the first. Per-project enablement makes that a normal configuration choice rather than a global all-or-nothing.

## Requesting and enabling a private version

The flow for getting a private version into a Seal Project:

1. **Identify the package and version**. The vulnerability is open in the [drawer](/new-documentation/new-docs/vulnerability-detail.md), and the [Unfixable](/new-documentation/new-docs/package-states.md#unfixable) section of Package states is where Seal's analysis lands when no clean fix exists.
2. **Contact your Seal account team** to request a private version for that package and version. Describe which Seal Project you intend to enable it for.
3. **Review the breaking-change impact** with the account team. The conversation covers what behavior the private version changes, who would be affected, and how to test that the change is safe for your project.
4. **Acknowledge the impact** to the account team. Acknowledgement is what authorizes Seal to enable the private version for your specific Seal Project.
5. **Seal enables the private version** for the project. The next CLI run, or the next pull through the [Seal Artifact Server](/new-documentation/new-docs/artifact-server-discovery.md), can use it.

The first time a customer requests a private version that does not yet exist, Seal builds the version itself before enabling it. If the version already exists for the package (because another tenant has already requested it), Seal can enable it for your project on its own schedule.

## After a private version is enabled

A private version is a normal sealed version once enabled. You create a Sealing Rule for it the same way you do for a public sealed version, on the [Sealing rules tab](/new-documentation/new-docs/protection-page/sealing-rules-tab.md) or through the Sealing instructions tab inside the [drawer](/new-documentation/new-docs/vulnerability-detail.md#the-sealing-instructions-tab). The Vulnerable packages tab moves the row to Pending deploy and then to Sealed in the usual way; the row carries the same state semantics as any other sealed package.

Disabling a private version is the same out-of-band conversation with the account team: ask, the project's allow-list is updated, the next CLI run no longer pulls the private version.

## Related

* [Partial fixes & open vulnerabilities](/new-documentation/new-docs/partial-fixes.md): the broader framing of why some vulnerabilities can only ship as private versions.
* [Vulnerability detail](/new-documentation/new-docs/vulnerability-detail.md): where you see the open vulnerability that motivated the request.
* [Package states](/new-documentation/new-docs/package-states.md): the lifecycle a private-version-using package follows once enabled.


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://docs.sealsecurity.io/new-documentation/new-docs/private-versions.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
