Framework Launch

This chapter describes the start-up of the JavaScript OSGi runtime.

Launcher $apprt.startApp

The framework is started by the statement $apprt.startApp. To launch the framework following snippet can be used.

$apprt.startApp in index.html
<script type="text/javascript" src="<registry-root>/apprt-core/<version>/boot.js"></script>
<script type="text/javascript">
  $apprt.startApp({
    param : "app",
    defaultApp : "traffic"
  });
</script>

When apprt-core/boot.js is loaded it makes the function $apprt.startApp globally available. This function provides two ways to start an application.

Use-case Sample Description

Start well-known app.

$apprt.startApp({
    app: "traffic",
    domId: "app-node"
});

App with name traffic is started.

The optional parameter domId defines the ID of a DOM node. The app is embedded inside this node.

Start app named by a query parameter.

$apprt.startApp({
  param : "app",
  defaultApp : "traffic"
});

Checks if a query parameter named app exists. If yes its value is interpreted as application name.

The function accepts the following options:

param: The name of the query parameter that contains the application name.

defaultApp: The name of the application that should be started if no query parameter is present.

domId: The ID of a DOM node where the application should be embedded.

Integrated Application Configuration

The parameter app supports a special configuration style - the so-called inline application definition - meaning that the app.json is declared directly inside the HTML page.

A definition looks like this:

inlined app.json
<script type="text/javascript" src="<registry-root>/apprt-core/<version>/boot.js"></script>
<script type="text/javascript">
$apprt.startApp({
    app: {
        "appName": "myapp",
        "load": {
            "allowedBundles": [
                "system",
                "templatelayout",
                "splashscreen",
                ...
            ]
        },
        "bundles" : {
            ...
        }
    }
});
</script>
<body class="start">
   ...
</body>

The JSON configuration of the application is directly embedded inside the app option of the $apprt.startApp.

These are special advanced features that should only be used when necessary.

There is a special "merge" mode. This means if you do not declare a load section in the app.json within the HTML or you declare "load": { "merge": true} in the inlined app.json, the appName is used to fetch a basic app.json configuration and the inline definition is merged into this base configuration to get the effective configuration. This allows to partially overwrite a common configuration.

The same behavior is supported if the query parameter app contains no name but an app.json definition.

Background

This diagram demonstrates the startup flow in detail.

bundle resolving

Following steps are performed during the framework start:

  1. Launcher (ConfigLocator) resolves the app.json

  2. Launcher (BundleLocator) resolves the bundles.json files in the root of each bundle location (specified in the app.json)

  3. The manifest.json files of required bundles are resolved (if not embedded in bundles.json)

  4. The core engine class (apprt/launch/BundleController) is created

  5. The system.bundle is installed and started (also called the framework bundle)

  6. All other required bundles are installed into the framework

  7. The framework is started (all bundles with autoStartPolicy=yes are started)

After these steps the application is ready for use.

ConfigLocator

The class apprt/launch/ConfigLocator is being used by the Launcher to fetch app.json files (locate a configuration). It is also responsible for the ${app} key replacement in the app.json files.

In the $apprt.startApp method you can specify following properties to customize the ConfigLocator:

Property Sample Description

configLocation

$apprt.startApp({
  configLocation: "apps"
})

optional (default: "apps")

The AMD prefix of the configuration location path. Use "builderapps" if you want to locate configurations (app.json files) of apps created in the map.apps Manager.

configFilePattern

$apprt.startApp({
 configFilePattern: "{appName}/test.json"
})

optional (default: "{appName}/app.json")

A resolution pattern for the sub path in the configuration location. Can be used to map to a different file as app.json if required.

BundleLocator

The class apprt/launch/BundleLocator is being used by the Launcher to fetch bundles.json file and manifest.json file.

The BundleLocator accepts the "Common JS Package Registry" format as input. For more details, see the concept of the JS Registry.

The default BundleLocator first fetches bundles.json files from bundle locations. A bundles.json file can have this structure:

bundles.json
// a bundles.json file with different kinds of package definitions
{
  // request the folder1/bundle1/manifest.json file relative to bundles.json
  "folder1/bundle1": {},

  // meta information of bundle2 is inlined
  "folder1/bundle2": {
       "Bundle-SymbolicName" : "bundle2",
        "Bundle-Version" : "1.0.0",
        ...
   },

  // request the folder3/manifest.json file relative to bundles.json
  "bundle3": "folder3/manifest.json",

  // sample that the relative path can go outside the location of the bundles.json
  "bundle4": "../folder/manifest.json",

  // use explicite URL to define manifest.json location
  "bundle5": "http://.../manifest.json",

  // with inlined version information and relative path
  // request the bundle6/manifest.json file relative to bundles.json
  "bundle6": {
        "name": "bundle6",
        "dist-tags": {
            "latest": "2.0"
        },
        "versions": {
            "2.0": "bundle6/manifest.json"
        }
   },

   // inlined manifest in version format
  "bundle6": {
        "name": "bundle6",
        "dist-tags": {
            "latest": "1.0"
        },
        "versions": {
            "1.0": {
                "Bundle-SymbolicName": "bundle6",
                "Bundle-Version": "1.0",
                ...
            }
        }
    }
}

If the bundle location is "bundles" that points to "http://localhost:8080/js/bundles", the BundleLocator first resolves the file "http://localhost:8080/js/bundles/bundles.json", parses the content and fetches the manifest.json for each required bundle in the file if not embedded into the bundles.json, for example "http://localhost:8080/js/bundles/mapcore/map/manifest.json".

In the $apprt.startApp method you can specify the following properties to customize the BundleLocator:

Property Sample Description

locations

$apprt.startApp({
  locations: ["bundles"]
})

optional (default: ["bundles"])

The AMD prefixes of the bundle locations. The values can be overwritten in an app.json (bundleLocations)

The Launcher requests the bundles.json, parametrized like this:

http://localhost:8080/js/bundles/bundles.json?needed=…​&skip=…​;

This allows the optimization through server side code, for example autoinlining of manifest.json files and the delivering of only these bundle metadata needed by the application.

preFetchBundles

$apprt.startApp({
  preFetchBundles: true
})

optional (default: dojo.config.ct.preFetchBundles)

Flag indicating that prefetching of bundle JavaScript code is enabled. For more details, see JavaScript prefetching.

JavaScript prefetching

This is a dynamic loading feature which ensures the JavaScript files needed by the application are fetched in a single request, which is much faster than single file fetching.

Only the preFetchBundles option of the Launcher enables the feature. It does not mean that it is enabled for all bundle locations.

JavaScript files are only prefetched from a BundleLocation if this is explicitly enabled for a bundle location.

It can be enabled in two different ways: . use the object notation in the "bundleLocation" specification and define a prefetch property . add a "__meta" property in a bundles.json

enable pre-fetching
// in app.json (see also Configuration/BundleLocation section)
{
    "load" : {
        "bundleLocations" :[{
            name : "bundles",
            prefetch : "./bundles.js"
        }]
    }
}

// in bundles.json or registry response
{
    // registry/location meta information
    "__meta" : {
        "prefetch" : "./bundles.js"
    },

    "<bundle name>" : ...
    ...
}

// NOTE: it is possible to use not the default "bundles.js" name, for example the JS Registry defines following:
__meta: {
    prefetch: "http://localhost:8080/resources/jsregistry/root/layer.js?requires=%7Binclude%7D&requires_skip=%7Bexclude%7D&locale=%7Blocale%7D"
}

// prefetch url explanation:
// %7Binclude%7D is the string "{include}": a place holder all required bundle names
// %7Bexclude%7D is the string "{exclude}": a place holder all bundles to skip
// %7Blocale%7D is the string "{locale}"  : a place holder the current locale