A lot of SFCC code is held together by strings: 'Cart-Show', 'cart/cart', 'button.checkout', 'app.payment.processor.basic_credit'. To plain JavaScript they are just text. Intellij SFCC knows what each one points to, so it completes them from your project and Cmd+Click (Ctrl+Click) takes you to the route, template, bundle key, hook, form or attribute behind them
Resource.msg keys complete from every .properties bundle with the locales that define them. Accepting fills in the bundle name tooRoutes and controllers
| Call | The string | Completes |
|---|---|---|
URLUtils.url, URLUtils.https, URLUtils.http, URLUtils.abs | The full route, for example Cart-Show | Every route of every linked cartridge: SFRA controllers, SiteGenesis exports.<Name> controllers and pipeline start nodes |
server.append, server.prepend, server.replace | A route name of the same controller, for example Show | The routes of the controller you extend |
server.get, server.post, server.use | The route name you define | Nothing, but Cmd+Click lists every other definition, append, prepend and replace of that route |
'use strict';
var server = require('server');
var URLUtils = require('dw/web/URLUtils');
server.extend(module.superModule);
server.append('Show', function (req, res, next) {
res.setViewData({ continueUrl: URLUtils.url('Search-Show', 'cgid', 'root').toString() });
next();
});
module.exports = server.exports();Here 'Show' completes the routes of the original Cart.js, and 'Search-Show' completes from every controller in the project. Route items carry the route icon . To find a route by name from anywhere, use the SFCC Routes tab of Search Everywhere
Templates
| Call | Template argument |
|---|---|
res.render, app.getView().render | First |
ISML.renderTemplate | First |
new Template(...) | First |
renderTemplateHelper.getRenderedHtml | Second |
emailHelpers.sendEmail | Second |
Template paths complete relative to the templates/<locale> folder of each cartridge, without the .isml extension. A call with a known template gets a gutter icon, Navigate to template. When the template exists in several cartridges, the icon opens Choose Declaration with every copy
res.render('cart/cart', { basket: basketModel });Resource bundles
Resource.msg and Resource.msgf complete keys from every .properties bundle in your linked cartridges. Each item lists the locales that define it, default first, and the right side shows the cartridge and bundle, for example app_storefront_base:cart
var Resource = require('dw/web/Resource');
var label = Resource.msg('button.checkout', 'cart', null);
var count = Resource.msgf('label.number.items.in.cart', 'cart', null, 3);- Accept a key in an empty
Resource.msg('')and the plugin fills the whole call: the key, its bundle andnullas the default. ForResource.msgfit leaves the cursor where the format arguments go - The second argument completes bundle names
Cmd+Clickon a key opens its entries in every locale file
Hooks
HookMgr.callHook and HookMgr.hasHook complete the hook names registered in your cartridges' hooks.json files. Each item shows the script it points to and the cartridge that registers it. The second argument of callHook completes the functions that the hook's scripts export
var HookMgr = require('dw/system/HookMgr');
if (HookMgr.hasHook('app.payment.processor.basic_credit')) {
HookMgr.callHook('app.payment.processor.basic_credit', 'Authorize', order.orderNo, paymentInstrument, paymentProcessor);
}SFRA's hooksHelper('app.customer.subscription', 'subscribeTo', ...) works the same way. Cmd+Click on the hook name opens its entry in hooks.json, and on the function name opens the exported function. The hooks.json side, with the 311 built-in hook names, is on XML & JSON Validation
Forms
server.forms.getForm('profile') completes the form IDs from cartridge/forms and opens the form XML on Cmd+Click. The returned form is typed from that XML, so its groups and fields complete like regular objects
var profileForm = server.forms.getForm('profile');
var email = profileForm.customer.email.value;In SiteGenesis-style code, session.forms. completes the form names. Resource keys, includes and validation inside the form XML are covered on XML & JSON Validation
Custom attributes and preferences
The plugin reads your metadata XML and completes custom attribute IDs where SFCC code uses them
| Code | Completes |
|---|---|
product.custom., product.custom['...'], product.getCustom(). | Custom attributes of the object's system type, for example Product |
Site.getCurrent().getCustomPreferenceValue('...') | Custom site preferences |
CustomObjectMgr.getCustomObject('...', key) | Custom object type IDs |
.custom. on a custom object | Attributes of custom object types |
Each item shows the attribute type and group, and the metadata file it comes from on the right. Cmd+Click opens the attribute definition in that file
Metadata is read from files named system-objecttype-extensions.xml or custom-objecttype-definitions.xml and from any XML file in a meta or metadata folder, for example the meta folder of your site import data. Keep that data in the project to get these completions
.custom. completes only when the IDE knows the object's type. If it doesn't, add the dw. type with JSDoc, see API & Types
What isn't checked
The plugin completes and resolves these strings but doesn't mark unknown ones as errors. A misspelled route, template or key compiles and fails only at runtime. A quick check is Cmd+Click: a string that resolves opens its target, one that doesn't goes nowhere
Troubleshooting
| Symptom | What to do |
|---|---|
A route is missing from URLUtils.url | Its controller is in a cartridge that isn't linked, or indexing is still running |
server.append('') lists nothing | Add server.extend(module.superModule) and make sure another linked cartridge has a controller with the same name |
| No Navigate to template icon | The template path doesn't match a file in templates/<locale> of a linked cartridge |
| A resource key is missing | The bundle is in a cartridge that isn't linked, or under a folder other than templates/resources |
No custom attributes after .custom. | The object isn't typed, or the metadata XML isn't in the project. Check the file name or meta folder rules above |
| A hook name is missing | It is registered in a hooks.json of a cartridge that isn't linked |