1

I'm working on a project that consumes Service Now API (Rest). To do so our client has registered us as a user in order to login and make all service calls we need to. This project has an interface where users can login once they have an account on Service Now as well, the username they type to log in has nothing to do with service now by the way, but later they associate theirs service now users to it. They can do some operations through this interface, where all of them are done using the integration user/pass not their service now users themselves, even because they do not need to share their passwords with us. But it's needed to track the correct user to register on service now and I'm in trouble specifically about commenting on an incident.

The endpoint to comment is the following:

http://hostname/api/now/table/incident/{sys_id}

where the request body is a JSON object just as simple as:

{
"comments": "My comment is foo bar"
}

but when this comment is registered on Service Now it is under integration user instead the user which commented. Is there any way I could keep a specific user, considering I already have the user id on Service Now ready to inform it on the request the way it should be. I tried reading Service Now documentation but had no clue how to solve it, altought I've found something about impersonate

TylerH
  • 20,799
  • 66
  • 75
  • 101
Leonardo Lana
  • 590
  • 1
  • 4
  • 13

2 Answers2

1

Firstly, you need an integration user with sufficient rights. Our integration user has sufficient rights out of the box, but your story could be different. A quick check is to try impersonate as other user using menu.

  1. Login as integration user to ServiceNow instance.
  2. Go to https://{instance}.service-now.com/nav_to.do
  3. Click on username at top right corner. This is a drop down.
  4. There should be at least three menu items: "Profile", "Impersonate User", and "Logout". If you do not have "Impersonate User" in this menu, your integration user miss some permissions. Contact system administrator if you miss this menu item to configure appropriate permissions.

Then you need to find sys_id of user that you want to impersonate. For example:

https://{instance}.service-now.com/api/now/table/sys_user?sysparm_query=user_name={username}&sysparm_fields=sys_id

If you have sufficient privileges, you could invoke the following endpoint with the sys id of user that you want to impersonate:

  • HTTP POST to https://{instance}.service-now.com/api/now/ui/impersonate/{user_sys_id} with body "{}" and content type "application/json". You need to provide HTTP basic authentication to this query as your integration user.

The response code on success is 200. The response body could be ignored. The interesting result of this response is a set of cookies for impersonated user in response headers. These cookies could be used for subsequent REST API calls until they expire. Use some HTTP rest client dependent method to capture them and to provide them to next calls.

For Apache HTTP Client (Java), I'm creating http client context using:

HttpClientContext context = HttpClientContext.create();
context.setCookieStore(new BasicCookieStore());

Pass thing context to impersonation request and to subsequent API calls until I get 401 reply, after that I'm reacquiring cookies. Setting new cookie store is important, as otherwise some default cookies store is used.

Two things to note:

  • This API looks like internal one, so it could change at any time. If it happens, look for what "Impersonate User" menu item does, and repeat it yourselves.
  • ServiceNow permissions are quite fine-grained, so the target user could lack permissions to perform operation. In some cases, if there is no permission to update the field the operation PATCH on object returns response 200, but field is not updated. This introduces a surprising mode of failure when you use impersonation.
TylerH
  • 20,799
  • 66
  • 75
  • 101
user1936595
  • 519
  • 4
  • 5
0

This is happening because you're being proxied through the "Integration User" instead of your own account. As long as this is the case, your comments are going to be attributed to the Integration User.

I can think of two ways to fix this issue.

  1. Ask the client to log you into their system directly as a user.

  2. Implement a special API (Scripted REST API, available in Geneva or later) that allows you to identify the Incident and enter the comment, and then the script forges the comment on your behalf, attributing authorship correctly.

The first solution can be expensive due to possible additional licensing costs.

The second solution will require a willing client to devote 2-3 hours of development time, depending on the programmer.

  • Thanks for answering. First option is not possible once user cannot input its password. The second option seems fine, a customization of ServiceNow API, right? That could work but the idea is: our application must be able to connect to many service now instances, from different clients, interoperability is something we are supposed to maintain, sometimes we won't be able to customize it – Leonardo Lana Dec 26 '16 at 19:32
  • If you're unable to customize your clients' ServiceNow instances, then you'll be unable to change the sys_created_by field in any journal records when making comments. The sys_created_by field records the identity of the person logged in, and it is assumed to be the same as the author. You're trying to tell the system that the person logged in is _different_ than the author. You _can_ manipulate the sys_created_by field, but you'd need to somehow gain write access to the record within ServiceNow. That would require a custom script via Scripted REST API or Business Rule or something similar. – Dan Schaefer Dec 29 '16 at 13:59
  • BTW: You mentioned something about impersonation. Indeed, you _can_ impersonate someone and leave a comment, assuming that the person you're impersonating has sufficient privilege to access the Incident records and leave comments. The problem is that it requires you to have admin privileges on the ServiceNow instance; something that I suspect your clients will not grant. – Dan Schaefer Dec 29 '16 at 14:10