Menu iconMenu

This is the second in a multi-part series looking at custom Ember Blueprints.  In part one we built an Ember Blueprint to generate read, edit and create form pages for an Ember Model, based around its attributes.  At the end, we’d got a working blueprint.  However, we didn’t test it, and it was only really useful within the project we authored it.

This second part is going to start and address those issues.

Now, I’ve got some good news and some bad news: the bad news is, if you’re not familiar with Ember, Ember Add-Ons, and Ember Blueprints then there is a lot of information in here.  In addition, we’re going to be heading into some choppy, un-documented waters.

But don’t worry, I’ve made this post as accessible as possible and dropped in a number of support links throughout.  Go as slow or fast as you like.  Read it twice.  Scan it to get a feel and then park it for reference later. It’s your content now, and I won’t be offended if you decide to leave. Much.

Follow Along At Home

The completed add-on for this blog post can be found on Github here:

https://github.com/mediasuitenz/mediasuite-ember-blueprints/tree/addon-blueprint

At the end of each section where I’ve made a commit, I’ll include a link.

Creating Our Add-On

Ember Add-Ons are created just like Ember Applications, by using the Ember CLI.  In this case the command ember addon <add-on-name> will create a folder <add-on-name>  and add all of the required files to get started.  To create the add-on in the current directory then simply ember addon <add-on-name> --directory ..

An outline of the Add-On project structure can be found here:

https://ember-cli.com/extending/#addon-project-structure

However, the blueprint  folder isn’t automatically created for you, as it’s only required if your add-on is going to provide Blueprints.  This one definitely is, so we’re going to need that folder.

The content for our Blueprint was already created in the last blog post, and exists in the my-first-blueprint  branch.  Fortunately, Git never ceases to amaze me, and there is a command for copying a folder from one branch to another.  Well, of course there is…

It also requires a simple npm install --save string  which is used by the Blueprint’s index.js when processing the generate request.

Git Commit:

https://github.com/mediasuitenz/mediasuite-ember-blueprints/commit/2b95cdf4ae7ea0f680a96ea7a2a7744cc5be3f63

And with that, our Add-On should be ready to be imported into another Ember project.  It’s easily tested.

Oddly enough, despite throwing an error, this is good news.  This simply indicates we don’t have a model config for the person  model, which is very true.

The other warning that we received isn’t relevant to this project, but if you’re curious it’s related to this issue: https://github.com/ember-cli/ember-cli/issues/6219

Testing

So now we’ve proven the Blueprint is installable to other projects, we need to ensure it’s working correctly.  For that we need some tests.

Testing Blueprints is not a well documented process, so let’s break down what we’d like to do:

  • Create a test instance of an Ember application.
  • Generate our model-crud Blueprint from a known Ember Model config into the test instance of the Ember application.
  • Run functionality tests against the test application to check the output of the Blueprint works as we hope.
  • Tidy up, so we can repeat this test at will as we make updates to the Blueprint.

The Ember eco-system is chock-full of great add-ons, and in fact there is one to help with testing Blueprints – https://github.com/ember-cli/ember-cli-blueprint-test-helpers.

Ember-cli-blueprint-test-helpers

Once you have ember install ember-cli-blueprint-test-helpers  within your project, you can use the ember generate blueprint-test my-blueprint  command to generate the outline of a blueprint test.

The outline test exists in node-tests/my-blueprint-test.js , which roughly does the following when executed:

  • Creates a temporary folder within the project and initializes a bare-bones Ember project inside it.  No NPM or Bower modules are installed.
  • The Blueprint under test is generated within this temp Ember project.
  • There is now an opportunity in the code to run some synchronous tests to ensure the files are in the correct location and they contain appropriate text.
  • The Blueprint under test is then destroyed.
  • Another opportunity to check that the files were removed correctly

That looks awesome, so let’s start there.

Ember-cli-blueprint-test-helpers

First off we need to install these into our project and generate our test harness.

This makes a number of minor changes, including to the package.json  to add a test execution command,  and drops a test harness file into the project:

If we follow that up by trying to now test:

Then we get a bunch of errors!  But again, this is actually good news.  Notice the test is running, and the Blueprint is failing to generate code because it can’t find the foo.form.json  config file within the test Ember application.

That’s okay!  We still haven’t got around to setting up any of test fixture files at all yet.  We’ll do that shortly, but first, we’ve got a big problem here that can’t be put off.

Git commit:

https://github.com/mediasuitenz/mediasuite-ember-blueprints/commit/078d04a45baf92b951d6b44d493ced63e612e6d3

Houston, We Have a Problem

Ember-cli-blueprint-test-helpers is our friend, but it doesn’t work quite the way we’d like out of the box.  By default, it spins up an Ember app, generates from the Blueprint, and allows rudimentary ‘did you generate in the right place with the right content’-type tests.  We’re looking to go one, or maybe several, steps further.  Not only do we want to generate from the Blueprint, but then launch the Ember app and execute Ember tests against the running instance.

This is where things start to get hairy.  I should also take this moment to thank Tobias Bieniek (@simplabs) – one of the main authors of the add-on – for taking some time to discuss this with me.  The Ember community is a great place, and no small reason why we love the framework.

The good news is: what we want to do is possible.

The bad news: to work it out, I had to spend a lot of time spelunking through the add-on’s source code.

The good news again: you don’t have to.

Let’s look at the key piece of the original model-test-crud.js  code:

It’s a beautiful, succinct thing, but we really need something more like:

Let’s take each of those steps in turn.

Set-up Test Fixture Data

Because at heart I’m a traditionalist, let’s go with Books and Authors.  Therefore, we’ll create a Book Model with a:

  • title (string)
  • Synopsis (string)
  • rating (number)
  • author (belongsTo Author)

The Author simply has:

  • name (string)
  • dateOfBirth (date)   

And a config file for the Book which we’ll use to build the form.  

There is a tests/dummy  folder in our project structure already which contains the structure of an Ember application.  Normally it’s used for testing Add-ons, but we can use it for storing our fixture data.

As our Blueprint doesn’t yet update the router.js  file, we’ll add that into the tests/dummy/app  folder as well with the known content:

Copy Our Fixture data

Now we have our fixture data, we need copy it into the correct place in the temporary Ember application under test.  Node has a couple of different ways to copy files, but we’re going to be copying whole folders, and for that we can use the package fs-extra .  

Our code so far now looks like this:

The tricky bit here is understanding that the setupTestHooks , amongst other things, creates the temporary folder and then moves the process’ working directory to that location.  There’s a few hours of my life I’m never getting back.

To see the full code, look at model-crud-test.js  here:

https://github.com/mediasuitenz/mediasuite-ember-blueprints/commit/33c7d9091887ffa5d7a3b53a47b9922b9c907726

Taking Stock

We’ve covered a lot here, and it’s time to take a breather.

The great way that the ember-cli-blueprint-test-helpers have been authored allows us to do exactly what we need by just scratching below the surface.  It’s a bit disappointing this isn’t more natively supported in Ember, but maybe it’s just an opportunity for the community to step into the breach.

Next time we’ll complete the testing framework, and then follow up with actually executing some useful tests.  It’s a lot of work, but re-usable once we’ve done it.

 

Ember Blueprints: why they’re awesome

Brit-turned-Queenstowner and keen coder Jonathan on why he's a fan of Ember Blueprints. Note: This is part one of a. . . (yet-to-be-decided-how-many-parts) series on this subject.
Jonathan H Posted by Jonathan H on 11 August, 2017

A Day in the Life of an Ember Concurrency Task…

Media Suite's itinerant American developer explores one of the nuances of ember-concurrency.
Patrick Posted by Patrick on 19 October, 2016

Managing Relations in Ember Data with JSON API

From his villa in beautiful Bali, our nomad developer Patrick weighs in on this technical issue. He even provides demo-code.
Patrick Posted by Patrick on 18 August, 2017
Comments Comments
Add comment

Leave a Reply

Your email address will not be published.