30 Dec 2025 06:06 PM
Hi,
I have a Browser Synthetic monitor with a JavaScript step, where under certain conditions I explicitly fail the execution using:
api.fail("My message");What I’m trying to achieve is:
a metric that counts failures of the synthetic monitor,
grouped or filtered by the failure message ("My message").
In Data Explorer, I can find synthetic error/failure metrics that allow split by:
geolocation
synthetic event
error code
However, I don’t see any dimension related to the failure reason / message coming from api.fail().
Is it possible to create a metric that counts synthetic failures based on the custom message passed to api.fail()?
(e.g. count executions failed with "My message")
Is there a way in a JavaScript step to explicitly define an error code when calling api.fail() (similar to HTTP error codes), or is it always message-only?
If this is not supported directly:
what would be the recommended best practice for distinguishing different failure reasons inside a single synthetic monitor?
Thanks in advance for any guidance or examples!
Regards, Deni
Solved! Go to Solution.
30 Dec 2025 06:30 PM - edited 30 Dec 2025 06:31 PM
I have done something similar but for http synthetic.
During the failure, in the javascript step (post execution in HTTP), I call the metric api to ingest a data point with the error message as dimension.
And for question 2, I don't think you can define custom HTTP errors to be displayed as your synthetic HTTP result.
https://docs.dynatrace.com/docs/observe/digital-experience/synthetic-monitoring/browser-monitors/bro...
30 Dec 2025 07:12 PM
Example of javascript code to call the metric api (it can be the log ingest api too)
(async function () {
try {
const ENV_URL = 'https://<yourtenanthere>.live.dynatrace.com';
const INGEST_URL = `${ENV_URL}/api/v2/metrics/ingest`;
const API_TOKEN = '<yourtokenhere>';
const metricKey = 'custom.synthetic.browser.message';
const dimKey = 'message';
const dimValue = 'Your Message';
const gaugeValue = 1;
const timestamp = Date.now();
const line = `${metricKey},${dimKey}="${dimValue}" gauge,${gaugeValue} ${timestamp}`;
const res = await fetch(INGEST_URL, {
method: 'POST',
headers: {
'Authorization': `Api-Token ${API_TOKEN}`, // requires metrics.ingest scope
'Content-Type': 'text/plain; charset=utf-8'
},
body: line,
mode: 'cors',
cache: 'no-store'
});
const text = await res.text();
api.info(`Metric ingest HTTP status: ${res.status} ${res.statusText}`);
if (text) api.info(`Ingest response: ${text}`);
if (res.status === 202 || res.status === 400) {
api.finish();
} else {
api.fail(`Metric ingest failed: ${res.status} ${res.statusText}`);
}
} catch (err) {
api.fail(`Metric ingest error: ${err.message}`);
}
})();Regards
30 Dec 2025 07:24 PM
Thank you very much 🙂
I’ve just started to “fight” with this and I really appreciate the example you shared.
just one more question, currently my code on the javascript synthetic event is:
var text = document.documentElement.innerText;
var isFound = text.indexOf('text') > -1;
if (isFound) {
api.fail("My reason");
}
How to integrate this call, something like this?
<my code>
(async function () { ... })
or should insert my code somewhere inside the async function?
Thank you!
Regards, Deni
Featured Posts