- Post History
- Subscribe to RSS Feed
- Mark as New
- Mark as Read
- Bookmark
- Subscribe
- Printer Friendly Page
- Report Inappropriate Content
on ‎03-27-2017 12:49 PM
Whether you are creating your first or 100th angular2 application, environment setup couldn't be easier. Javascript development in 2017 can be a confusing thing. There are enough frontend frameworks alone to make your head spin. Then you have ECMA5, ECMA2016, TypeScript, etc. There are tools like gulp, bower, grunt, npm, systemJS, webpack, and the list goes on.
Luckily, with Angular2, there is an official angular command line tool that will help setup, develop, test, build, and (with a few tweaks) even deploy to our ServiceNow instance. Don't be afraid of the phrase "command line tool", I'll walk you through all of the commands you need to run to achieve our goal. But first, let's setup our development environment. We will need a few things:
- NodeJS (and npm)
- Angular-cli
- git
- An editor (My favorite is SublimeText, but if you fancy a free option, then Atom (http://atom.io) comes in a close second).
- A browser (if you are reading this, then I assume you already have a browser)
Let's start by making sure we have NodeJS and npm installed. Open up a terminal on your local machine and type node -v if you get a response indicating that the command isn't found or the file doesn't exist, then you should install it otherwise this indicates what version of node you are running. For Mac and Windows users, you can run over to nodejs.org to download the installer. If you have Linux, then I assume you already know how to install it or you are good at using Google which I recommend you put those skills to use. Likewise, run the command npm -v to determine if you have npm installed. If you have Mac of Windows, the installers generally treat this as a packaged deal and you get a 2 for 1 thing.
Note: For the rest of this article I am going to assume you have node 6.10.0 or greater and npm 3.10.10 or greater. If you have old versions, you should probably update (another awesome (not!) side effect of current day javascript development, release cycles are short and rapid causing you to update frequently).
Well now that we have npm and node installed and up to date, we can install our angular-cli tool. This little guy really is magical. He can setup a project, generate different parts of your app (components, interfaces, classes, services, etc), and he will also transpile and bundle (build) our application for us into a few handy little files.
So, open a terminal (or use an open one if you are like me and have 100 open terminals because you forget to close them) and type the command ng -v. Just like with node and npm, if you get a response indicating it can't be found, then you should install it. The installation command is universal across platforms which is npm install -g angular-cli. Yes, some of you linux users will need to issue that command as sudo. And BOOM! Done installing Angular-cli.
Note: I am running version 1.0.0-beta.28.3. Yes, it's still in beta…don't tell me how to live my life!
The last thing we will need to install is git. It's not 100% required, but it is highly recommended. You can get around using git by just downloading the zip files from github and unzipping them. You should just head on over to https://git-scm.com/ to download and install it to your machine.
I'm going to skip how to install a text editor and a browser on your machine. However, I will say, if you have SublimeText or another configurable editor (like Atom) then you should install a package for TypeScript support if it doesn't already support it. Angular2 applications are written in TypeScript, and it sounds far scarier than it really is. TypeScript is like regular javascript (at least what we will use it for), but with some syntactical sugar and type checking in the transpiler.
Ok, we should have all our tools installed and be ready to rock and roll at this point. So, let's get started!
First, clone the repo of our starter application https://github.com/nathangrove/ng2-snow.git with the command git clone https://github.com/nathangrove/ng2-snow.git snow-demo
Then we will want to setup the project and configure the tools. So, issue the command npm install to install all the dependencies. Followed by the command npm run setup to run through the configurator.
Lastly, we fire up the local development server. "Local?" you say? Yes! Local development server, because its fast and allows for automatic builds and reloads when a file is updated. So, to spin up the server issue the command npm run start. This command will start the server and setup the HTTP proxy.
The development server will proxy any requests with the relative url starting with "/api" to the ServiceNow instance provided during setup using BasicAuth with the credentials provided during setup. While you are developing, you should use the HttpClientService to make any http requests. During production, this library will grab the X-UserToken using jelly script and pass it on with the requests as a header.
After development, it is time to deploy. Simply issue the command npm run deploy this command will build the application and push it to the Scoped Application that was built during the setup. The deploy command will upload the files to ServiceNow using the table api. This step can be repeated as many times as necessary. Each deployment will overwrite the previous deployment. Sometimes the browser cache will need to be cleared between deployments, but this is more of a browser setting, so I won't go into detail on that.
That is it. Now you can quickly build top notch Angular2 applications for your ServiceNow instance.
- 11,114 Views
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
Nathan,
I followed this doc and have done everything contained within.
I am going to be in the workshop for this at KB17
I ran all the commands from my mac, how do I check my developer instance now?
It asked for an application name I used global and the following url was built
https://dev21926.service-now.com/x_79102_global_index.do
When I go to this link I am getting ng2snow home works! page.
Is that all I need at this point to be ready for the workshop?
Also I never used angular, so I am looking forward to this experience.
I opted to use "atom" so I will try and get familiar with that as well before the conference.
Thank you
Tricia
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
Tricia,
The tools were only made to work in scoped applications. So it created a new scoped application on your development instance with the name "x_79102_global". It's not going to hurt anything and it will work, but this is probably not what you were expecting. If things go into the real "global" scope, then each application could potentially overwrite each other unless you do your configurations manually.
It sounds like everything is working as it should and you are good to go!
See you there!
- Nathan
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
Yea, I should have named it something other than GLobal 🙂
Good yes it seem like I am all se then!
Looking forward to the workshop
Thank you
Tricia
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
At this point:
Then we will want to setup the project and configure the tools. So, issue the command npm install to install all the dependencies. Followed by the command npm run setup to run through the configurator.
Am I using my developer instance on Service Now?
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
You can use whatever instance of ServiceNow you would like the application to be installed on. If you are running through this as a pre-req for the Knowledge workshop, then (thank you for taking the time) yes, just go ahead and just use your personal dev instance. The main purpose of asking the attendees run through this is to setup the development environment on your computer before coming to the class. Getting NodeJS, npm, Angular-CLI, etc installed.
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
So, follow-up question.
Is it safe to assume we'll be using this angular cli that we're installing during the seminar at K17? I'm setting it up on a desktop at work, so I'll need to be prepared to VPN into my desktop from my laptop while at K17.
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
Yes. We will be using the environment we setup here in the workshop against a ServiceNow instance they will provide you for the workshop. VPN should suffice.
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
@Nathan -- This starter project is great! I'm wondering about how to make API calls so I can start making requests to my instance. Do you have any example code?
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
Hey David,
I created a branch of the repo for you to look at https://github.com/nathangrove/ng2-snow/tree/apiSample
Take a peek at the home component and you can see how I make a simple API call using the custom HttpClient. It will make authenticated calls with the credentials you gave it during setup while running locally and will auto'magically work with the logged in user when pushed to production.
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
This is awesome, thanks Nathan! Really wish I could attend your workshop but there's always next year!
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
ngrove@exegy.com First of all, hello from the other side of the State! Go Royals (I support the Cards when I'm in Bush Stadium). That aside. We are now post K17, in the past some of these workshops have made it out to the community. As a special request. Can we get this one out here on community too? I would love to be deploying Angular2 apps to SN. I know our organization would appreciate it. I have made data driven Angular Apps in SN using Web App Accelerator from share. However, utilizing the new architecture would be great!
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
Hey Christian,
Unfortunately, I don't think I'm allowed to give you the presentation or lab guide unless you attended the conference, I believe ServiceNow has IP rights to it. Here is the link to the information for the people that attended Angular2 applications for the ServiceNow platform .
Either way, the class wasn't much more than what is described in this document along with the example api call project mentioned earlier in a comment: https://github.com/nathangrove/ng2-snow/tree/apiSample
Sorry I can't be much more help but, let me know if you have any questions I can answer for you.
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
Hi Nathan and all,
I'm an Angular developer new to ServiceNow and, having used your starter ng-snow repo, I found the development experience great! That said, my team is more familiar with ServiceNow and would prefer to build Angular apps through the Service Portal because it is more 'configuration' friendly. I'm told that i will not have to develop as much in the ServicePortal because the ServicePortal makes use of pre-built forms, widgets (like the calendar), etc. I'm having a hard time accepting this because I don't like the ServicePortal's web based IDE tools or the decentralized app development (not having all the code in one place) - I'm afraid that even with the ServicePortal's pre-built items, the dev experience is so bad (hard to debug, etc) that it will actually take me much longer to develop something. Any advice in terms of pros and cons to each approach (ng-snow vs ServicePortal)? Is there some kind of hybrid approach (i know the ServicePortal uses Angular 1.x, but i still havent seen a way to download that code and run it locally as an app, like with ng-snow)? ServiceNow best practices?
Some other questions: I assume NG-Snow can only use web services (REST) for interacting with service now and not the client-side api (i think its called GlideScript?) since you run it locally first - if so, any gotchas (like big differences in the api methods)? I'm thinking specifically about querying user roles and permissions for showing and hiding content based on permission to the content...
Thanks for any advice!
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
Service Portal will land more opportunity, and can be supported by a wider audience.
However, there is the use case for completely custom solutions. Using Accelerator for Web Apps found on share can help bring it all in, and curb some of the pains with the decentralization. The links are below.
Accelerator for Web Apps - YouTube YouTube
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
Well, after working with the service portal for a bit, I'm going to have to disagree... not sure what 'landing more opportunity' means, but so far I'm finding the Service Portal interface very constraining, from a typical Angular development point of view. The benefit to the less experienced developers on the team is the drag and drop capabilities of widgets onto a page. This works well for very simple cases, but once a widget has a sub-widget, it breaks the model - you cant drag a widget into the template of another widget. Although you can code nested widgets, you've lost the drag and drop benefits already.
Far worse are the problems with routing (why doesn't this use the standard Angular router? - or better yet, UI-Router?) - Again, I can add the UI-Router library manually, but now I've. again, lost the Page-driven drag and drop widget benefits of the Service Portal. The widget IDE only works with local dependencies, not application dependencies - so if I add a filter or a service to the application, I cant access those things while developing in the widget IDE - once deployed, however, the widget has access to the global application and can then access my global filters and services. This makes developing in the IDE very difficult - and I haven't even mentioned that you cant debug in the widget IDE (not, console.log is not debugging - and nor is adding debugger statements - I should just be able to set my breakpoints without modifying my code). Also, it takes me about 15 minutes to add something as simple as an Angular Filter because I don't have direct access to the app.
So, after using the Service Portal, I would argue that while it may be a better approach for non-developers (or at least non-front-end developers), for anyone who plans to create a moderately complex angular application, the Service Portal interface is very constraining, buggy, and generally hard to code in.
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
Hey Joseph,
Sorry for the late reply. I agree, I do not particularly like the development IDE in ServiceNow. I actually wrote a Chrome extension called SNow-VIM to add the monokai theme and vim (yes, I still use vim) keymap to the editor. If you happen to be running Jakarta, you can use their server side debugger, it is nice, but unfortunately, my team cannot switch to Jakarta yet due to other bugs we've found in its REST API.
NG-Snow can use any webservice in or out of ServiceNow. I primarily use their REST Table API. I do occasionally write Scripted REST APIs, but maintaining them is annoying. The API methods are used the same way as with any other angular2 application.
You could certainly hide sections in the UI, however, just remember that the code does run in the user's browser. So it isn't a far fetched idea for a malicious guy to reverse engineer the code and discover how to make those portions visible, then you are relying on ACLs to keep your data secure on the server. I typically just make sure I do not include any sensitive information in my Angular applications.
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
I had to make two fixes to get it work on my SN Instance:
1. Deploy script wasn't working until upgrading the CLI to the newest version
2. UI Page was totally empty after changing content of index.html:
<link href="{{styles}}.cssdbx" rel="stylesheet" type="text/css/"> TO <link href="{{styles}}.cssdbx" rel="stylesheet" type="text/css/"/> <-- As you see the end closing tag was missing
-Ville
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
@Nathan, this is crazy-good! Do you have any plans to make this work with VueJS?
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
Thanks. No I do not really have plans to support VueJS. I don't use Vue in my daily development, so it would be hard for me to implement and keep up with (angular breaks it with almost every release). However, upon quick inspection, it would be pretty trivial to implement such support using vue-cli as the bundler. You would need to modify the "helper" scripts to create the right SNow records during setup and then modify the file uploader script.
It would be awesome if this project could turn into a generic SPA creator for ServiceNow, but I don't have the time to dedicate those resources at this point. I envision being able to pick your framework (if any) and then setup your project as your normally would. Feel free to fork or clone the repo and modify it. If you get it working with both frameworks, then submit a merge request and I'll happily merge it in!
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
This is really great. I am looking forward to try this out.
Have this been tested with the latest versions of Angular ?
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
So I just tried to run npm install but get erros related to python. The article does not mention the need for Python so I am not sure if I can ignore those error or need to install python ?
ng version:
Angular CLI: 6.0.8
Node: 11.11.0
OS: win32 x64
Angular: 6.0.7
... animations, common, compiler, compiler-cli, core, forms
... http, language-service, platform-browser
... platform-browser-dynamic, router
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
This just worked on my machine, no problem. The snow-helpers are written in nodejs so I'm not sure how you are getting an error message related to python. I do have an older version of Node:
Angular CLI: 6.0.8
Node: 8.11.1
OS: win32 ia32
Angular: 6.0.7
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
I guess I can just ignore the errors because after running setup and deploy I get a working app in my developer instance. This is so cool. I am attending Angular training in 3 weeks.
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
Although I am not 100% sure. I believe the angular-cli tool has a python dependency for certain features that this specific boilerplate doesn't use.
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
On a different pc I did not get the same error so not sure why it occurred. But regardless its a great tool to get started with Angular apps.
I have one suggestion. How about extending it to create a Service Portal widget ? So make a choice either deploy as UI Page or Deploy as SP Widget.
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
Nathan,
Thanks for this wonderful post. I have a question.
Do you have any idea how I can use GlideAjax instead of REST API? Because Table API call takes about 7 to 8 seconds to load the initial data, which is not acceptable for our users. I think GlideAjax can help better performance, but when I use it, Angular doesn't know about GlideAjax. How can I make GlideAjax known to Angular and use it for the initial load of data?
Thanks a lot in advance for your help.
Regards,
Bala
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
I made some improvements to the ui page to initiate the angular app.
First I changed the line getting the session token to use a more readable var name 😉
So it now looks like this:
<div style="display:none"><g:evaluate object="true">var sessiontoken=gs.getSession().getSessionToken();</g:evaluate></div>
Then I removed this line to avoid potential conflict with multiple sesssions:
<script>(function() { window['_g_ck']="$[g_ck]"; })()</script>
Instead I pass the token to the Angular app as a parameter to the directive like this:
<app-root token="$[sessiontoken]" table="$[sysparm_table]" sysid="$[sysparm_sysID]">Loading...</app-root>
Then in snow.interceptor.ts the token is fetched like this
let token = document.getElementsByTagName("app-root")[0].getAttribute("token");
This is a more clean way of passing parameters to the angular app rather than adding them to the window.
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
I have run into an issue.
I created a UI actio on incident that opnes the UI Page.
When I open an incident an click on the UI Action the Angular app is loaded correctly.
If I close the window and click again on the UI Action the Angular app is NOT loaded, instead I see the error "Uncaught error: Zone is already loaded"
If I use the next or previous UI Actions to move to another incident then the Angular app opens again normally when clicking on the UI Action to open it.
So a sort of cleanup is done when moving to another incident. How can I do the same when closing the UI Page window?
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
Hey Bala,
Sorry for the late response. Not sure if I didn't get a notification for this post or what. I do not know of a way to get the GlideAjax library to play nicely. Last time I tried including it with angular, they did not appreciate each others presence. I'm sure that with time and maybe some scoping magic, it would be possible to incorporate the 2 on the same page. If you find a solution, please let us know.
- Nathan
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
That's a great idea! Can you make modifications to a repo and submit a pull request on GitHub? Then you get proper credit on GitHub for it.
Thanks for the improvement!
- Nathan
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
what does the code for you UI Action look like?
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
function run() {
var sysId = typeof rowSysId == 'undefined' ? gel('sys_uniqueValue').value : rowSysId;
var gDialog = new GlideModal('x_80603_testng_index');
gDialog.setSize(1400,400);
gDialog.setPreference('sysparm_sysID', sysId);
gDialog.setPreference('sysparm_table', g_form.getTableName());
gDialog.setTitle('Angular App');
gDialog.render();
}
I have found a workaround, not very good so still interested if this can be solved in a better way. For now I hide the close button on the dialog window with this in the client script
$('x_80603_testng_index_closemodal').hide();
And then add a function to call to close the wndow which runs this
GlideDialogWindow.get().destroy();
window.location.reload();
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
Nathan, another question. I will figure this out eventually but do you have any hints on what I need to change in order to add a new file to upload for the client script? I would like to have all the code in the solution.
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
Will do eventually 🙂
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
I know page reloads suck, but if it works and its acceptable to the app's stakeholders. Then...
However, if you wanted to look further into fixing it..here are two possible leads.
I think it has to do with the way Angular bootstraps the app. Removing the elements from the DOM doesn't remove the app from running in memory. You will probably need to write a custom bootstrapper function for the app to detect when its DOM selection element comes back on the page and then bootstrap itself to it.
OR
It looks like you might be able to remove the last line in pollyfills.ts that loads in zone.js. I'm not an angular expert, so I don't know all of the implications of this. Resource: https://github.com/angular/zone.js/issues/405
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
snow-helpers/uploader.js is the script that handles file uploading to ServiceNow. It works in conjunction with the data stored in the snow.conf.json file. It's not exactly dynamic...in fact...its pretty hard coded. You will need to add an entry into the snow.conf.json "files" object with the record's sys_id in ServiceNow and then modify the uploader.js script accordingly.
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
I tried the solution of removing the zone from pollyfills but that results in the angular app never loading even the first time.
The first option I do not know what that involves.
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
Thank you, I was on the right path 🙂
I appriciate the help 🙂
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
Hi Nathan,
I've got another question.
The main.js file is becoming bigger and bigger for us, anfd now it's not possible to store it in a UI Script anymore.
Is there any way to store the JS file within ServiceNow itself and include it in the UI page? I looked at the "Upload file " option, but it allows only xml files. Thanks in advance for your reply.
Regards,
Bala
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
If you can figure out how to generate the main file in smaller bits then you can modify the uploader.js and snow.conf.json to upload more files which you then include it in the html. Today I have just added two extra files to upload so it is possible.
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
you won’t be able to host the code which size is greater than 1.3MB. If that’s the case, then you need to serve it in a different way. You may store the file as a regular attachment in ServiceNow and then reference it like this:
https://<instance-name>/sys_attachment.do?sys_id=<attachment_sys_id>