Introduction Writing your own formatters can be easily done if you have common knowledge about JavaScript. We will explain how you register your own formatters
Writing your own formatters can be easily done if you have common knowledge about JavaScript. We will explain how you register your own formatters and give some samples.
Formatters are registered for a specific data type, the types available in App Connect are string, number, boolean, array, object, and null. There are also some special types undefined, global and any. We will explain them all in some examples.
There are 2 ways to register formatters, the first is registering a single formatter using dmx.Formatter(datatype, name, function) and secondly for registering multiple formatters for a specific datatype using dmx.Formatters(datatype, object).
The first argument of the formatter function is the input data, the other arguments are the ones passed in the expression. It is important that the function has no side effects, when the same input is given it should always return the same output again.
[!warning]
Formatters should only be used for formatting data and are always sync functions. When you need async function or functions with side-effects you should create a flow action instead.
// using the expression {{"ha".repeat(4)}} will return "hahahaha"
dmx.Formatter('string', 'repeat', function(str, n) {
return new Array(n + 1).join(str);
});
[!example]- Example: Localization using Intl
The following formatters uses the build-in browser Internationalization library for formatting for a specific locale.
// Datetime are passed as UTC strings and not as Date objects.
// Most browsers understand the ISO standard and you can simply use
// new Date(dateString) to get the date. Alternative you can use
// the dmx.parseDate() to parse the string, it also converts numbers
// as unix timestamps and the string now will return the current date.
For complex functions that use heavy calculations you can use Memoization which is an optimization technique that makes the application more efficient and hence faster. It does this by storing computation results in cache, and retrieving that same information from the cache the next time it's needed instead of computing it again.
[!example]- Example: Caching results
// Simple example with lookup table.
// We wrap it in an anonymous function to prevent the variables from leaking
// to the global scope where they can potentially cause some conflicts.
(() => {
// We use a Map for our cache
const cache = new Map();
dmx.Formatter(‘number’, ‘heavyCalculation’, (n) => {
if (!cache.has(n)) {
const result = doHeavyCalculation(n);
cache.set(n, result);
return result;
}
return cache.get(n);
});
})()
[!example]- Example: Fibonacci sequence
Example using the Fibonacci sequence and a recursive function.
For performance it uses memoization by caching previous results.
dmx.Formatter('number', 'fib', function fib(n, memo) {
memo = memo || {};
if (memo[n]) return memo[n];
if (n <= 1) return n;
return memo[n] = fib(n-1, memo) + fib(n-2, memo);
});
[!hint]
Some data types that are recognized but currently not officially supported are date, regexp, blob, file, filelist, arraybuffer, imagebitmap, imagedata, map and set.