RXJS subscription management in Angular

If you’re reading this then you’re probably familiar with the fact that Angular uses RxJS and embraces the reactive paradigm. You might be familiar that RxJS is based on the Observable class. Let’s recap what this means.
 
To extract any information from an Observable we need to subscribe to it. A subscription is a bunch of optional callback functions. We can define a success, an error function and a completed function, all of them optional. When an Observable emits, RxJS invokes the proper callback function.
 
Subscriptions aren’t free though, you’re required to tell RxJS when you’re done with them. It’s pretty easy, you need to invoke their unsubscribe function. The problem is – when and how to do that?

Not unsubscribing

 The easiest – and worst – solution is to ignore the problem. Subscribe to an Observable and leave it at that. When Angular destroys your component the open subscription will simply leak it.
 
Your subscriptions are holding a reference to the hosting component. If you don’t unsubscribe then you’ll create a memory leak with your whole component.

Manual subscription management

Let’s take a step in the right direction. Usually you’ll set up your observables in the ngOnInit lifecycle hook. There’s a corresponding hook when your component is destroyed, called ngOnDestroy. By simply storing all your subscriptions as members of your component class you can just call unsubscribe on all of them in the destroy hook.
 
 
This is a solution to the problem, but not a great one. For simple components it might work. But when you are adding more subscriptions later, you might forget to unsubscribe from them. And let’s face it, we just copying and pasting the code lines in cases like this, and will forget to change the variable name eventually.

Semi-automatic management with takeUntil

 We can harness the power of hot observables, aka Subjects. The logic is the same as when you’re using manual management. The difference is that you create a subject. In every observable subscription you pipe your subject through the takeUntil operator.
 
You also create an ngOnDestroy hook and complete your subject there. This will unsubscribe from your observables.
 
 
There’s a slight catch though. Order matters when piping operators, and you generally want to put takeUntil to the very end. The actual reasons are beyond the scope of this post, refer to this article on Angular in Depth.

Using the async pipe

 My personal favourite is to delegate the subscription management to Angular. This results in much less code and very straightforward components. Angular has the built-in async pipe for consuming observables. You’d use them in your component template.
 
 
Notice how all the subscription boilerplate code is gone. That’s a great thing, we need to maintain less code!
 
Also, when your component is destroyed Angular automatically unsubscribes from your observables. Though there are some caveats you should look out for.
 
If you use an async pipe multiple times on the same observable you’d get a different subscription. This could lead to multiple API calls. Fixing this will be the subject – pun intended – of my next post.

Source code

I’m maintaining and developing a repo on GitHub. It contains Angular7 best practices. Follow this link to the relevant part of the code.

 

Advertisements

Letting others fail

In the last couple of months I started to shift my attention from coding to making sure the team works properly. This of course brings lots of challenges and frustrations – but also you learn a lot about yourself.

One area it hit me very hard is mentoring people. I always did it, even at my first gig I trained and coached people in C# stuff. But boy I did it horribly wrong.

Continue reading “Letting others fail”

Building an iBeacon-based app

I spent a big chunk of my free time in the last couple of months to build an iOS app. The app’s primary feature is to connect with people who are in your close (close as in Bluetooth) range. Here’s what I’ve learned in the process.

Handling permissions – your users will see lots of dialogs

Running anything in the background in iOS is painful. From Apple’s point of view this is perfectly reasonable – they don’t want you to drain their devices’ precious battery. On the other hand the UX is terrible. You’ll only get one shot to convince your users to give you the desired permission. If they don’t do it then comes the “leave the app and change the settings” scenario. Instant churn.

The Location Services background permission is a special case. Apple will constantly ask the user in random intervals if they are aware that your app does location scans in the background. This can quickly lead your users to disable it as it was some kind of malware.

Then there are some badly worded system dialogs – my favorite is the “Turn on Bluetooth” dialog which has two buttons: OK and Settings. You’d assume that the OK button would turn on Bluetooth but it just closes the dialog. It’s really nice since users generally don’t read these at all, just bluntly hit OK and expect the problem to go away.

The background settings are brittle at best. There’s an app level permission, and there’s a permission for the whole system (parental lock excluded). It again makes sense from the user’s side, but from the app’s side it’s disastrous. The API calls will just return that there’s no required permission to run, but they won’t tell you why. It’s quite hard to guide the user through the problem if you don’t know the cause.

BLE is special

In a bad way. First there’s no way to tell if the device Bluetooth is turned off, or is not supported at all (aka iPhone 4). Now I lied, you can deduce this with checking various constants, but if you’d like to do this cleanly using the API you’re doomed.

Then there’s the plist fun when you need to add the keys to support background Bluetooth running. You can also have a lot of fun with events not firing, or firing with a huge (40 secs) of latency. In a real time app like mine, this is a huge deal.

Broadcasting iBeacons in the background – confusion overload

The short answer is that it’s impossible. You will only be able to broadcast iBeacons when your app is in the foreground. The problem is that there are tons of resources (mostly stackoverflow users in despair) who claim otherwise or offer creative ways around the problem. But nothing works. What works is a UX which rewards the user for opening and engaging with the app. Forget everything else.

Background Bluetooth scanning – even more confusion

Ranging or geofencing (region entering and leaving)? What constitutes a region? What can I do in the background?

I was really confused at first. Region entering can run in the background, but with a limited set of regions (I remember 20 for the whole device). Ranging cannot run when you’re in the background. The problem is when you use iBeacons you’d like to identify them (major/minor anyone?). Region entering won’t do this for you, you’ll need ranging.

But a little creativity goes a long way. Entering a region will wake up your app and you’ll have 5 seconds to do what you need. Now you can use these 5 seconds for ranging, since you’re not in the background anymore. Problem solved.

So what’s the conclusion?

If I were to start again this app I’d do it on Android. I finished it because the emotional investment was huge. On iOS you’d get seriously hindered functionality when you try to be creative with iBeacons. They seem to be a perfect fit for indoor navigation but when you try to do something different you’d hit into way too much barriers.

Oh, the app is waiting for review right now. I’m very interested to see if Apple approves it. I’ll post about it when it’s done.

Draw binary image to the HTML5 canvas

Recently I tried to draw some binary image data to the canvas. The image data was in a Uint8Array but it was already compressed, so no raw RGB.

You see the canvas context has some convenience functions working with binary data, like putImageData. Normally you would use it like this:

Be warned though that putImageData only works with RGB values, not an already compressed image, like a JPEG or PNG file data.

There are two courses of action here:

  1. Uncompress the image array
  2. Convert the array to a data URL

I’d go with the second option. There are two ways to do this as well. First you could manually encode the image data to base64 and append the proper data URL prefix for it, like this:

Alternatively you could use a blob and the createObjectURL function. Sadly these are experimental stuff and I haven’t been able to make it work yet. However the code is a bit cleaner and should be more efficient. It should look like this:

I really hope that there will be support for this later on. Of course you can always just point your image’s src to your image somewhere on your server. However there are cases where this approach is not viable (such as mine was).

Setting up your environment for JavaScript development – Part I

In this post we’ll go through the details of how to get started with JavaScript development on a Windows machine. We’ll cover the following stuff:

  1. Upgrade your command line
  2. Install Node.JS and NPM
  3. Install Git
  4. Install Bower
  5. Making your life easier by adding these to your PATH

1. Upgrade your command line

When you’re doing modern JS development you’ll spend lots of time at the command line. You will constantly need to run stuff like acquiring packages, unit tests, minification and the rest.

The Windows command line is capable of doing the job, you’re better off with a more advanced solution. I would recommend using ConEmu which is a great substitution of cmd. It can handle multiple tabs which is quite a life saver. Of course there are lot more features, be sure to check it out.

2. Install Node.JS and NPM

Although I won’t write much about Node.JS we will be using its packet manager NPM. The two are linked together in one download. Go over to the download page of Node.JS and get the proper version.

After the installation go to your %APPDATA% folder. If everything is set up properly you should see an npm folder there (the whole path is supposed to be Users/username/AppData/Roaming/npm). Add this npm folder to your PATH variable.

3. Install Git

Git is a distributed version control system which is pretty popular. Since lots of people are using it and most JS packages are maintained in git repos on GitHub we’ll be using it as well.

You can download git from Git-scm.com or just the GitHub client for Windows. Either way, make sure that git.exe is in your PATH.

After git is installed you can test it by just typing git in your console and see the help page emerge. Be sure to do this before you proceed, since Bower will be using git internally.

4. Install Bower

Bower is a package manager for client-side web development stuff. Although you’ll find lots of packages in NPM as well it is mainly intended to be used with Node.JS. To install Bower we will use NPM. Open up a command line and type the following command:

npm install -g bower

You might figure it out that this command installs Bower to your system. It’s very important to use the -g switch which means that the package is installed globally. It will be placed to the npm folder you just added to your PATH so you’ll be able to work with Bower ASAP.

To test if everything is working properly create a new folder somewhere, point your console to that folder and issue the following:

bower install jquery

If everything went well you should see a newly generated folder bower_components and within it the latest version of jQuery. But using Bower this way is not leveraging its full potential. You would get the packages but would not get the mobility.

You need to configure Bower by adding a bower.json file to your project root. This file will contain some information about your project, and all the packages that Bower needs to use. You can generate it using the

bower init

command. Don’t worry if you don’t understand something, just hit enter and Bower will use reasonable defaults.

The main point of interest in a bower.json file is the list of dependencies. There are two main types – normal and dev dependencies. Normal dependencies are everything that your final product uses and requires to function. Like jQuery or Bootstrap. Dev dependencies are stuff that you need to develop your application but the app doesn’t depend on them. Like Jasmine and Karma for unit testing.

You don’t need to edit your bower.json file by hand every time you add a new dependency. There are two switches that update this file. If you are adding a normal dependency then use the –save switch:

bower install jquery-ui --save

If you are adding a dev dependency then use the –save-dev switch:

bower install qunit --save-dev

Conclusion

Now you have a solid setup with all the necessary tools to start working on your project. Although we’re far from finished – part 2 will cover Grunt, the JS task runner, and part 3 will deal with the extensive options of unit testing JS code. Stay tuned!

Starting Steps for “Real” JavaScript Development

JavaScript is a misunderstood little language. It seems easy to get into and people with extensive background in other languages think they can deal with it smoothly. I know this firsthand because I was one of those people until I had to work on my first JS project.

I won’t be lying to you that stuff came to be an abomination. It was relatively simple stuff. We needed some dialog with a searchable tree inside it and some extra features I don’t really remember. Well I worked, sweat and delivered. The result was your typical thousand lines long unmaintainable ball of spaghetti covered in mud and crap. But it worked so that was nice.

Since then I spent a lot of time figuring out how to do JS properly. I even gave a presentation about it which pretty much shared the characteristics of my first JS project. I’m not a talker guy and it showed. Anyway I learned a lot by myself and had even better guidance from people vastly more knowledgable than me. So I present some action items to you so you don’t have to learn them the hard way.

Step 1 – Modularize

This is perhaps the most important thing. If you ever attempt to write maintainable JS code you need to split your stuff into smaller files. Don’t write all your code into a single file. Also don’t mix HTML and JS in one file, use references.

You should also keep your files short. One hundred lines should be enough for most use cases. You can even use a JS dependency manager, like RequireJS.

There is also a host of patterns on JS modularisation. I’d point out to the Asynchronous Module Definition or if you wouldn’t want it to formal, just using the Revealing Module Pattern.

Step 2 – Test

There are volumes of literature written about testing – especially unit testing – code. JS given its dynamic nature provides enormous flexibility – and the same breadth of errors. Since there’s no compilation with type checking you can easily invoke function which doesn’t exist causing a runtime error.

This is my favourite kind of error I use to make – writing the function getParameterByName and then trying to invoke getParamByKey in other places. Tests are great to catch this. And also a lot of other errors.

And be sure to actually run those tests. There are great unit testing tools in JS like Karma, a test runner, Jasmine or QUnit, unit testing frameworks. There’s also the great browser PhantomJS which is written for JS testing and automation.

Step 3 – Analyse your code

There are numerous best practices and anti patterns in JS accumulated over the years. Some of these can be validated by other code, called a static analyser. Do yourself a favour and use one. I’d recommend JSHint for this purpose. It’s pretty strict by default, but you can obviously fine-tune its behaviour.

Basically all it does is that it goes over your code and checks if you do something in a less than ideal way. Like not declaring variables or using undefined functions by mistake.

Step 4 – Use a package manager

Much has been written in JS and much is being written in this very moment as well. Sure you can write it better but you don’t have to. You should be focusing on providing value for whoever you write that code for.

So use what is already there if it fits. To do that, you can use Bower, a package manager for client-side JS. The usage is easy, you just type bower install this_awesome_package and Bower takes care of resolving and storing the files.

You just need to push the configuration file to source control, so that others can download the same packages with Bower, without requiring to keep lots of third party code in your repository.

Step 5 – Use a task runner

You don’t want to do all common tasks by hand (unit testing, running JSHint, minifying your code, etc). Everybody hates these recurring and menial tasks, so let your machine do them for you.

Get Grunt, a task runner for JS. You’ll find tons on predefined tasks (like running your Jasmine tests with Karma on a PhantomJS browser outputting coverage data) and you save precious time where you can create value instead of getting frustrated with your toolset.

Step 6 – Use source control

Seriously this shouldn’t even be a step. Setting up a git repo is super simple, so you should have one. And if you don’t like git there are tons of other alternatives, most of them free.

Step 7 – Have a build process

This is obviously more advanced stuff, but a proper build process is a must have when there are other people working on your codebase. I would argue that even if you’re just by yourself you would benefit from running a build every time you commit code.

Your build process should validate your JS code (a la JSHint), run your tests and publish the result to some place where you can check it for yourself.

A Stack Change

In the not so distant past I was assigned to a very interesting HTML5 / JavaScript project. I used to say that I’m familiar with JS and I even add it to my resume with a modest years of experience number. Needles to say that as soon as I had to dive deeper into the JS world my confidence vanished away.

On the other hand I learned tons of new stuff. I can only compare the current knowledge gaining to the very beginning of my career, when I started to learn C# and ASP.NET.

The reason I write this post is twofold. First, I want to propagate the idea of abandoning your well-known technology stack for a while to learn something entirely different. I believe there’s succinct and fundamental diversities between the C# and the JS world. It successfully moved me out from being stuck in a warm and fuzzy world with little uncertainty. It also opened lots of new opportunities.

The other reason is that I plan to write some follow up posts on the more intricate stuff that was quite a pain to figure out in the current cutting edge JS stack. To name a few, I got the chance to work with AngularJS, RequireJS, Node, NPM, Bower, Grunt, Karma, Jasmine, etc. I also had the opportunity to get into a more intimate relationship with functional programming practices and JS per se.

Brace yourselves, complete stack change is coming.