# Flag Providers

The Umbraco management APIs for trees, collections, and items include a `flags` collection for each item. These indicate additional information for the item that can be presented to users.

The Umbraco backoffice uses this to provide additional overlay icons on tree, collection, and item presentations. This core behavior and extension point is described in the article on [backoffice signs](/umbraco-cms/18.latest/extend-your-project/backoffice-extensions/signs.md).

## Core Flag Providers

Umbraco ships with four flag providers that will provide indications of the following document or media states:

* **Is Protected** - indicates the document is not available for public access.
* **Has Pending Changes** - indicates that the document is published but has changes in draft waiting for publication
* **Has Schedule** - indicates that the document is scheduled for publishing in the future
* **Has Collection** - indicates that the document or media is based on a content type that is configured for display as a collection

For example, an item that is scheduled for publication would contain the following in the tree, collection or item API response:

```json
  "flags": [
    {
      "alias": "Umb.ScheduledForPublish"
    }
  ],
```

## Providing a Custom Flag Provider

If your package or project needs to present additional information for a tree, collection or item value, a custom flag provider can be created. This will be coupled with a presentation extension to determine how the information is interpreted for display as a [backoffice sign](/umbraco-cms/18.latest/extend-your-project/backoffice-extensions/signs.md).

To create a flag provider, implement the `IFlagProvider` interface. There are two methods to implement:

* `CanProvideFlags<TItem>` - returns `bool` indicating whether this provider can provide flags for the tree, collection or item view model.
* `PopulateFlagsAsync<TItem>(IEnumerable<TItem> itemViewModels)` - populates the `Flags` property for the provided collection of view models.

An illustrative implementation is as follows:

```csharp
using Umbraco.Cms.Core;
using Umbraco.Cms.Api.Management.Services.Flags;
using Umbraco.Cms.Api.Management.ViewModels;
using Umbraco.Cms.Api.Management.ViewModels.Document.Collection;
using Umbraco.Cms.Api.Management.ViewModels.Document.Item;
using Umbraco.Cms.Api.Management.ViewModels.Tree;

internal class MyDocumentFlagProvider : IFlagProvider
{
    private const string Alias = Constants.Conventions.Flags.Prefix + "MyDocumentFlag";

    // Indicate that this flag provider only provides flags for documents.
    public bool CanProvideFlags<TItem>()
        where TItem : IHasFlags =>
        typeof(TItem) == typeof(DocumentTreeItemResponseModel) ||
        typeof(TItem) == typeof(DocumentCollectionResponseModel) ||
        typeof(TItem) == typeof(DocumentItemResponseModel);

    public Task PopulateFlagsAsync<TItem>(IEnumerable<TItem> itemViewModels)
        where TItem : IHasFlags
    {
        foreach (TItem item in itemViewModels)
        {
            if (ShouldAddFlag(item))
            {
                item.AddFlag(Alias);
            }
        }

        return Task.CompletedTask;
    }

    private bool ShouldAddFlag<TItem>(TItem item) => true; // Provide custom logic here.
}
```

The flag provider needs to be registered with Umbraco in a composer or application startup with:

```csharp
  builder.FlagProviders()
    .Append<MyDocumentFlagProvider>();
```

For some flags, there may be sufficient information on the view models to map whether a flag should be created.

For an example of this, see the core flag provider `IsProtectedFlagProvider` whose [source code can be found here](https://github.com/umbraco/Umbraco-CMS/blob/main/src/Umbraco.Cms.Api.Management/Services/Flags/IsProtectedFlagProvider.cs).

More complex flags will require additional information, using the identifiers of the view models to retrieve the necessary data. It's important to avoid "N+1" issues. The aim should be to retrieve all the data needed to populate the flags for the whole collection in one step.

In core, the flag provider `HasScheduleFlagProvider` shows a good example of this. The [source code can be found here](https://github.com/umbraco/Umbraco-CMS/blob/main/src/Umbraco.Cms.Api.Management/Services/Flags/HasScheduleFlagProvider.cs).


---

# 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.umbraco.com/umbraco-cms/18.latest/extend-your-project/server-side-extensions/flag-providers.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.
