Capturing an App Builder application with Roxy

Author: Dave Cassel  |  Category: Software Development

This post is an update to my earlier tutorial on how to use Roxy with MarkLogic‘s Application Builder. I finally wrapped up a feature that automates the process, so the procedure has changed. I’m working with:

  • MarkLogic 6.0-3.1 (6.0-2+ required)
  • Roxy 1.4 (see the version.txt file in the project’s base directory)

Motivation

Application Builder makes it easy to create search applications, but copying that application to other servers can be a pain. In my case, I often need to get an application onto a few laptops (each of the developers on a project), a dev server (used for integration testing) and a production server (used to actually show a demo to a prospect). Capturing the application’s REST API configuration and source code on the file system allow us to get it under version control, making it much easier to work in a team environment.

Assumptions

This tutorial assumes the following:

  • You have installed Ruby (needed for the Roxy deployer)
  • You have downloaded Roxy’s ml script and put it into your path (note: that link points to the latest & greatest on the dev branch)
  • You have installed MarkLogic 6.0-2+
  • You are using localhost for your MarkLogic instance (though you can capture from remote servers as well)
  • All commands are run from your project’s home directory (created by “ml new”) unless otherwise stated

Approach

In this tutorial, I’ll walk through using Roxy and App Builder on a project where that’s the plan from the beginning. (It’s a bit different if you have an existing database and you’ve already run App Builder. I’m leaving that scenario out because I’m intending better tool support.) Here’s the high-level plan:

  1. Create a Roxy project
  2. Set up the configuration
  3. Bootstrap
  4. Run App Builder
  5. Capture the code
  6. Cleanup

Create a Roxy Project

Roxy lets you create a new project using the ml new command:

$ ml new app-name

Using the command this way will create a Roxy MVC application, intended for projects built mostly from XQuery. As of Roxy 1.4 (currently on the dev branch), you can also choose to do a rest application (like what Application Builder produces — using the REST API with no MVC XQuery behind it) or a hybrid application (using the REST API and Roxy’s MVC structure). This approach to capturing App Builder code requires having a REST application (in the future, I could set it up to work with hybrid apps if people request that).

# from ~/git/, or wherever you like your projects to live:
$ ml new my-app --branch=dev --app-type=rest
$ cd my-app

This creates a Roxy application with the name “my-app”. That name will be used in naming app servers, databases, and other things set up by Roxy for this application. That’s also the name of the directory where the project lives (~/git/my-app, in my case).

The REST application type provides no source code, just the REST API set up, on the assumption that you’ll provide the source code. After running the command above, you’ll have a deploy directory, containing the configuration of your databases, forests, app servers, roles and users; a rest-api directory, where you can put the options that will control your REST API searches; and a src directory, which for a REST application will be empty.

Set up the Configuration

Our next step is to set up the configuration that we need. In particular, you’ll want to add range indexes and make other changes to the database settings. You can do this by editing deploy/ml-config.xml (there are comments in the file providing examples) or by using the index interview feature (“$ ml index” will ask you a set of questions and build element or attribute range indexes based on the answers). Having the range indexes in place will give Application Builder something to work with.

Other than the indexes, you might need to change the ports or password that Roxy will use. In deploy/build.properties, you’ll see the default values for app-port, xcc-port, user and password. Change them as needed to avoid conflict with existing applications and to match your admin username and password. (If you don’t want the password in your properties file, leave it blank (“password=”); Roxy will prompt you.

Bootstrap

Time put that configuration to work.

$ ml local bootstrap

After running bootstrap, you should have an HTTP app server, and XCC app server, a content database, a modules database, and an app-specific role and user. If you have some sample data to work with, create a {project-home}/data directory, put the data there, and run

$ ml local deploy content

We don’t have any code yet, so there’s no need to deploy modules.

At this stage, we have something worth preserving — the configuration. That makes it a good time to set up a local git repository. This is a good idea even if you’re just working by yourself on a small project.

$ git init
$ git add *
$ git commit -m "Initial commit"

Run Application Builder

We have a database with indexes and some content (assuming you loaded some sample documents). On to Application Builder. This tutorial doesn’t cover how to use Application Builder, but here are the relevant parts for our purposes:

  1. Point your browser to http://localhost:8000 and click Application Builder at the top.
  2. Click the New Application button
  3. Pick an application name different from the name you gave Roxy (“my-app” above; use “ab-my-app” or something)
  4. For the database, pick the content database built by Roxy (“my-app-content”)
  5. Go through the wizard
  6. At the Deploy stage, choose a port that does not conflict with the one Roxy is using

You now have two applications: a Roxy app with no source code and an Application Builder app. Both point to the same content database.

Capture the Code

App Build creates a MarkLogic REST API-based application consisting of HTML, JavaScript, CSS, images, and some configuration options for the REST API. The ml capture command retrieves these files from the modules database created by App Builder and puts them on the file system, in your project, in the directories where things belong. Here’s how to use it:

$ ml local capture --modules-db=ap-my-app-modules

Let’s break that down.

The local part specifies that the App Builder modules database is available on the local environment server. If you ran App Builder somewhere else, you can use a different environment to get there. For instance, if my dev environment points to van-dev2 and I’ve run App Builder there, I can use dev in this command instead of local.

The –modules-db parameter specifies the name of the modules database created by App Builder.

The command will create a temporary directory on your system (for instance, somewhere under /tmp/ on Linux), download the files, then copy them into the appropriate places in your project. For the source code, this would typically be under your project’s src/ directory, but if you’ve changed the xquery.dir property to point somewhere else, that’s where the source code will go. Likewise, the REST API configuration will be copied to the directory pointed to by your rest-options.dir directory, typically rest-api/config/.

Note that App Builder typically generates one transform (appidentitytransform) and one extension (extsuggest). When you create transforms and extensions in a Roxy application, they would typically go under rest-api/transform or rest-api/ext (see Working With the REST API for more information). The capture command currently leaves the App Builder-generated transform and extension under src. That’s okay; deploy modules knows what to do with them. Move along.

We can test that the capture was successful by deploying the code to our Roxy application server.

$ ml local deploy modules

If all went well, you should now be able to point your browser to your Roxy app-port and see the captured version of the app. It should be identical to the App Builder version.

This is another good time to capture what we have.

$ git add rest-api src
$ git commit -m "Added App Builder code and options"

Cleanup

This step is optional. You might want to re-run App Builder a couple time to tweak what you have, and the repeat the process of grabbing the code. If you decide you want another index, make the change in deploy/ml-config.xml and then bootstrap again — doing it this way (instead of through the Admin UI) keeps your configuration up to date.

When you are done with the App Builder version, you can remove that project.

  • On http://localhost:8000/appbuilder, you can delete the App Builder project
  • Using the Admin UI on http://localhost:8001, you can delete the HTTP app server, the App Builder-generated modules database, and the associated forest.

Deploying to Other Environments

We have captured the App Builder version of the application. Now suppose we want to set up a copy on some other host “devbox” as our dev environment.

  1. Create a file called deploy/dev.properties
  2. If the ports you used locally are not available on devbox, copy the app-port and xcc-port properties from deploy/build.properties to deploy/dev.properties
  3. If the admin password is different on devbox, copy the password property from build.properties to dev.properties (or leave it blank: “password=”)
  4. Set the dev-server property to the name of the server — you’ll probably need a fully qualified domain name

At that point, you should be set.

$ ml dev boostrap
$ ml dev deploy modules
$ ml dev deploy content

Happy coding!

Tags: , , ,

3 Responses to “Capturing an App Builder application with Roxy”

  1. mohamad Says:

    The transformation is not working when the module deployed.

  2. Dave Cassel Says:

    Hi mohamad. I’ll need more than that to go on. If you found something that isn’t working, please file a bug on GitHub. https://github.com/marklogic/roxy/issues

  3. Geert Josten Says:

    We have done some improvements on the capturing features. There is a new –app-builder=srvname parameter that you can use instead of –modules-db=dbname. That will do a little more effort in capturing REST properties correctly.

    More details about the various improvements here: http://grtjn.blogspot.nl/2014/10/capturing-marklogic-applications-with.html

    Cheers

Leave a Reply