Examples of Accessing Global Functions in Extensions
The following examples describe the level of access available to global functions from extension artifacts.
Example 1-79 extA is a top level extension that defines a functions JavaScript extAUtils.js
extA defines its own functions files, under ui/self/resources
. Additionally, it also defines functions under an App UI (appUi-A) and under appUi-A/pages
.
- extA has no dependencies on other extensions
- extA defines a public
extAUtils.js
that can be accessed by downstream extensions.- Additionally, UI artifacts such as
some-page.json
can access the extAUtils.
- Additionally, UI artifacts such as
extA/
ui/
self/
resources/
functions/
extAUtils.js
functions.json // { extAUtils: { referenceable: "extension" } }
applications/
appUIA/
.../
some-page.json
manifest.json // { dependencies: [] }
In the example above, some-page.json
can have an imports
section like this:
{
"imports": {
"modules": {
"AUtils": {
"path": "self:$functions/extAUtils"
}
}
}
}
The imported module in the example above can be accessed using the expression ({{ $page.modules.AUtils.someMethod() }}
).
Example 1-80 extA1 depends on extA and defines functions (both private and public)
- extA1 has a dependency on extA
- extA1 defines a private
a1PrivateUtils.js
that can be imported only by extA1 containers.- For example,
a1-form-fragment.json
can import the private module.
- For example,
- It also defines a public
extA1Utils.js
that can be imported by containers in the current and downstream extensions.
extA1/
ui/
self/
resources/
functions/
private/
a1PrivateUtils.js
public/
extA1Utils.js
functions.json
fragments/
a1-form/
a1-form-fragment.json
a1-form-fragment.js
a1-form-fragment.html
manifest.json // { dependencies: [ extA ] }
In the example above, a1-form-fragment.json
can import the private module and have an imports
section. If a module is not declared here, it's not automatically available. For example, 'extA1Utils' is not defined here, so it cannot be used.
{
"imports": {
"modules": {
"A1PrivateUtils": {
"path": "self:$functions/a1PrivateUtils"
},
"extAUtils": {
"path": "extA:$functions/extAUtils"
}
}
}
}
Some fragment markup can call a method exposed on the private utils:
<oj-bind-text text="{{ $modules.A1PrivateUtils.titleCase($variables.name)) }}"/>
<oj-bind-text text="{{ $modules.extAUtils.region($variables.code) }}"/>
Because extA1 depends on extA, it can also refer to public functions from extA.
Example 1-81 extB depends on extA and extA1 and defines a functions JS extBUtils.js
- extB defines a layout 'buttons'
- extB defines its own global functions (extBUtils)
- extB also extends the fragment 'a1-form-fragment' from extA1
extB/
dynamicLayouts/
self/
buttons/
layout.json
ui/
self/
resources/
functions/
extBUtils.js
functions.json
js/
ext-A1/
fragments/
a1-form/
a1-form-fragment-x.json
a1-form-fragment-x.js
manifest.json // dependencies: [ extA, extA1 ]
buttons/layout.json
references the fragment from extA1. It can call the public extAUtils and extA1Utils, in addition to the global functions extBUtils. This could be defined in layout.json
:
{
"imports": {
"modules": {
"extA1Utils": {
"path": "extA1:$functions/extA1Utils"
},
"BUtils": {
"path": "self:$functions/extBUtils"
}
}
}
}
The layout.html
could define a template that uses a fragment from extA1. The fragment, because it's defined by extA1, can internally call a 'functions' module that is private to extA1.
<template id="formTemplateSimple">
<oj-vb-fragment name="extA1:a1-form"
bridge="[[vbBridge ]]">
<oj-vb-fragment-param name="dynamicLayoutContext"
value="[[ $dynamicLayoutContext ]]"></oj-vb-fragment-param>
<oj-vb-fragment-param name="foo" value="[[ $modules.BUtils.titleCase($layout.variables.lucy) ]]">
</oj-vb-fragment-param>
</oj-vb-fragment>
</template>
extB also extends the fragment from extA1. This means the fragment-x will need to explicitly define all imports it needs from the current extension and any of its upstream extensions. The use of $base
is not recommended for accessing imports of the base container, because the exact list of imports that are accessible by the extended artifact cannot be easily determined, nor can it be complete. For example, the a1-form-fragment.json
from extA1 did not import extA1Utils. Likewise, it imports local resources that should be hidden for the current extension.
It is recommended that authors explicitly import the modules they need. A sample imports on a1-form-fragment-x.json
might look like this:
{
"imports": {
"modules": {
"extA1Utils": {
"path": "extA1:$functions/extA1Utils"
}
}
}
}
Example 1-82 extZ extends layout from extB and also depends on extA1
- extZ extends the 'buttons' layout from extB and also defines its own 'zippers' layout.
- extZ also overrides some pages from the unified app.
- extZ also defines its own functions, in addition to having a 'functions' folder at the App UI level (
resources/functions
) folder under appUiZ (see the example below).- While there appears to be a
functions.json
defined at the App UI resources level, these cannot be imported into the App UI using the$functions
scheme. These files can be imported into the App UI pages using the current schemes for importing such files.
- While there appears to be a
extZ/
dynamicLayouts/
extB/
buttons/
layout-x.json
self/
zippers/
layout.json
ui/
self/
applications/
appUiZ/
app.json
pages/
shell-page.html
shell-page.json
resources/
functions/
appUiZtils.js
functions.json
resources/
functions/
extZUtils.js
functions.json
base/
pages/
root/
first-page-x.json
app-flow-x.json
manifest.json // dependencies: [ extB, extA1 ]
The following sections detail the level of access for functions and the $modules
usage in the various Visual Builder containers.
Functions Access and $modules Usage in extZ/dynamicLayouts/extB/buttons/layout-x
When layout-x is an extension of a layout from extB, it should be possible to import extB's functions, as well as the dependency extension (extA1).
extA is not specified in the dependencies list, so its functions cannot be imported.
Note:
An extension must explicitly import the resources it needs, and not use$base
to access the imports set up by the artifact it extends.
extZ defines its own functions, so layout-x can import any of these.
{
"imports": {
"modules": {
"extBUtils": {
"path": "extB:$functions/extBUtils"
},
"extA1Utils": {
"path": "extA1:$functions/extA1Utils"
},
"ZUtils": {
"path": "self:$functions/extZUtils"
}
}
}
}
Functions Access and $modules Usage in extZ/dynamicLayouts/self/zippers/layout-x
The files allowed in the previous section are also allowed here.
Functions Access and $modules Usage in extZ/ui/self/applications/appUiZ/pages/shell-page
The files allowed in the previous section are also allowed here.
Functions Access and $modules Usage in extZ/ui/base/pages/app-flow-x.json
The files allowed in the previous section are also allowed here.