Join the #BuildWithBuildAgent Challenge! Get recognized, earn exclusive swag, and inspire the ServiceNow Community with what you can build using Build Agent.  Join the Challenge.

Incident client script access DOM for getElementById

xiaix
Tera Guru

Needed a client script to a "g_form.showFieldMsg()" on the subcategory field.  Easy enough, right?  Only issue is the message I needed displayed had line breaks, and well... you can't add line breaks in a showFieldMsg.  I tried the \r\n and <br/> methods, but all failed.  I realized I needed to wrap that message in a <pre> tag for the line breaks "\r\n" to work.  

 

The other issue was that if I did this, I also had to set the parent div of the showFieldMsg to "fit-content".

Here's the rub... the showFieldMsg div's id is "incident.subcategory_fieldmsg", but har har if you think you can use top.document.getElementById().  Oh no no no, it's all buried in the infamous gsft_main iFrame, but then to make matters worse, THAT's all buried in a shadowRoot element.  What a joke.  

 

I digress... here is what I needed to have happen:

xiaix_0-1761672120137.gif

And here's the client script code I used to make it happen:

 

function onChange(control, oldValue, newValue, isLoading, isTemplate) {
    if (isLoading) {
        return;
    }

    function consoleWarn(msg) {
        /* eslint-disable-next-line no-console */
        console.warn(msg);
    }

    function consoleDir(msg) {
        /* eslint-disable-next-line no-console */
        console.dir(msg);
    }

    g_form.hideFieldMsg("subcategory");
    var msg = false;
    var lineBreak = "\r\n";
    var category = g_form.getValue("category");
    if (category == "NEW Truck Service System (Dynamics 365)") {
        switch (newValue) {
            case "":
                break;
            case "Access & Configuration":
                msg = '- Access denied errors and principal user errors' + lineBreak;
                msg += '- TSA role misconfigured (e.g., able to edit Work Orders or create accounts)' + lineBreak;
                msg += '- Site Manager (lacks access to functional location tab)' + lineBreak;
                msg += '- Site Manager (Incorrect account/contact creation)' + lineBreak;
                msg += '-Shop employee plays a temporary TSA role and will need TSA permissions';
                break;
            case "Resource Management - Site Manager":
                msg = '- Site Manager Unable to edit newly created skills and characteristics' + lineBreak;
                msg += '- Site Manager Error adding skill to technician' + lineBreak;
                msg += '- Site Manager unable to create new resource from skills page' + lineBreak;
                break;
            case "Resource Management/Booking  - TSA":
                msg = '- TSA Resource category table not visible' + lineBreak;
                msg += '- TSA Not able to see Technical Resources in the Schedule Dashboard' + lineBreak;
                msg += '- Time zone discrepancies during booking' + lineBreak;
                msg += '- Incorrect estimated time updates';
                break;
            case "Reporting":
                msg = '- Work Order Summary or Resource Utilization report not available' + lineBreak;
                msg += '- Dashboards not rendering properly' + lineBreak;
                msg += '- KPI dashboards missing or incomplete';
                break;
			case "Feedback Survey Issues":
                msg = '- Survey invitations not sent after work order completion';
                break;
			case "Customer Notifications":
                msg = '- SMS notifications not triggered properly';
                break;
			case "Shopcore to D365 Misalignment":
                msg = '- Work orders not flowing from ShopCore' + lineBreak;
                msg += '- Status changes not reflected in D365' + lineBreak;
                msg += '- Time zone discrepancies during booking' + lineBreak;
                msg += '- Incorrect estimated time updates';
                break;
			case "Operations & Scheduling":
                msg = '- Site Manager unable to create or delete bookings from Schedule Board' + lineBreak;
                msg += '- Empty entries in Bookable Resources view' + lineBreak;
                msg += '- Booking suggestions not available for G13/multi-resource work orders' + lineBreak;
                msg += '- Wait time estimates not visible';
                break;
			case "XXX": /* template */
                msg = 'XXX' + lineBreak;
                msg += 'XXX' + lineBreak;
                break;
        }
    }

    if (msg) {
        g_form.showFieldMsg("subcategory", msg);
        try {
            setTimeout(function() {

                var mc = top.document.getElementsByTagName("MACROPONENT-F51912F4C700201072B211D4D8C26010")[0];
                if (mc) {
                    var shadowRoot_ = mc.shadowRoot;
                    if (shadowRoot_) {
                        var iFrame = shadowRoot_.querySelector("#gsft_main");
                        if (iFrame) {
                            var iframeDoc = iFrame.contentWindow.document;
                            var iframeWin = iFrame.contentWindow;

                            if (iframeDoc) {
                                var div = iframeDoc.getElementById("incident.subcategory_fieldmsg");
                                if (div) {
                                    div.style.setProperty("width", "fit-content");
                                    var pre = iframeDoc.createElement("pre");
                                    pre.appendChild(div.children[0]);
                                    div.appendChild(pre);
                                } else {
                                    consoleWarn("NO DIV FOUND");
                                }
                            } else {
                                consoleWarn("no iframeDoc");
                            }

                        } else {
                            consoleWarn("no iFrame");
                        }
                    } else {
                        consoleWarn("no shadowRoot_");
                    }
                } else {
                    consoleWarn("no mc");
                }
            }, 300);
        } catch (e) {
            consoleWarn("try/catch err: " + e.message);
        }
    }

}

 

Pay very close attention to the code here:

 

var mc = top.document.getElementsByTagName("MACROPONENT-F51912F4C700201072B211D4D8C26010")[0];
                if (mc) {
                    var shadowRoot_ = mc.shadowRoot;
                    if (shadowRoot_) {
                        var iFrame = shadowRoot_.querySelector("#gsft_main");
                        if (iFrame) {
                            var iframeDoc = iFrame.contentWindow.document;

 

that's the magic-sauce to access elements buried in a shadowRoot that's buried in the gsft_main iFrame.

 

Lovely we are forced to do such things, isn't it?

0 REPLIES 0