# How to override \`admin.hbs\`

**URL:** https://meta.discourse.org/t/how-to-override-admin-hbs/98307
**Category:** Development
**Created:** [September 28, 2018, 8:59pm UTC](https://meta.discourse.org/t/how-to-override-admin-hbs/98307 "2018-09-28T20:59:39Z")
**Posts on this page:** 9
**Page:** 1

<div class="post-metadata">

### Author: ![pfaffman](https://sea3.discourse-cdn.com/meta/user_avatar/meta.discourse.org/pfaffman/32/120154_2.png) [@pfaffman](https://meta.discourse.org/u/pfaffman)
#### Post date: [September 28, 2018, 8:59pm UTC](https://meta.discourse.org/t/how-to-override-admin-hbs/98307/1 "2018-09-28T20:59:40Z")

</div>

I’m just a caveman.

I want to override `app/assets/javascripts/templates/admin.hbs` because I want to change the nav menu on the admin page (but if that’s not how to do it, I’m all ears). If this is possible in a theme, I’d be interested, but this is related to a plugin that does a bunch of other stuff, so the plugin solution is what I want. I mostly want to disable links to API.

I figure that I need to:

1. make a copy of `admin.hbs`, make my changes, and stick it, uh, somewhere (`app/assets/javascripts/templates`, perhaps?)
2. put something in `plugin.rb` that tells Rails that I want to use my file instead of the stock one.
3. Keep an eye on updates to admin.hbs in the future so that I don’t break it.
4. Profit.

---

<div class="post-metadata">

### Author: ![gdpelican](https://sea3.discourse-cdn.com/meta/user_avatar/meta.discourse.org/gdpelican/32/81308_2.png) [@gdpelican](https://meta.discourse.org/u/gdpelican)
#### Post date: [September 28, 2018, 9:25pm UTC](https://meta.discourse.org/t/how-to-override-admin-hbs/98307/2 "2018-09-28T21:25:54Z")

</div>

Overriding templates is a fairly nuclear solution, and some one-off fiddly javascript or css like

```plaintext
// NB I am pseudocode
$('.api-nav-item').attr('disabled', 'true')
.api-nav-item { display: none; }

```

would definitely serve you better here if you can get away with it.

If you need to override a whole template, theme component is the simpler way that I know of, with something like

```plaintext
<script type="text/x-handlebars" data-template-name="admin">
  <div>Hello world!</div>
</script>

```

If your plugin is going to go onto a bunch of instances, or you need to automate the installation more for whatever reason, you can go with my jack-wild solution from [mingle](https://github.com/gdpelican/mingle/blob/master/app/extras/theme_component_seed.rb), which automatically populates a theme component when the plugin is installed (but note that this is well within the realm of mad science 👨‍🔬).

---

<div class="post-metadata">

### Author: ![pfaffman](https://sea3.discourse-cdn.com/meta/user_avatar/meta.discourse.org/pfaffman/32/120154_2.png) [@pfaffman](https://meta.discourse.org/u/pfaffman)
#### Post date: [October 4, 2018, 6:03pm UTC](https://meta.discourse.org/t/how-to-override-admin-hbs/98307/3 "2018-10-04T18:03:35Z")

</div>

Thanks very much for this. Let me see if I have this straight.

> [@gdpelican](#):
>
> some one-off fiddly javascript or css like

And by “one-off fiddly”, you mean that it wouldn’t survive an upgrade or work across sites because there’s no `api-nav-item`

 ![image](https://global.discourse-cdn.com/meta/original/3X/0/b/0b1af4073eb15b89836503e517103d7716c68fef.png)

Do I understand that correctly?

So I can’t hide the API link without overriding the template (which you argue is better in a theme is better than a plugin, but again, the plugin is what’s going to decide whether the API link should be hidden) is a feature request for a `enable-api` that’s just like the `enable_backups`?

I’ve already hijacked the /admin/api route, so I think my solution may just be to redirect it somewhere (currently it 404s). EDIT: I did that with `custom_admin_check`, so that’s why it’s a 404. Hmm.

> [@gdpelican](#):
>
> you need to automate the installation more for whatever reason, you can go with my jack-wild solution

That’s fantastic, and I do want to automate it. Thanks very much for that.

---

<div class="post-metadata">

### Author: ![gdpelican](https://sea3.discourse-cdn.com/meta/user_avatar/meta.discourse.org/gdpelican/32/81308_2.png) [@gdpelican](https://meta.discourse.org/u/gdpelican)
#### Post date: [October 4, 2018, 7:43pm UTC](https://meta.discourse.org/t/how-to-override-admin-hbs/98307/4 "2018-10-04T19:43:00Z")

</div>

Ah, I hadn’t really understood what you were up to in the first post, but I think I understand better now.

The admin menu isn’t very open for customization, but there’s often some way around it. I might try something like this for my fiddly one-off javascript solution (this is plugin land):

```plaintext
api.modifyClass('component:nav-item', {
  classNameBindings: ['hidden'],

  @computed('label')
  hidden() {
    return this.label == 'admin.api.title'
  }
})

```

Note that this works by applying the `hidden` class to the nav li in question, which has `display: none` as a style.

---

<div class="post-metadata">

### Author: ![pfaffman](https://sea3.discourse-cdn.com/meta/user_avatar/meta.discourse.org/pfaffman/32/120154_2.png) [@pfaffman](https://meta.discourse.org/u/pfaffman)
#### Post date: [October 4, 2018, 11:13pm UTC](https://meta.discourse.org/t/how-to-override-admin-hbs/98307/5 "2018-10-04T23:13:48Z")

</div>

> [@gdpelican](#):
>
> (this is plugin land)

Hmm. I tried sticking that in places like `assets/javascripts/initializers/lc-site-settings.es6` to no avail. I did manage to foolishly override `admin.hbs` and use my plugin’s settings to enable/disable stuff in the menu. I do like the idea of not mucking with the template for all the reasons you mention.

In a plugin where do I stick your code?

---

<div class="post-metadata">

### Author: ![gdpelican](https://sea3.discourse-cdn.com/meta/user_avatar/meta.discourse.org/gdpelican/32/81308_2.png) [@gdpelican](https://meta.discourse.org/u/gdpelican)
#### Post date: [October 4, 2018, 11:40pm UTC](https://meta.discourse.org/t/how-to-override-admin-hbs/98307/6 "2018-10-04T23:40:05Z")

</div>

You’ll want an initializer which imports the pluginApi for use, cerca

```plaintext
// javascripts/initializers/hide-admin-api.js.es6
export default {
  name: 'hide-admin-api',
  initialize: function() {
    withPluginApi('0.8.6', (api) => {
      api.modifyClass(...)
    })
  }
}

```

I’m also suspicious of the `file.es6` extension, as I think the system uses regex matching to look in that folder for things to load, and might enforce a `file.js.es6` ending as well.

---

<div class="post-metadata">

### Author: ![pfaffman](https://sea3.discourse-cdn.com/meta/user_avatar/meta.discourse.org/pfaffman/32/120154_2.png) [@pfaffman](https://meta.discourse.org/u/pfaffman)
#### Post date: [October 9, 2018, 4:55pm UTC](https://meta.discourse.org/t/how-to-override-admin-hbs/98307/7 "2018-10-09T16:55:19Z")

</div>

Update: I’ve managed to get my `api-hide.js.es6` file in a place where it is doing something.

```javascript
// javascripts/initializers/hide-admin-api.js.es6
export default {
  name: 'hide-admin-api',
  initialize: function() {
    withPluginApi('0.8.6', (api) => {
      api.modifyClass('component:nav-item', {
        classNameBindings: ['hidden'],
        @computed('label')
        hidden() {
          return this.label == 'admin.api.title'
        }
      })
    })
  }
}

```

Results in a blank page. I’ve tried stuff like

```plaintext
hidden() {
    return false
}

```

and `api.modifyClass('component:NOT-nav-item'`  
but the whole page is still empty.

Thanks again for your patience.

---

<div class="post-metadata">

### Author: ![tshenry](https://sea3.discourse-cdn.com/meta/user_avatar/meta.discourse.org/tshenry/32/119495_2.png) [@tshenry](https://meta.discourse.org/u/tshenry)
#### Post date: [October 9, 2018, 8:53pm UTC](https://meta.discourse.org/t/how-to-override-admin-hbs/98307/8 "2018-10-09T20:53:14Z")

</div>

If using a script that applies `display: none` is an acceptable solution, is there a reason you can’t just use CSS from the start?

```plaintext
.admin-main-nav a[href="/admin/api"] {
    display: none;
}

```

---

<div class="post-metadata">

### Author: ![pfaffman](https://sea3.discourse-cdn.com/meta/user_avatar/meta.discourse.org/pfaffman/32/120154_2.png) [@pfaffman](https://meta.discourse.org/u/pfaffman)
#### Post date: [October 9, 2018, 9:32pm UTC](https://meta.discourse.org/t/how-to-override-admin-hbs/98307/9 "2018-10-09T21:32:56Z")

</div>

> [@tshenry](#):
>
> is there a reason you can’t just use CSS from the start?

Mostly because I didn’t know how. But I pasted that in to `assets/stylesheets/common/lc-site-settings.scss` and lo! it turned it off. And, I swapped in a different path in for that `href` and it turned off too! I didn’t even need to reload!!! It’s like magic! I’ve done little this exciting since I wrote this:

```
10 print "Hello, world."
20 goto 10

```

Brilliant. Thanks very much.

But now, I need to be able to turn off the link optionally when a SiteSetting is on/off.
