Duplicate Attachment is being sent from one ServiceNow Instance to Another Servicenow

SandeepKSingh
Kilo Sage

Hi Team,

 

I have a issue as I have created the below  rest message  and everytime on update also it is sending same attachment twice.

How to control this ??

I have used After BR Insert

(function executeRule(current, previous /*null when async*/ ) {
    var answer = "";
    var attachmentMsg = "";
    var targetUserID = "admin";
    var targetUserPassword = ""; //I have used my password
    var targetInstanceURL = "https://dev244808.service-now.com/";

    var r = new sn_ws.RESTMessageV2('dev244808-Ebonding', 'Create an Incident');
    r.setStringParameterNoEscape('id', current.sys_id);
    r.setStringParameterNoEscape('state', current.state);
    r.setStringParameterNoEscape('sd', current.short_description);
    r.setStringParameterNoEscape('caller', current.caller_id);
    r.setStringParameterNoEscape('cat', current.category);

    var response = r.execute();
    var responseBody = response.getBody();
    var httpStatus = response.getStatusCode();

    if (httpStatus.toString() == "201") {
        answer = "Incident successfully sent.";

        var parser = new JSONParser();
        var parsed = parser.parse(responseBody);
        var targetRec = parsed.result;
        var attachmentCount = sendAttachments(current.getTableName(), current.sys_id, targetRec.sys_id);

        if (attachmentCount != "none") {
            attachmentMsg = " Attachments successfully sent: " + attachmentCount[0].toString() + ". Attachments failed to be sent: " + attachmentCount[1].toString();
        } else {
            attachmentMsg = " Record had no attachments to send.";
        }
    } else {

      gs.addInfoMessage('Failed');
    }
    answer = answer + attachmentMsg;
    gs.addInfoMessage(answer);
    function sendAttachments(sourceTable, sourceID, targetID) {
        var answer = [0, 0]; //successful attachments, failed attachments
        var attachmentRec = new GlideRecord("sys_attachment");
        attachmentRec.addQuery("table_sys_id", sourceID);
        attachmentRec.addQuery("table_name", sourceTable);
        attachmentRec.query();
        if (attachmentRec.hasNext()) {
            while (attachmentRec.next()) {
                var attachmentMessage = new sn_ws.RESTMessageV2();
                attachmentMessage.setHttpMethod("post");
                attachmentMessage.setBasicAuth(targetUserID, targetUserPassword);
                attachmentMessage.setEndpoint(targetInstanceURL + "api/now/attachment/file");
                attachmentMessage.setQueryParameter("table_name", attachmentRec.table_name);
                attachmentMessage.setQueryParameter("table_sys_id", targetID);
                attachmentMessage.setQueryParameter("file_name", attachmentRec.file_name);
                attachmentMessage.setRequestHeader("Content-Type", attachmentRec.content_type);
                attachmentMessage.setRequestHeader("Accept", "application/json");
                attachmentMessage.setRequestBodyFromAttachment(attachmentRec.sys_id);
                var response = attachmentMessage.execute();
                var responseBody = response.getBody();
                var parsedAtt = JSON.parse(responseBody);
                var attsys = parsedAtt.result.sys_id;
                var httpStatus = response.getStatusCode();
                if (httpStatus.toString() == "201") {
                    answer[0] += 1;
                } else {
                    answer[1] += 1;
                }
            }
        } else {
            answer = "none";
        }
        return answer;
    }
})(current, previous);
2 ACCEPTED SOLUTIONS

ShubhamGarg
Kilo Sage

Hello @SandeepKSingh ,

Duplicate is being sent because you are fetching all the attachments (every time) while sending the update.

Either you can -

1. Fetch only latest attachment.

2. Use 'Hash' key/column on attachment records and compare with previous attachments so sent. It will fetch only latest attachment.

Hope it helps.

If my response helps you in any way, kindly mark this as Accepted Solution/Helpful and help in closing this thread.

Regards,

Shubham

View solution in original post

Adding to @ShubhamGarg  you can update the script like the below
Check if you are getting 200 and check for Existing attachment by using "Get" Method and if exisits don't send else send.

 if (httpStatus.toString() == "200") {
        answer = "Incident successfully sent.";

        // Check for Existing Attachments
        var checkIncident = new sn_ws.RESTMessageV2('your Message', 'Get Method');
        checkIncident.setStringParameterNoEscape('sys_id', current.sys_id);
        var checkResponse = checkIncident.execute();
        var checkResponseBody = checkResponse.getBody();
        var checkHttpStatus = checkResponse.getStatusCode();
        gs.addInfoMessage("Get Attachment response status: " + checkHttpStatus);
        var existingAttachments = JSON.parse(checkResponseBody).result;
        var existingAttachmentNames = [];

        for (var i = 0; i < existingAttachments.length; i++) {
            if (existingAttachments[i].table_sys_id == current.sys_id.toString()) {
                existingAttachmentNames.push(existingAttachments[i].file_name);
            }
        }

        // Send New Attachments
        var parser = new JSONParser();
        var parsed = parser.parse(responseBody);
        var targetRec = parsed.result;
        var attachmentCount = sendAttachments(current.getTableName(), current.sys_id, targetRec.sys_id, existingAttachmentNames);
        if (attachmentCount.length > 0) {
            attachmentMsg = " Attachments successfully sent: " + attachmentCount[0] + ". Attachments failed to be sent: " + attachmentCount[1];
        } else {
            attachmentMsg = " Record had no new attachments to send.";
        }
    } else {
        gs.addInfoMessage('Failed');
    }
and After this call your function "sendAttachments".

I hope that should work
--------------------------------------------------------------------------------------------------------------------------


If you found my response helpful, I would greatly appreciate it if you could mark it as "Accepted Solution" and "Helpful."
Your support not only benefits the community but also encourages me to continue assisting. Thank you so much!

Thanks and Regards
Ravi Gaurav | ServiceNow MVP 2025,2024 | ServiceNow Practice Lead | Solution Architect
CGI
M.Tech in Data Science & AI

 YouTube: https://www.youtube.com/@learnservicenowwithravi
 LinkedIn: https://www.linkedin.com/in/ravi-gaurav-a67542aa/

View solution in original post

4 REPLIES 4

ShubhamGarg
Kilo Sage

Hello @SandeepKSingh ,

Duplicate is being sent because you are fetching all the attachments (every time) while sending the update.

Either you can -

1. Fetch only latest attachment.

2. Use 'Hash' key/column on attachment records and compare with previous attachments so sent. It will fetch only latest attachment.

Hope it helps.

If my response helps you in any way, kindly mark this as Accepted Solution/Helpful and help in closing this thread.

Regards,

Shubham

Thanks Shubham will try.. can you provide sample code??

 

Hello @SandeepKSingh ,

1. To fetch latest record of given table, you can always use orderByDesc function of GlideRecord class. Sample code -

 

.orderByDesc('sys_created_on');

 

 2. You can use hash query. Sample code -

 

.addEncodedQuery('table_sys_id=' + <object>+ '^hash=' + <appropriate object>.hash);

 

In both point 1 and point 2, you would need some array of sys_ids to compare with. You can use your Outbound Integration Logs, if defined.

 

If you do not have list of sys_ids to compare with and you have access to Integrated ServiceNow instance using attachment API, then what can be done is to remove all attachments (count = N), then copy all attachments using your existing logic(new count = N+1).

 

If my response helps you in any way, kindly mark it as Accepted Solution/Helpful and help in closing this thread.

Regards,

Shubham

Adding to @ShubhamGarg  you can update the script like the below
Check if you are getting 200 and check for Existing attachment by using "Get" Method and if exisits don't send else send.

 if (httpStatus.toString() == "200") {
        answer = "Incident successfully sent.";

        // Check for Existing Attachments
        var checkIncident = new sn_ws.RESTMessageV2('your Message', 'Get Method');
        checkIncident.setStringParameterNoEscape('sys_id', current.sys_id);
        var checkResponse = checkIncident.execute();
        var checkResponseBody = checkResponse.getBody();
        var checkHttpStatus = checkResponse.getStatusCode();
        gs.addInfoMessage("Get Attachment response status: " + checkHttpStatus);
        var existingAttachments = JSON.parse(checkResponseBody).result;
        var existingAttachmentNames = [];

        for (var i = 0; i < existingAttachments.length; i++) {
            if (existingAttachments[i].table_sys_id == current.sys_id.toString()) {
                existingAttachmentNames.push(existingAttachments[i].file_name);
            }
        }

        // Send New Attachments
        var parser = new JSONParser();
        var parsed = parser.parse(responseBody);
        var targetRec = parsed.result;
        var attachmentCount = sendAttachments(current.getTableName(), current.sys_id, targetRec.sys_id, existingAttachmentNames);
        if (attachmentCount.length > 0) {
            attachmentMsg = " Attachments successfully sent: " + attachmentCount[0] + ". Attachments failed to be sent: " + attachmentCount[1];
        } else {
            attachmentMsg = " Record had no new attachments to send.";
        }
    } else {
        gs.addInfoMessage('Failed');
    }
and After this call your function "sendAttachments".

I hope that should work
--------------------------------------------------------------------------------------------------------------------------


If you found my response helpful, I would greatly appreciate it if you could mark it as "Accepted Solution" and "Helpful."
Your support not only benefits the community but also encourages me to continue assisting. Thank you so much!

Thanks and Regards
Ravi Gaurav | ServiceNow MVP 2025,2024 | ServiceNow Practice Lead | Solution Architect
CGI
M.Tech in Data Science & AI

 YouTube: https://www.youtube.com/@learnservicenowwithravi
 LinkedIn: https://www.linkedin.com/in/ravi-gaurav-a67542aa/