Harrington Web

Build your own expectation library.

Monday, February 13, 2017
In the world of impending deadlines, testing is a key a vital role with any project. When building software you can test many functions and processes in a matter of minutes depending on how you setup your tests and how well the code was written to be testable. A key element for that tests is what you expect. Javascript for example, there are many expectation frameworks out there. Jasmine, Chai, Mocha to name a few. Let's build a simple expectation without their input.
var expect = function(obj) {
  return {}
}
This will be our starting point for what we will expect. Very simply it is a function that will accept an argument obj and then it returns some object back that will be defined in more detail soon. You may be thinking one object? That doesn't seem quite right. For an expect statement to work shouldn't we have something like "expect(a, b, 'equal')". Yes, we could do something like that. However, for this example, we will attempt to make the code read like a sentence. For example "expect(a).to.beEqual(b)". For this to work, we will create a singleton class out of the object that gets returned. The first item we will need is what value that we are wanting to test. This can be our expectation.
var expect = function(obj) {
  return {
    "expectation": obj  
  }
}
Once we have that value we need to create an object "to". This is really just for readability and organization.
var expect = function(obj) {
  return {
    "expectation": obj,
    "to": {}  
  }
}
Lastly, we need to create a function with the "to" object called beEqual(val).
var expect = function(obj) {
  return {
    "expectation": obj,
    "to": {
      "beEqual": function(val) {}
    }  
  }
}
At this point, you can run your expect statement and no matter what you put into it, the statement will pass. Depending on your test framework and how you use it this can be a real problem. The issue on this one is that we have not written any code to cause a failure yet. However as a reminder when you write your tests make sure that they will actually fail for the right reason. Tests that always pass are not necessarily useful. Hopping off the soap box and back into beEqual. In this function, we want to do 2 main things. The first is to check if the value in beEqual(val) is equal to the obj in the expect statement. The second is what to do if it is or is not equal. If they are equal we want to return true. If the answer turns out to be false, we want to throw an error and probably return some kind of message about why it failed as well.
var expect = function(obj) {
  return {
    "expectation": obj,
    "to": {
      "beEqual": function(val) {
        if (obj === val) {
          return true;
        } else {
          throw "Expected: " + val + " Got: " + obj;
        }
      }
    }  
  }
}
Congratulations you now have a very simplistic expectation framework that you can add too and modify to your hearts desire. There are many more opportunities to explore in this area. If you are new to coding etc, I suggest try writing a few more matchers that you can expect. Some examples toBeGreater, toBeLess, or maybe add a "not" object in there somewhere. Where ever it takes you I hope it ends up with better more solid code.

No comments :

Post a Comment