Interface MetadataContext


public interface MetadataContext
The MetadataContext stores information about a long-running business processes that is independent of specific APIs or business rules of a single service. A MetaContext is built from the metadata fields of input APIs like HTTP or Kafka message headers. It is added automatically to output APIs when using platform clients from the JerseyClientBundle or the KafkaMessageProducer.

Services that claim to support MetadataContext must take care that it is also kept and reloaded when the business process is interrupted and proceeded later. An interrupted business process in these terms is for example asynchronous processing in a new Thread or finishing the current step of the process by saving the current state to a database.

The metadata fields (e.g. header names) that are put into the MetadataContext must be configured by environment variable or system property "METADATA_FIELDS" as comma separated list of header names, e.g. business-process-id,tenant-id. Header names are treated case-insensitive.

Metadata supports to have multiple values per key. Commas (@code ,) are not allowed in values to support composition as described in RFC 9110 5.2.

Technically, the MetadataContext is implemented as static ThreadLocal. When code is executed in a new Thread, the context must be transferred. Helper methods are available for Runnable and Callable

  • Field Details

    • METADATA_FIELDS_ENVIRONMENT_VARIABLE

      static final String METADATA_FIELDS_ENVIRONMENT_VARIABLE
      The name of the property or environment variable that defines which fields (e.g. of HTTP request headers or Kafka message headers are) included in the MetadataContext. The value must be a comma separated list of field names.

      Example: METADATA_FIELDS=tenant-id,processes

      See Also:
  • Method Details

    • metadataFields

      static Set<String> metadataFields()
      Returns:
      The fields that should be included in the MetadataContext, derived from the property or environment variable "METADATA_FIELDS".
    • current

      static MetadataContext current()
      Returns:
      the immutable metadata context of the current Thread, never null.
    • detachedCurrent

      static DetachedMetadataContext detachedCurrent()
      Returns:
      the current metadata context, never null. Changes in the returned instance will not affect the MetadataContext of the current Thread.
    • createContext

      static void createContext(DetachedMetadataContext metadataContext)
      Creates a new MetadataContext for the current Thread. Any existing MetadataContext in the current Thread will be replaced.
      Parameters:
      metadataContext - the new MetadataContext, e.g. derived from a DetachedMetadataContext.
    • createCloseableContext

      static MetadataContextCloseable createCloseableContext(DetachedMetadataContext metadataContext)
      Creates a new current context that is alive until the returned Closeable is closed. On closing, the previous context will be restored.

      Example usage:

         
           var myContext = // create a context from something
           try (var ignored = MetadataContext.createCloseableContext(myContext)) {
             // do something
           }
         
       
      Parameters:
      metadataContext - the context to be set until the returned closable is closed
      Returns:
      a closeable that will restore the previous context when closed
    • mergeContext

      static void mergeContext(DetachedMetadataContext newContextData, MetadataContextMergeStrategy mergeStrategy)
      Merges the given new metadata context data into the current() metadata context.
      Parameters:
      newContextData - the context data that should be merged into the current context
      mergeStrategy - defines the preference when metadata for a specific key exists in both contexts
      Throws:
      NullPointerException - if mergeStrategy is null
    • transferMetadataContext

      static Runnable transferMetadataContext(Runnable runnable)
      Transfers the current metadata context to the runnable when executed in a new thread.
      Parameters:
      runnable - The runnable to wrap with the current metadata context.
      Returns:
      The original runnable wrapped with code to transfer the metadata context when executed in a new thread.
    • transferMetadataContext

      static <V> Callable<V> transferMetadataContext(Callable<V> callable)
      Transfers the current metadata context to the callable when executed in a new thread.
      Parameters:
      callable - The runnable to wrap with the current metadata context.
      Returns:
      The original callable wrapped with code to transfer the metadata context when executed in a new thread.
    • keyFromConfiguration

      static String keyFromConfiguration(String environmentOrPropertyName) throws KeyConfigurationMissingException
      Derives the metadata key from the service specific configured environment.

      This is the preferred approach to determine the key when adding information to the metadata context.

      Parameters:
      environmentOrPropertyName - environmentOrPropertyName the name of a system property or environment variable that defines the actual key for a specific need of the service.
      Returns:
      the metadata key that is used for the metadata context
      Throws:
      KeyConfigurationMissingException - if the given environmentOrPropertyName does * not resolve to a metadata context key
    • keys

      Set<String> keys()
      Returns:
      all available keys in the metadata context.
    • valuesByKey

      List<String> valuesByKey(String key)
      valuesByKeyFromEnvironment(String) should be preferred to be independent of different environments.
      Parameters:
      key - a key in the metadata context
      Returns:
      the values stored in the metadata context by this key
    • valuesByKeyFromEnvironment

      default List<String> valuesByKeyFromEnvironment(String environmentOrPropertyName) throws KeyConfigurationMissingException
      reads the values of the metadata context from a key that is configurable by system properties or environment variables. This is the preferred approach to get information from the metadata context for a specific need.

      The environmentOrPropertyName should refer to the business use of the context values in a specific service. The actual key is dependent on the environment where the service is used. Other services may need the same key in a different context and operators may have their own assumptions about the naming.

      Parameters:
      environmentOrPropertyName - the name of a system property or environment variable that defines the actual key for a specific need of the service.
      Returns:
      the values stored in the metadata context by this key
      Throws:
      KeyConfigurationMissingException - if the given environmentOrPropertyName does not resolve to a metadata context key
    • isEffectivelyEmpty

      default boolean isEffectivelyEmpty()
      Returns:
      true, if no metadata keys() are defined or no valuesByKey(String) contain data, false if any valuesByKey(String) is not empty