close

Filter

loading table of contents...

Headless Server Developer Manual / Version 2307

Table Of Contents

4.8 Adapter

An Adapter can be used to enhance domain model objects with

  • Business logic from blueprint-base
  • Aggregation, Recomposition
  • Fallbacks

An Adapter is defined as Spring Bean and can be accessed from the GraphQL schema.

There are several predefined Adapters in the Headless Server, that can be accessed in the GraphQL schema.

For example, to access the settings of a content object, the SettingsAdapter can be used.

The StructAdapter provides access to values in structs. The Adapter expects a name of the struct which is to be accessed and a list specifying the path including the property to be found. This list shouldn't contain the name of the struct. Additionally, it is possible to provide a default value which is used in case the struct value wasn't found.

      type CMSettingsImpl implements CMSettings ... {
  settings(paths: [[String]]): JSON @fetch(from: "#paths == null ? #this.settings : @structAdapter.to(#root).getWrappedInStruct('settings',#paths, null)")
}

    

Example 4.3. Retrieve a value from a struct with the StructAdapter


The SettingsAdapter provides functionality to retrieve settings via the SettingsService from blueprint-base packages. By doing so, it can find local and linked settings on content objects. The SettingsAdapter covers a specific case of values in a Struct. Inheritance of settings is not supported at the moment.

Although the schema demands a nested list structure as an argument, the underlying GraphQL framework accepts an incomplete list structure, even a single string. Graphql-Java enhances the missing lists automatically, which might lead to an unwanted or unexpected behaviour. Therefore it is recommended, to always specify an unambiguous, full list structure as demanded by the schema. This is true for the usages of the SettingsAdapter in the schema as well as for the StructAdapter, whenever a setting or a struct is retrieved by its path.

      
// a single string is interpreted as a single path, as expected.
settings(paths: "commerce")

// same behaviour as above
settings(paths: ["commerce"])
settings(paths: [["commerce"]])

// two elements list: EACH entry is handled as an individual path! (potentially unexpected behaviour)
settings(paths: ["commerce","endpoint"])

// recommended: fully qualified list structure specifying two settings paths
settings(paths: [["commerce","endpoint"],["commerce","locale"]])

    

Example 4.4. Different ways to pass the paths parameter to the settings field from the GraphQL perspective


      
@Bean
public SettingsAdapterFactory settingsAdapter(@Qualifier("settingsService") SettingsService settingsService) {
  return new SettingsAdapterFactory(settingsService);
}

    

Example 4.5. Define SettingsAdapter as bean


      
type CMTeasableImpl implements CMTeasable ... {
  customSetting: String @fetch(from:
    "{!@settingsAdapter.to(#root).get({'customSetting'},'')}")
}

    

Example 4.6. Retrieve settings with the SettingsAdapter


There are several Adapters available, for example:

structAdapter

Retrieve values from a Struct at a content object.

responsiveMediaAdapter

Retrieve the crops for a Picture.

mediaLinkListAdapter

Retrieve the media for a content object, for example, picture(s), video(s).

pageGridAdapter

Retrieve the pagegrid.

imageMapAdapter

Retrieve image maps.

navigationAdapter

Retrieve the navigation context.

DataFetchingEnvironment Support

Similar like a DataFetcher, adapters can access the GraphQL DataFetchingEnvironment. The access is possible in two flavours. First, the DataFetchingEnvironment is available in the SpEL evaluation context under the name #dataFetchingEnvironment.

Second, if an adapter extends the class DataFetchingEnvironmentAware, the current DataFetchingEnvironment is automatically injected after(!) the instantiation of the adapter via its factory. The DataFetchingEnvironment can be accessed via a getter. Additionally, DataFetchingEnvironmentAware offers a convenience method to read any variable from the GraphQL context, e.g. the preview date.

Due to the fact, that the DataFetchingEnvironment is injected after the adapters instantiation, the factory method itself cannot access the DataFetchingEnvironment via the getter. If access is necessary during instantiation, the first approach via an explicit SpEL expression is inevitable.

# Example: Passing the DataFetchingEnvironment explicitly via SpEL.

type CMNavigationImpl implements CMNavigation {
  ...
  grid: PageGrid @fetch(from: "@pageGridAdapter.to(#root,'placement', #dataFetchingEnvironment)")
  ...
}


# Example: Transparent access to the DataFetchingEnvironment.
# - 'byPathAdapter' extends DataFetchingEnvironmentAware.
# - DataFetchingEnvironment is injected after the factory method 'to()'!
# - 'getPageByPath(#path)' accesses the DataFetchingEnvironment internally.

type ContentRoot {
  ...
  pageByPath(path: String!): CMChannel @fetch(from: "@byPathAdapter.to().getPageByPath(#path)")
  ...
}

Example 4.7. Accessing the DataFetchingEnvironment.


Automatic conversion of GraphQL input types to Java Objects

In most cases, scalar types like strings or integers are sufficient as call parameters for the execution method of an adapter. It is however also possible to use GraphQL input types as call parameters as well. Since GraphQL does not offer an out-of-the-box conversion of GraphQL input types to Java Objects, the given value of an input type will be a deserialized composition of collection classes, similar to a deserialized JSON string.

A Spring Converter offers the possibility to convert the values of an input type into a typed Java object, which in turn can the be used as input parameter of an adapter. If a suitable converter exists, the underlying Spring Expression Language will invoke it implicitly. A Converter simply has to be created as a regular SpringBean. It will then be automatically added to the EvaluationContext of the Spring Expression Language. See also Section 4.7, “Conversion Service”.

Search Results

Table Of Contents
warning

Your Internet Explorer is no longer supported.

Please use Mozilla Firefox, Google Chrome, or Microsoft Edge.