| name | sfcc-script-evaluation |
| description | Guide for using the evaluate_script tool to execute JavaScript on SFCC instances via the script debugger |
SFCC Script Evaluation Skill
This skill documents how to use the evaluate_script tool effectively for executing JavaScript code on an SFCC instance via the script debugger.
Overview
The evaluate_script tool allows you to execute arbitrary JavaScript code on an SFCC sandbox instance. It works by:
- Creating a debugger session
- Setting a breakpoint on a controller
- Triggering the controller via HTTP
- Evaluating your expression in the halted context
- Returning the result and cleaning up
Required Parameters
| Parameter | Required | Default | Description |
|---|
script | Yes | - | The JavaScript code to execute |
siteId | No | RefArch | The site ID (accepts either RefArch or Sites-RefArch-Site) |
locale | No | default | Storefront locale segment used when triggering the controller (tries without locale first, then retries with /{locale} if needed) |
timeout | No | 30000 | Maximum execution time in milliseconds |
breakpointFile | No | Auto-detected | Custom controller path for breakpoint |
breakpointLine | No | 1,10,20,30,40,50 | Specific line for a single breakpoint; if omitted, strategic lines (1,10,20,30,40,50) are used |
triggerUrl | No | Auto-detected | Custom storefront URL or path to trigger; site-relative paths are resolved to https://{hostname}/s/{siteId}/... |
Script Syntax Rules
✅ DO: Use expressions that return a value
The last expression in your script is returned as the result.
1 + 1
dw.system.Site.current.ID
❌ DON'T: Use return at the top level
return 1 + 1
❌ DON'T: Use var assignments expecting the variable
var result = {}; result.foo = 'bar';
✅ DO: Use inline object literals with JSON.stringify
JSON.stringify({siteId: dw.system.Site.current.ID, locale: request.locale})
✅ DO: Use IIFEs (Immediately Invoked Function Expressions) for complex logic
(function() {
var p = dw.catalog.ProductMgr.getProduct('25518704M');
return JSON.stringify({id: p.ID, name: p.name, online: p.online});
})()
❌ DON'T: Use require() statements
var CustomerMgr = require('dw/customer/CustomerMgr');
CustomerMgr.getSiteCustomerList()
✅ DO: Use global dw.* namespace directly
dw.customer.CustomerMgr.getSiteCustomerList().ID
Accessing SFCC Objects
Site Information
dw.system.Site.current.ID
(function() {
var sites = dw.system.Site.getAllSites();
var result = [];
for (var i = 0; i < sites.size(); i++) {
result.push(sites[i].ID);
}
return JSON.stringify(result);
})()
JSON.stringify(Object.keys(dw.system.Site.current.preferences.custom))
dw.system.Site.current.preferences.custom.myPreferenceName
Products
dw.catalog.ProductMgr.getProduct('productId')
(function() {
var p = dw.catalog.ProductMgr.getProduct('25518704M');
if (!p) return 'Product not found';
return JSON.stringify({
id: p.ID,
name: p.name,
online: p.online,
brand: p.brand
});
})()
(function() {
var p = dw.catalog.ProductMgr.getProduct('25518704M');
return JSON.stringify(Object.keys(p.custom));
})()
Customers
dw.customer.CustomerMgr.getSiteCustomerList().ID
dw.customer.CustomerMgr.getCustomerByCustomerNumber('00001234')
Orders
(function() {
var orders = dw.order.OrderMgr.searchOrders(
'orderNo != {0}',
'creationDate desc',
''
);
var result = [];
var i = 0;
while (orders.hasNext() && i < 5) {
var o = orders.next();
result.push({
orderNo: o.orderNo,
status: o.status.value,
total: o.totalGrossPrice.value
});
i++;
}
orders.close();
return JSON.stringify(result);
})()
Request/Session Context
request.locale
session.sessionID
session.customer
Working with Collections
SFCC collections need special handling - they're not JavaScript arrays.
Iterating Collections
(function() {
var sites = dw.system.Site.getAllSites();
var result = [];
for (var i = 0; i < sites.size(); i++) {
result.push(sites[i].ID);
}
return JSON.stringify(result);
})()
(function() {
var iter = dw.catalog.CatalogMgr.getSiteCatalog().getRoot().getSubCategories();
var result = [];
while (iter.hasNext()) {
var cat = iter.next();
result.push({id: cat.ID, name: cat.displayName});
}
return JSON.stringify(result);
})()
Array Operations
JSON.stringify([1, 2, 3].map(function(x) { return x * 2; }))
JSON.stringify([1, 2, 3].map(x => x * 2))
Return Value Formatting
Primitives
'hello'
42
true
Objects
({foo: 'bar'})
JSON.stringify({foo: 'bar'})
SFCC Objects
dw.catalog.ProductMgr.getProduct('25518704M')
dw.catalog.ProductMgr.getProduct('25518704M').name
Error Handling
Check for null values
dw.catalog.ProductMgr.getProduct('invalid').name
(function() {
var p = dw.catalog.ProductMgr.getProduct('invalid');
return p ? p.name : 'Product not found';
})()
Wrap complex logic in try-catch
(function() {
try {
var p = dw.catalog.ProductMgr.getProduct('25518704M');
return JSON.stringify({id: p.ID, name: p.name});
} catch (e) {
return 'Error: ' + e.message;
}
})()
Best Practices Summary
- Never use
return at top level - use expression evaluation instead
- Never use
require() - use global dw.* namespace
- Wrap complex logic in IIFEs for variable declarations
- Use
JSON.stringify() for object/array output
- Close iterators after use (OrderMgr.searchOrders, etc.)
- Check for null before accessing properties
- Verify API usage with
get_sfcc_class_info tool before calling unknown methods
Common Patterns
Quick Value Check
dw.system.Site.current.ID
Multi-Value Query
JSON.stringify({
siteId: dw.system.Site.current.ID,
locale: request.locale,
customerList: dw.customer.CustomerMgr.getSiteCustomerList().ID
})
Complex Data Retrieval
(function() {
var result = [];
return JSON.stringify(result);
})()
Troubleshooting
| Error | Cause | Solution |
|---|
invalid return | Using return at top level | Remove return, use expression or IIFE |
Cannot call method of null | Using require() | Use dw.* global namespace |
Cannot set property of null | var x = {} returns null | Use IIFE or inline object literal |
Timeout waiting for breakpoint | Wrong siteId or instance unreachable | Verify siteId, check instance connectivity |
Unexpected token '<' | Auth/connectivity issue | Check dw.json credentials, verify instance is accessible |
Unauthorized / 401 | Username case mismatch | Username is case-sensitive - match exactly from BM user |
No compatible storefront cartridge | Missing SFRA or SiteGenesis | Deploy app_storefront_base or specify custom breakpoint |
Pre-Flight Checklist
Before using evaluate_script:
- ✅ Valid credentials in dw.json configuration
- ✅ Username matches BM user exactly (case-sensitive!)
- ✅ Sandbox instance is accessible
- ✅ Storefront cartridge deployed (app_storefront_base or app_storefront_controllers)
- ✅ Script uses
dw.* namespace, not require()
- ✅ Complex logic wrapped in IIFE
- ✅ Objects/arrays wrapped in
JSON.stringify()
Requirements
- SFCC sandbox instance
- Either
app_storefront_base (SFRA) or app_storefront_controllers (SiteGenesis) deployed
- Valid credentials in dw.json configuration
- Important: Username in dw.json must match BM user exactly (case-sensitive)