About the Jahia back-end layer
This section presents the various technologies and frameworks available in back-end layer of Jahia.
OSGi
Open Services Gateway initiative (OSGi) is a dynamic module system for Java. It is currently the most powerful and most mature dynamic module system available for Java applications. In OSGi, modules are called bundles. Bundles are specialized JARs that include extra MANIFEST.MF entries that declare the dependencies between modules, and versioning and package information made available to other modules. You can convert most existing JARs to an OSGi bundle with little work (automatic transformation tools are also available). In OSGi runtime, only packages that are exported are available and visible to other bundles, only if the using bundles also import them. This approach provides fine-grained control of accessible Java packages (as well as associated versions) between bundles.
In Jahia, modules are written as OSGi bundles. OSGi makes it easier for you to build full-fledged Jahia modules that can interact with each other. OSGi help you avoid complex interdependencies that can make maintenance and deployment complex. At the same time, it also leverages the already available OSGi bundles such as the Felix Web Console or the Felix Shell to quickly add functionality to a Jahia installation.
The following table illustrates how working modules behaves before the introduction of OSGi and after:
Before OSGi | With OSGi | |
---|---|---|
Class or library deployment | Requires web app restart | No restart needed |
Module is "exploded" on deployment | ||
Quick changes to source files don't require deployment | Only works in exploded directory, not module's source | |
External libraries are deployed into WEB-INF/lib and exposed to all other modules | ||
Undeployment cleans up everything immediately | ||
Modules depending on others cannot be deployed without their dependency | ||
Modules started/stopped after installation |
OSGi offers to module developers:
- True hot deployment
You can deploy and fully undeploy modules that contain complex dynamic content such as Java code or libraries. - Proper dependency management
The OSGi standard clearly defines the interdependencies between bundles, including bundle versioning, making it possible to use different versions of bundles in different parts of the application. - Isolation
OSGi modules can finely control what resources they expose and use to ensure that authorized access to resources inside modules does not occur. - Ready-made tools
With little effort, you can use existing OSGi tools and libraries in your projects. These tools may offer extensions or new functionality, such as extensions to the Felix Web Console and Felix Gogo shell.
Figure 1 - Integrated Apache Felix OSGi web console
OSGi is a powerful framework that can scale from embedded systems to large server-side applications, and does require a little understanding of the way the framework works to get started. Jahia provides tooling that makes the transition easy, including Maven plugins that convert existing modules to OSGi bundle projects, or even transforming on-the-fly simple legacy (WAR) Jahia modules to deploy directories onto Jahia.
Spring Web Flow
Spring Web Flow builds on Spring MVC and allows you to implement flows of a web application. A flow encapsulates a sequence of steps that guide a user through the execution of a business task. It spans multiple HTTP requests, has state, deals with transactional data, is reusable, and may be dynamic and long-running in nature.
Figure 2 - Example of a Spring Web Flow
The sweet spot for Spring Web Flow are stateful web applications with controlled navigation such as checking in for a flight, applying for a loan, shopping cart checkout, or even adding a confirmation step to a form. These scenarios have the following in common:
- There is a clear start and end point.
- The user follow a set of screens in a specific order.
- The changes are not finalized until the last step.
Once complete it shouldn't be possible to repeat a transaction accidentally.
Jahia integrates Spring Web Flow as a rendering technology available in modules to make it possible to build complex form handling views. For example, Spring Web Flow is used in Jahia in the Server Settings and Site Settings administration panels.
Module developers can leverage the power of Spring Webflow to build their own user interfaces that may require multiple step form inputs, and validation of form processing before performing an action.
Webflow are defined through an XML file that defines the application flow. Here is an example of a simple flow:
<?xml version="1.0" encoding="UTF-8"?>
<flow xmlns="http://www.springframework.org/schema/webflow"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/webflow
http://www.springframework.org/schema/webflow/spring-webflow-2.0.xsd">
<var name="adminPropertiesHandler" class="org.jahia.modules.serversettings.flow.AdminPropertiesHandler"/>
<on-start>
<evaluate expression="adminPropertiesHandler.init()" />
<evaluate expression="adminPropertiesHandler.adminProperties" result="flowScope.adminProperties"/>
</on-start>
<view-state id="adminPropertiesForm" model="adminProperties">
<on-render>
<evaluate expression="adminPropertiesHandler.userMembership" result="requestScope.userGroups"/>
</on-render>
<transition on="submit">
<evaluate expression="adminPropertiesHandler.save(messageContext)" />
</transition>
</view-state>
</flow>
As you can see in the example, the flow definition file makes it easy to define the different view states as well as the transitions between the views. If you're interested in learning more about Spring Webflow, check out the resources available here : https://docs.spring.io/spring-webflow/docs/2.3.x/reference/html/. We also presented the integration of Spring Webflow at JahiaOne 2014. You may find the video here : https://www.youtube.com/watch?v=TUESY3l5XIw&feature=youtu.be.
External data providers
Jahia External Data Providers enable you to integrate external systems as content providers in the Java Content Repository (JCR) managed by Jahia. All external data providers must at a minimum provide access to content ("read" external data provider) and optionally allow for searching, or writing and updating content. External Data Providers can provide enhanceable content, which means that the raw content they provide can be extended by Jahia content, for example, the ability to add comments to an object provided by an External Data Provider. To be accessible, external content is mapped as nodes inside Jahia so that the server can manipulate them as regular nodes (perform edit, copy, paste, or reference). The external provider module must also provide a CND definition file for each content object type that is mapped into the JCR back-end.
Here is an example CND definition file from the ModulesDataSource:
[jnt:editableFile] > jnt:file
- sourceCode (string) itemtype = codeEditor
[jnt:cssFile] > jnt:editableFile
[jnt:cssFolder] > jnt:folder
[jnt:javascriptFolder] > jnt:folder
[jnt:javascriptFile] > jnt:editableFile
External Data is made accessible by registering a provider declared in a Spring XML bean definition file that may specify some properties of the provider, such as the mount point, unique key, or data source.
<bean id="ExternalMappedDatabaseProvider" class="org.jahia.modules.external.ExternalContentStoreProvider" parent="AbstractJCRStoreProvider">
<property name="key" value="ExternalMappedDatabaseProvider"/>
<property name="mountPoint" value="/external-database-mapped"/>
<property name="identifierMappingService" ref="ExternalProviderIdentifierMappingService"/>
<property name="dataSource">
<bean class="org.jahia.modules.external.test.db.MappedDatabaseDataSource"/>
</property>
</bean>
A provider then accesses the underlying data source (implementing the ExternalDataSource and other optional Java interfaces if needed) to read, save or search data. An implementation of the ExternalDataSource interface must also list the node types that it is capable of handling. This can be done programmatically or inside a Spring configuration file. Here is an example of declarative nodeType support from the ModuleDataSource:
<bean id="ModulesDataSourcePrototype" class="org.jahia.modules.external.modules.ModulesDataSource"
scope="prototype">
<property name="supportedNodeTypes">
<set>
<value>jnt:cssFolder</value>
<value>jnt:cssFile</value>
<value>jnt:javascriptFolder</value>
<value>jnt:javascriptFile</value>
</set>
</property>
</bean>
These content are simple content (simple text files where the content of the file is mapped to a simple string (with a specific editor)) As you can see, External Data Providers offer an interesting way to fully integrate external data with the full power of Jahia's CMS features. For example, the eCommerce Factory product is mostly built using an External Data Provider that plugins into an eCommerce back-end.
Workflow
Jahia integrates the jBPM 6 workflow engine. The engine provides support for advanced workflow integrations through the definition of workflows, using the standardized Business Process Model and Notation (BPMN) 2.0 specification. Jahia's UI is integrated with the workflow screens making the experience seamless for end-users who never have to leave the UI to perform workflow operations (unless integrators wish to, of course). It is also compatible with any jBPM compatible GUI workflow definition tools, such as the web-based JBPM Designer or the Eclipse plugin. Note that these additional components must be installed and deployed by the integrator as they are not part of the Jahia core.
JBoss Drools and event listeners
Often, as content is modified, integrators need to perform a specific action when an event occurs. In previous versions of Jahia, you could write event listeners in Java classes or in JSP files, or even Groovy scripts. Starting with version 6.5, it was replaced with a much more powerful and easier to use rule system based on JBoss Drools. An example of such a rule is given below:
rule "Image update"
salience 25
#Rebuild thumbnail for an updated image and update height/width
when
A file content has been modified
- the mimetype matches image/.*
then
Create an image "thumbnail" of size 150
Create an image "thumbnail2" of size 350
Set the property j:width of the node with the width of the image
Set the property j:height of the node with the height of the image
Log "Image updated " + node.getPath()
end
As you can see rules are similar to the English language formulation and this makes it easy for integrators to use and read. The vocabulary of conditions makes it easy to respond to any event with any action.
File repository
Jahia uses the Java Content Repository (JCR) as Jahia's standard file repository and has built services on top of it. Actually, the integration of Jackrabbit is not a strong dependency, as Jahia uses the standard JCR API to offer access to multiple repositories. On top of file repository services, different interfaces expose content through various interfaces such as WebDAV, template file browsing and Jahia's AJAX UI.
On the other side of the repository, integration with a rules engine is used, among other things, for image thumbnail generation and metadata extraction. This rule engine is also pluggable and can be extended by integrators to perform other specific logic upon repository events.
Searching and indexing
Jahia comes built-in with strong support for searching and indexing, and does so by combining multiple frameworks to offer the following features:
- Full-text searches (Apache Lucene)
- Multi query languages support (Apache Jackrabbit)
- Facets (Apache Solr)
- "Did you mean" (Apache Solr)
- Open search
- Connectors to other search repositories such as Alfresco via EntropySoft connectors (available in the Jahia Unified Content Hub extension)
- Augmented search (optional module that provides functionality to index and search contents of the website using Elasticsearch)
To support these features, Jahia provides three technologies: full-text search tag libraries, query languages and Elasticsearch full-page search.
Full text queries using search tag libraries
Full-text query is made available through a set of tags that focus on searching using basic text matching with content object properties or file contents. This produces results as hits that contain information such as the target object that matched the result, an extract of the matching content and the matching score. It also supports search options defined by the JSR-283 standard such as optional words, mandatory or excluded words, search by sentence or word, and more.
Here is an overview of the features available when using full text queries:
- Search on all content within a site.
- Search on multiple sites on the server.
- Search the contents of files in the content repository.
- Search the contents of files in external repository (only with the Jahia United Content Hub extension).
- Highlight searched terms in the results page.
- Order by matching score.
- Exclusion of matching property (through content definition parameters).
- Limit results to improve performance.
Full text queries are a great way to offer an easy to use yet powerful search feature on a Jahia installation, but not for targeted queries, such as retrieving a list of the last 10 news entries or similar queries. This is where the query languages become interesting.
Query languages
The query language feature is a native functionality of a JCR-compliant implementation such as Apache Jackrabbit. It offers different query languages that are functionally equivalent, but differ in implementation and usage scenarios. It allows for complex condition matching and result ordering, as well as in some cases joins on multiple content object types. The result of the query is a list of matching nodes, ordered by the specified properties.
Here is an overview of the features offered by this type of querying:
- Search by content type (news and article)
- Complex conditions based on properties, or even in the case of SQL-2 or Query Object Model, joins.
- Integration with faceted search
- Integration with front-end HTML caching
The following query languages are available:
- SQL- 2
Similar to the standard SQL database language so easy to use for developers. The queries are parsed and transformed into Java Query Object Model queries and then executed as such. As this is part of JCR v2, it is relatively new and therefore there are some issues with its implementation, notably on join performance. For most simple queries it will do fine, but for more complex ones it is recommended to use XPath until this language implementation matures. - JQOM (Java Query Object Model)
A Java object representation of a JCR v2 query. You can build these using Jahia's query tag libraries, or to build them directly from Java code. SQL-2 and JQOM queries are quite similar, except that JQOM avoids the parsing stage and are a bit faster. In practice, it is quite seldom that JQOM is used, but it might be interesting in some cases. - XPath
Although it has been marked as deprecated in JCR v2, it is still available in Apache Jackrabbit and is by far the most optimized query language. It is not as easy to use as SQL-2, but is useful for building very fast queries. It is often worth the extra effort of designing the query. There are some tricks to know how to search for multi-language content, as it is not handled transparently, in the case of the other two implementations. Jahia uses it internally for speed in the cases where SQL-2 performance is not fast enough.
Jahia also comes built-in with modules that use queries to provide their functionality. An example of this includes the "last news retrieval" feature in the news module. Also available is a generic "query" module that will ask for the query when added to a content page. This makes it easy for editors to be able to build custom queries at content creation time, without requiring any assistance from the integrators (of course this module should not be made available if this possibility is to be restricted).
Elasticsearch full-page search
The Augmented Search module lets you use the power of Elasticsearch to index and search the contents of your Jahia websites. The module acts as connector to an existing Elasticsearch environment, by sending index data and search queries, and retrieving search results.
This module improves the relevance of the search results (compared to the default JCR search) as it includes a full-page search as opposed to a content-based search. It connects to an Elasticsearch cluster in version 7.X using the elasticsearch-connector-7 module.
To read more about this feature, go to Augmented search FAQ's and Using the Augmented Search GraphQL API.
Authentication and authorization
One of Jahia's strengths is its authentication and authorization sub-system. It allows for modular yet precise controls of permissions on a wide-variety of objects or actions. Permissions may be very granular or as coarse as desired, which makes it a great tool for deployment in small to large enterprises.
Single sign-on
Jahia integrates with the following SSO frameworks:
- Central Authentication Service (CAS) SSO
- Java EE container authentication support
- Pluggable authentication pipeline that can be easily implemented to add support for more SSO solutions
The last framework is useful when integrating with non-standard SSO technologies or custom-built ones. One possible example would be the case of a mobile service provider that uses phone numbers as authentication logins. Interfacing with a custom database will integrate into Jahia's back-end, exposing user and group information directly to Jahia's UI and permissions.
While it is possible to integrate with Kerberos (the authentication valve is present in the distribution), this integration is not officially part of the tested and supported stack for Jahia.
Please get in touch with the company to know the usage conditions.
Once the user is properly identified, the authorization sub-system is composed of:
- Access control lists on content objects
- Roles the user may participate in
- Permissions on any user actions for a specific role
To be able to set access control lists, user and group services are provided, and are of course also pluggable. By default, Jahia includes its own user and group provider service, as well as a connector to LDAP repositories. You can also develop custom services to plugin to either a custom database or a remote service. Jahia can also store properties and user information for external users and groups inside its own services, making it possible to store personalization data in Jahia. Note that all these service implementations are available at the same time, so there is no need to replace one with the other.
Roles and permissions
Jahia supports full-fledged roles. Roles are a collection of permissions grouped under a logical name. For example, an "editor" role groups permissions for editing content and starting workflow processes. Jahia comes with default roles and a UI for modifying the default roles. Integrators can define their own roles and permissions and change the defaults. You can also add permissions in modules and automatically assign them to existing roles upon deployment.
You can assign roles to users and groups at any location in the content repository. For example, you may define an "editor" role to a specific group in a specific section of the website. Group members can act as that role only in that specific location in the content repository, and nowhere else. This makes it easy to delegate responsibilities for content editing, review, and overall content management. It is recommended that you reuse roles through sites and sections. A minimal set of roles is beneficial for both for site management and authorization performance, as HTML caching uses roles to determine whether content is viewable.
Import/export
You can use Jahia's import/export feature to migrate content in between Jahia sites or even installations. It uses the JSR-170 (or JCR) XML format as a basis for content export, along with other specific files such as file hierarchies for binary data export. All these different files are compressed in a ZIP file that may be used by the import sub-system. This makes it possible to export a complete Jahia installation, a set of sites, a single site or even a sub-section of a site using the same import/export technology. Using this feature, users can migrate content between sites, or even between sections of sites, or also use it to export content to non- Jahia systems or import from non- Jahia systems. The same system is also used for migrations from previous versions of Jahia to the newest available version.
Distant publication
Jahia can be deployed in multiple instances to cover scenarios where a Jahia instance is located inside a firewall, and a public instance is located inside a DMZ zone accessible from the public web. To publish data from the inside to the outside, you can use Jahia's distant publication feature (also known as remote publication) to automate the process of migrating data from an authoring server to a browsing one. Note that this is still compatible with user-generated content such as a deployed forum on the public instances, meaning that remote publication will not touch user generated content created on the public instance.
Portlets
Jahia includes an embedded portal server, which is based on the Apache Pluto reference implementation of the JCR Portlet API specification. The portal server offers support for integrators who need to embed portlets on content pages. Any portlet API compliant application can be integrated with Jahia in a few simple steps.