Series: Making ember-cli Addons

Making Addons Extensible

Published on Mar 30, 2016

This video shows a common pattern for making your addon easier to use and customize. Don't publish without it!


Links

Code

Move the old blink-tag component from the app folder to the addons folder:

cd blink-tag
mv app/components/blink-tag.js addon/components/blink-tag.js

Create a new file in the apps folder, to make a default available.

//blink-tag/app/components/blink-tag.js
import BlinkTagComponent from "blink-tag/components/blink-tag";

export default BlinkTagComponent

You can also extend it from within the consuming application:

//consuming-app/app/components/blink-tag.js
import BlinkTagComponent from "blink-tag/components/blink-tag";

export default BlinkTagComponent.extend({
  tagName: null
})

Transcript

So in the last two episodes, we created an addon, in this case the blink addon, and then we published it so that we could use it in different apps on different computers. But it does have some weaknesses.

One of those is that it’s automatically a header 1. So if we want to make it something like a paragraph tag, it won’t necessarily work right out of the box. It’ll turn into a header 1. We have to do something like this. That’s okay for sometimes, but what if we wanted to have all of our blink tags as paragraph tags, or if we wanted to extend the tag in a more comprehensive way, something that can’t just be fed in in the handlebars?

Luckily, there’s a well-understood pattern for making this work, and to understand it you have to understand the difference between the app and the addon folders.

So currently, our component is in the app folder, app/components/blink-tag. And so what that means is it gets mixed in automatically to the applications namespace. That’s why we can’t just use blink-tag.

But there’s also an addon folder, which is part of the addon’s namespace. And the addon’s namespace is great because it can be imported and extended anywhere in both the addon and the app the addon is being used in.

So let’s go ahead, and we’ll go to our blink-tag, and we’ll take this and we’ll change it to be in the addons folder. So now we’ve got our blink tag in our addon folder. But this will create a disruption. So if we restart our Ember app, and remember that this app is still npm linked, and so we don’t need to re-download anything. So we restart it and we reload and it’s giving us an error because the blink-tag helper couldn’t be found because it’s just in the addon’s namespace. And there are two ways that we could deal with this.

One is we could create a component here called blink-tag.js, and we’ll import from blink-tag/components/blink-tag, and that’ll be the BlinkTagComponent, and then we’ll just export that. And that will give us back our blink tag.

But we don’t want everyone to have to create their own blink tag component file in order to import our stuff. We want it to be able to be available by default if that’s what people want. So here’s how you do it. First we’re going to cut this and remove the blink-tag component file. And then I’ll show you that yes, if you reload this now, it now errors.

And what we’re going to do is we’re going to go in here and we’re going to go into the apps folder again and we’re going to create a blink-tag component, but now instead of defining everything on the blink-tag component, we'll just import it from the addons folder and then export it as is. And then when we restart our project, we’ll see that it’s working again.

So now that we’ve replicated the old functionality, let’s go ahead and use this new power that we’ve created. So we’ll go to our components and we’ll create a BlinkTag and we’ll extend the blink tag that we have from our addon, and then we’ll just make the tagName null. And this indeed copies over.

So in order to make this look good, we’ll go ahead and add an h1 back here, and we’ll go ahead and remove this tagName. So now it’s looking like it should. We could even wrap everything in a blink-tag, because now that we’re not having a tag associated with it, it’ll just provide the blink functionality.

But let’s not get up caught up in the rather silly example. The point that we’re making is that now that we have it in the addons folder, so addon/components/blink-tag, we can extend it both in the host application that has the addon within it, or if we don’t want to do that, if we just want the default, then we can extend it in app/components/blink-tag, and that will have the default available with no work by the user.

So I hope this is useful to you and even though this is one of the most common patterns within Ember cli for making an extensible addon, there are plenty of other things that you can do to make your addon a better experience for other users, and you may go over those in future episodes. I’ll see you then.

Making ember-cli Addons

Subscribe to our mailing list