v0.9

App

class App extends Router → mvc/App.js

Instance

To start the app create an object instance.
const app = new App(appName);

Properties

The app instance properties are:
Property Description Type Default
$appName The application name. It defines the window property. For example if $appName='myApp' then window.myApp string dodoApp
$debugOpts Debugger options. Set specific option to true if you want to see the debugging messages. See all options. object {...}
$postflight array of postflight functions, will be executed on every route ater the controller's __postrend() Function[] []
$preflight array of preflight functions, will be executed on every route before the controller's __loader() Function[] []
ctrlConstants A controller constants which will not be deleted when one controller is replaced by another controller (when route is changed).
{$appName, $fridge, $httpClient, $auth, $debugOpts, $model, $modeler, $dd}
object {...}
ctrls A collection of all controllers. This makes possible to use a controller's methods inside another controller. object {}
routeDefs route definitions object[]

Methods

fridge($fridge) :App

Establish a $fridge property that remains accessible and unchanged across all controllers.
The $fridge object will persist even when the app route changes and controllers are replaced. Conversely, other controller properties will be deleted.
This approach is useful for defining values that need to be shared among all controllers.
The $fridge can contain properties and functions.
    ARGUMENTS:
  • $fridge :object - $fridge object, for example {'api_url': 'http://dex8.com'} then the frozen constant will be this.$fridge.api_url and it can be used in every controller
EXAMPLE:
Let's define a constant that will be needed in all or most of the controllers, such as an API URL.
const app = new App('myApp');
const $fridge = {
 api_baseurl: 'http://api.example.com',
 func: (key) => {
   const ctrl = corelib.navig.current.ctrl; // current controller
   const skript = ctrl.skripts[key];
   return ctrl.$model.loggedUser.username !== skript?.user_id.username ? { color: 'green' } : {};
}
}
app.fridge($fridge); // put the object in the fridge
Now we can fetch the api_baseurl in every controller with this.$fridge.api_baseurl

httpClient($httpClient) :App

Set the $httpClient property in all controllers. It can be called with this.$httpClient in the controller.
The HTTP client is used for specific API calls.
    ARGUMENTS:
  • $httpClient :object - the http client object
EXAMPLE:
An app needs HTTP client in the controllers to fetch the JSON from API.

// src/const/$httpClient.js
=========================
import { corelib } from '@mikosoft/dodo';

// default HTTP client
const opts = {
  encodeURI: true,
  timeout: 21000,
  responseType: '', // 'blob' for file download (https://developer.mozilla.org/en-US/docs/Web/API/XMLHttpRequest/responseType)
  retry: 0,
  retryDelay: 1300,
  maxRedirects: 0,
  headers: {}
};
const $httpClient = new corelib.HTTPClient(opts);

export { $httpClient };


// src/app.js
=========================
import { $httpClient } from './conf/httpClient.js';
const app = new App('myApp');
app.httpClient($httpClient);
Now this.$httpClient is injected in every controller and can be used to call the API.
// src/controllers/SomeCtrl.js
=============================
import { Controller } from '@mikosoft/dodo';

class SomeCtrl extends Controller {
  async __init() {
    const answer = await this.$httpClient.askJSON('https://jsonplaceholder.typicode.com/posts/1');
  }
}

auth($auth) :App

Inject the auth library into all controllers and access it using `this.$auth` within the controller.
This is particularly useful for applications that require authentication guards on all routes, such as web panels where users need to log in.
    ARGUMENTS:
  • $auth :object - instance of the Auth class
EXAMPLE:
Create an app which has login and dashboard page. After succesful login the user is redirected to dashboard.
Study the Stackblitz example

debug($debugOpts) :App

Set the debug options.
EXAMPLE:
Lets define a constant which will be needed in all or most of the controllers, for example an API URL.
import { $httpClient, $debugOpts } from './conf/index.js';
const app = new App('myApp');
app
  .httpClient($httpClient)
  .debug($debugOpts);

preflight($preflight) :App

Define preflight functions which will be executed on every route before controller __loader() hook.
    ARGUMENTS:
  • $preflight :Function[] - array of functions (some or all functions can be async, with trx argument)
EXAMPLE:
Define and export preflight functions in the lib/$preflight.js
// lib/$preflight.js
const rend_loggedUser = (trx) => {
  const ctrl = corelib.navig.current.ctrl; // fetch current page controller from navig
  ctrl.$model.loggedUser = ctrl.$auth.loggedUser; // update loggedUser in the views/inc/.../header.html
};
export default [rend_loggedUser];


// app.js
const app = new App('webPanel');
app
  .auth(auth)
  .fridge('wsLib', wsLib)
  .preflight($preflight)
  .postflight($postflight)
  .debug($debugOpts);

postflight($postflight) :App

Define postflight functions which will be executed on every route after controller __postrend() hook.
    ARGUMENTS:
  • $postflight :Function[] - array of functions (some or all functions can be async, with trx argument)

destroyflight($destroyflight) :App

Define destroyflight function which will be executed when controller is destroyed i.e. when route is changed.
It's useful for example when you want to off() some event listeners.
    ARGUMENTS:
  • $destroyflight :Function - a single function (This function doesn't have arguments)

i18n($i18n) :void

Set the global window.<appName>.i18n property, which is used in the View.loadI18n(langCode) method.
The language object $i18n can be loaded from various sources such as databases, files, browser storage, etc
It is not saved in the controller object to keep it as small as possible. The language $i18n object can be large and significantly increase the size of the controller object.
    ARGUMENTS:
  • $i18n :object - object with language translations, for example {de: {common: {USERNAME: 'Nutzername'}, home: {TITLE: 'Startseite', LOGIN: 'Anmeldung'}}}
EXAMPLE:
As the i18n() is async function it must be wrapped in async function so await can be used. Call i18n() before routes() and listen() because language json files must be read before controller execution.
const initApp = async () => {
  const app = new App('dodoApp');
  app
    .auth($auth)
    .httpClient($httpClient)
    .debug($debugOpts)
    .i18n($i18n); // load language JSON files in the window.dodoApp.i18n
    .routes($routes)
    .listen();

routes($routes) :object

Define app routes i.e. which controller will be executed when app URL is changed.
    ARGUMENTS:
  • $routes :object - the routes object
EXAMPLE:
Create HomeCtrl controller and inject it in the $routes.
Study the Stackblitz example

listen() :void

Listen for the route changes. Should be used after routes() method.
    ARGUMENTS:
  • - no arguments

Stackblitz Examples

  • Example 1 - how to make APP instance and how to use its methods