Red Hat

What’s New in WildFly Management Console

WildFly 13 comes with a management console (HAL) which has been rewritten from scratch. HAL still uses a similar technical stack (GWT) and user experience, but now fully adopts PatternFly.

More important we enhanced the existing features and added support for many new subsystems and attributes. The following sections show some highlights of the latest version. For more details about the new features see the release notes for HAL 3.0.0.Final.

Finder

The column based navigation (finder) has been greatly improved. You can now use the cursor keys for navigation inside and across columns. To open an application view press ↵ (enter), to go back press ⌫ (backspace). Items in one column are now ordered alphabetically by default. You can pin frequently used items to stay at the top. Most columns offer a filter which can be used to quickly find the items you’re looking for. Finally the previews have been enriched and provide detailed documentation or the main attributes of the selected item. If appropriate the previews contain action links for the most common tasks.

Finder
Figure 1. Finder

Applications

Applications provide a new breadcrumb at the top to quickly switch between items of the same kind. More complex applications can include a vertical navigation. Finally most applications can be easily opened in an external window and provide an expert mode which uses the generic model browser.

Applications
Figure 2. Applications

Deployments

Many new features have been added to the deployment section:

  • Use drag and drop to deploy artifacts

  • Content browser with preview for text and images

  • Create exploded deployments

  • CRUD support for exploded deployments:

    • Add empty files

    • Upload content

    • Modify content

    • Remove content

  • Download complete deployments or deployment content

Deployments
Figure 3. Deployments

Deployment Model
Figure 4. Deployment Model

Content Browser
Figure 5. Content Browser

Topology

The topology view has been reintroduced to the management console. It was removed in the last versions due to performance issues with large domains. But thanks to new management operations, we were able to add this useful tool again.

Topology
Figure 6. Topology

Runtime

The lifecycle operations for hosts, server groups and servers have been improved. New operations are available for hosts and disconnected hosts are now shown in the finder columns. For servers you can specify custom URLs which is extremely useful when running WildFly inside a docker container.

Runtime
Figure 7. Runtime

Monitor

The existing screens have been improved and many new subsystems have been added to the monitoring section. Some of the new and enhanced subsystems are:

  • Batch

  • EJB

  • IO

  • JAX-RS

  • Messaging

  • Web (Undertow)

Monitor Server
Figure 8. Monitor Server

EJB Subsystem
Figure 9. EJB Subsystem

JAX-RS Resources
Figure 10. JAX-RS Resources

Undertow Listener Statistics
Figure 11. Undertow Listener Statistics

Get Involved

If you want to learn more about HAL, head over to https://hal.github.io/. The new website contains both end user and technical documentation. Read about HAL’s architecture, building blocks and how you can build, run and debug the console. HAL is an open source project and we love to receive contributions from our community — you!

Management Model Referential Integrity and Suggestions

A significant improvement in WildFly 11 is much better support for referential integrity when one resource in your configuration refers to another resource. Going beyond just checking that your references are correct, the server provides reference information that our CLI and the HAL web console are able to use to suggest valid values to you as you set up your configuration.

Configuration references

When you are configuring a WildFly server, a common thing you need to do is configure attributes whose value refers to the name of some other resource. A common example of this is a resource that includes a socket-binding attribute:

[standalone@localhost:9999 /] /subsystem=undertow/server=default-server/ajp-listener=ajp:add(socket-binding=ajp)

When you do this, it’s because the services managed by the resource you are configuring need some capabilities provided by another resource. What you’re doing is configuring which one to use. But what kind of resource that socket-binding attribute refers to may not be obvious, and what the valid values are is also not obvious. And before the rollout of improved reference support, if you got it wrong the failure you’d see could be difficult to understand.

Here, using WildFly 9 with a config where the previously unused 'ajp' socket binding config had been removed, we try and add an AJP listener to the web container:

[standalone@localhost:9990 /] /subsystem=undertow/server=default-server/ajp-listener=ajp:add(socket-binding=ajp)
{
    "outcome" => "failed",
    "failure-description" => {"WFLYCTL0180: Services with missing/unavailable dependencies" => ["jboss.undertow.listener.ajp is missing [jboss.binding.ajp]"]},
    "rolled-back" => true
}

That error message says nothing about where to go to correct the mistake.

Worse, if you made that mistake when working with a server started in admin-only mode, that bad reference would not be detected when you entered it.

[standalone@localhost:9990 /] reload --admin-only=true
[standalone@localhost:9990 /] /subsystem=undertow/server=default-server/ajp-listener=ajp:add(socket-binding=ajp)
{"outcome" => "success"}

The configuration would be updated and the problem would only be detected when the server was reloaded or restarted not in admin-only mode. The server would boot but would not function correctly.

Referential Integrity Checks and Reference Suggestions

Starting in WildFly 10 and greatly expanded in WildFly 11, we’ve added reference description metadata to our resources and attributes, and we use that to proactively ensure that management operations that violate referential integrity fail immediately.

The same incorrect operation shown above will now fail immediately, with a message that gives a hint as to where you can configure the missing resource:

[standalone@embedded /] /subsystem=undertow/server=default-server/ajp-listener=ajp:add(socket-binding=ajp)
{
    "outcome" => "failed",
    "failure-description" => "WFLYCTL0369: Required capabilities are not available:
    org.wildfly.network.socket-binding.ajp; Possible registration points for this capability:
		/socket-binding-group=*/socket-binding=*",
    "rolled-back" => true
}

The same failure will happen if the server is running in admin-only mode (with some exceptions; see "Referential Integrity Checks in an admin-only Process" below.)

If you think the resource you need already exists, but you’re not sure of its name, you can use CLI tab completion to get a list of suggestions:

[standalone@embedded /] /subsystem=undertow/server=default-server/ajp-listener=ajp:add(socket-binding=
http  https  management-http  management-https  txn-recovery-environment  txn-status-manager
[standalone@embedded /] /subsystem=undertow/server=default-server/ajp-listener=ajp:add(socket-binding=

Once the needed socket binding resource is added, it is available in the tab completion results.

[standalone@embedded /] /socket-binding-group=standard-sockets/socket-binding=ajp:add(port=8009)
{"outcome" => "success"}
[standalone@embedded /] /subsystem=undertow/server=default-server/ajp-listener=ajp:add(socket-binding=
ajp                       https                     management-https          txn-status-manager
http                      management-http           txn-recovery-environment
[standalone@embedded /] /subsystem=undertow/server=default-server/ajp-listener=ajp:add(socket-binding=ajp)
{"outcome" => "success"}

The HAL console will also suggest valid values by means of a pull-down:

choose socket binding

If you try and remove a resource whose capabilities are depended upon by other resources, that will also result in a failed operation:

[standalone@embedded /] /socket-binding-group=standard-sockets/socket-binding=ajp:remove
{
    "outcome" => "failed",
    "failure-description" => "WFLYCTL0367: Cannot remove capability 'org.wildfly.network.socket-binding.ajp' as it is required by other capabilities:
capability 'org.wildfly.undertow.listener.ajp' requires it for attribute 'socket-binding' at address '/subsystem=undertow/server=default-server/ajp-listener=ajp'",
    "rolled-back" => true
}

Referential Integrity Checks in an admin-only Process

If your xml configuration file contains invalid references and you start the server normally, the server will fail to boot and the log will have an error message describing the problem. However, if you start the server with the --admin-only flag, the server boot will not fail. This is because starting in admin-only and manipulating the configuration via the CLI is the recommended way of correcting your configuration. If we didn’t allow the server to boot, the user would have no alternative to manually editing the xml.

When the server is started in this state, no operation will be rejected due to an invalid reference until all referential integrity problems have been corrected. Once the configuration reaches a state where there are no integrity issues, thereafter any changes that break integrity will be rejected. If a server is started in admin-only and has no integrity problems at boot, any changes that break integrity will be rejected. So, leniency in integrity checks is only enabled when the server’s configuration at boot has problems.

Further Work

The referential integrity functionality discussed here first began to appear in WildFly 10, but it’s use was greatly expanded in WildFly 11, and the use of it to drive CLI tab completion and HAL pulldowns is new in 11. But still, we don’t yet have complete coverage of all capabilities subsystems provide, although the bulk of cases are covered, particularly those involve configuration attributes. Rollout of the use of capabilities will continue in future WildFly releases.

More Information

If you are interested in learning more about how the capabilities and requirements system works from the point of view of someone working on developing WildFly, please see the Working with WildFly Capabilities document in the WildFly documentation.

Using exploded deployments and CLI attachments

In WildFly there used to be two worlds : one for developers with exploded deployments using a scanner and one for production where artifacts (wars/ears/jars) were deployed.
Now those two worlds have collided and you can have exploded deployments without a scanner.
And since this is using the management API you get remote access to the content for "free" and of course it works in domain mode.
While this new feature is really usefull for tools developers (JBoss Developer Studio will use this in a tech preview, and NetBeans should use it also), YOU can also take advantage of it.

Creating exploded deployments

There are two ways to create an exploded deployment:

  • Create an empty deployment and add content to it.

  • Deploy an artifact and explode it.

Creating an exploded deployment from scratch

Let’s create a from_scratch.war deployment:

[standalone@localhost:9990 /] /deployment=from_scratch.war:add(content=[{empty=true}])
[standalone@localhost:9990 /] /deployment=from_scratch.war:add-content(content=[
          {input-stream-index=/home/ehsavoie/NetBeansProjects/SimpleWebapp/target/SimpleWebapp/index.html,target-path=index.html},
          {input-stream-index=/home/ehsavoie/NetBeansProjects/SimpleWebapp/target/SimpleWebapp/WEB-INF/web.xml, target-path=WEB-INF/web.xml},
          {input-stream-index=/home/ehsavoie/NetBeansProjects/SimpleWebapp/target/SimpleWebapp/WEB-INF/classes/org/wildfly/sample/simplewebapp/SimpleServlet.class, target-path=WEB-INF/classes/org/wildfly/sample/simplewebapp/SimpleServlet.class}])
[standalone@localhost:9990 /] /deployment=from_scratch.war:deploy

Here we have created an empty deployment called from_scratch.war to which we have added 3 files: - a simple HTML page index.html. - A class file for a servlet. - A web.xml descriptor.

Then we have enabled the deployment and thus could access the index.html and the servlet.
If you take a look at the $JBOSS_HOME/standalone/content/dc/9567f71b186466b21fff825d60f5fbc84ae6b1/content/ you will see the exploded war content.

Since this content is managed, don’t touch it directly by copying file to it manually, always use the Management API (through the jboss-cli or the web console).

Note that the add-content can be used to replace files in a deployment but if the deployment is running this might not show until you redeploy it.
You can also delete files in a deployment using remove-content but if the deployment is running this might not show until you redeploy it.

Exploding a deployment

Let’s install and explode a to_be_exploded.war deployment:

[standalone@localhost:9990 /] /deployment=to_be_exploded.war:add(content=[{input-stream-index=/home/ehsavoie/NetBeansProjects/SimpleWebapp/target/SimpleWebapp.war}],enabled=false)
[standalone@localhost:9990 /] /deployment=to_be_exploded.war:explode
[standalone@localhost:9990 /] /deployment=to_be_exploded.war:deploy

This can be achieved via the web console using the explode operation in the menu: image::exploded_deployments/explode.png[explode]

If you take a look at the $JBOSS_HOME/standalone/content//cf/9918bad9d875ffb20da8747b5dcd15bdab16e0/content/ you will see the exploded war content (it differs from the first example hash has the war file contains META-INF files).

Since this content is managed, don’t touch it directly by copying file to it manually, always use the Management API (through the jboss-cli or the web console).

Note also that you can only explode an unexploded deployment or an archive file if the deployment is not running (aka is disabled).

Reading content from a deployment

Now you can read content from a deployment, so you can directly see what’s in your deployment. This operation can be use to browse the content of a deployment and read or download its files (even from inside an archive file).

Using the JBoss CLI

Using the browse-content operation you can have the list of files in the deployment :

[standalone@localhost:9990 /] /deployment=to_be_exploded.war:browse-content
{
    "outcome" => "success",
    "result" => [
        {
            "path" => "META-INF/",
            "directory" => true
        },
        {
            "path" => "META-INF/MANIFEST.MF",
            "directory" => false,
            "file-size" => 134L
        },
        {
            "path" => "WEB-INF/",
            "directory" => true
        },
        {
            "path" => "WEB-INF/classes/",
            "directory" => true
        },
        {
            "path" => "WEB-INF/classes/org/",
            "directory" => true
        },
        {
            "path" => "WEB-INF/classes/org/wildfly/",
            "directory" => true
        },
        {
            "path" => "WEB-INF/classes/org/wildfly/sample/",
            "directory" => true
        },
        {
            "path" => "WEB-INF/classes/org/wildfly/sample/simplewebapp/",
            "directory" => true
        },
        {
            "path" => "WEB-INF/web.xml",
            "directory" => false,
            "file-size" => 916L
        },
        {
            "path" => "WEB-INF/classes/org/wildfly/sample/simplewebapp/SimpleServlet.class",
            "directory" => false,
            "file-size" => 2302L
        },
        {
            "path" => "index.html",
            "directory" => false,
            "file-size" => 234L
        },
        {
            "path" => "META-INF/maven/",
            "directory" => true
        },
        {
            "path" => "META-INF/maven/org.wildfly.sample/",
            "directory" => true
        },
        {
            "path" => "META-INF/maven/org.wildfly.sample/SimpleWebapp/",
            "directory" => true
        },
        {
            "path" => "META-INF/maven/org.wildfly.sample/SimpleWebapp/pom.xml",
            "directory" => false,
            "file-size" => 2992L
        },
        {
            "path" => "META-INF/maven/org.wildfly.sample/SimpleWebapp/pom.properties",
            "directory" => false,
            "file-size" => 125L
        }
    ]
}

You can reduce the output by filtering using the path, depth and archive parameters. For exemple

[standalone@localhost:9990 /] /deployment=to_be_exploded.war:browse-content(path=WEB-INF/, depth=1)
{
    "outcome" => "success",
    "result" => [
        {
            "path" => "web.xml",
            "directory" => false,
            "file-size" => 916L
        },
        {
            "path" => "classes/",
            "directory" => true
        }
    ]
}

So now we can display the content of the web.xml. Using the read-content operation is not sufficient enough as it will return an attachment:

[standalone@localhost:9990 /] /deployment=to_be_exploded.war:read-content(path=WEB-INF/web.xml)
{
    "outcome" => "success",
    "result" => {"uuid" => "c778c51e-a507-4a71-a21f-d6af8b230db4"},
    "response-headers" => {"attached-streams" => [{
        "uuid" => "c778c51e-a507-4a71-a21f-d6af8b230db4",
        "mime-type" => "application/xml"
    }]}
}

So we need to combine this operation with the attachment operation like this :

[standalone@localhost:9990 /] attachment display --operation=/deployment=to_be_exploded.war:read-content(path=WEB-INF/web.xml)
ATTACHMENT 582a10e0-5159-4d2b-8d07-8d39af0df8c3:
<?xml version="1.0" encoding="UTF-8"?>

<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd"
    version="3.1">
    <session-config>
        <session-timeout>
            30
        </session-timeout>
    </session-config>
    <servlet id="SimpleServlet">
        <servlet-name>SimpleServlet</servlet-name>
        <display-name>SimpleServlet</display-name>
        <servlet-class>org.wildfly.sample.simplewebapp.SimpleServlet</servlet-class>
        <init-param>
            <param-name>message</param-name>
            <param-value>Hello World</param-value>
        </init-param>
    </servlet>
    <servlet-mapping>
        <servlet-name>SimpleServlet</servlet-name>
        <url-pattern>/SimpleServlet</url-pattern>
    </servlet-mapping>
</web-app>

And to save this content locally we can use:

[standalone@localhost:9990 /] attachment save --operation=/deployment=to_be_exploded.war:read-content(path=WEB-INF/web.xml) --file=/home/ehsavoie/tmp/web.xml
File saved to /home/ehsavoie/tmp/web.xml

Using the web console

Navigate to 'Deployments' and select the deployment you want to browse. Then open the context menu and choose Browse Content:

browse content op

This opens a new page with the contents of the deployment. For each file, there’s a link with the full path and size of the file. Click on the link to download the file:

content

Using HAL.NEXT

The next major version of the web console (HAL.next) is currently under active development and is available as technical preview https://github.com/hal/hal.next. Follow the instruction in https://github.com/hal/hal.next#running to get started. Besides general improvements like better navigation and a revisited look and feel, HAL.next comes with many improvements for dealing with deployments:

  • Add Deployments using drag & drop.

  • New content browser using a tree view and an editor with syntax highlighting.

  • Download complete deployments or single files of a deployment.

Select deployments and just click on View to display its content:

explode next

This opens a new page which allows for a really nice way to browse and read content from a deployment:

content next

References

For the official documentation regarding deployments: Official Documentation
The example basic webapp used in this article is available here

back to top