diff --git a/assets/scripts/app/auth.coffee b/assets/scripts/app/auth.coffee
index 46dda80f..40a47c79 100644
--- a/assets/scripts/app/auth.coffee
+++ b/assets/scripts/app/auth.coffee
@@ -71,7 +71,7 @@
try
router.send('afterSignIn')
catch e
- throw e unless e =~ /There are no active handlers/ || e =~ /Can't trigger action "afterSignIn/
+ throw e unless e =~ /There are no active handlers/
@refreshUserData(data.user)
refreshUserData: (user) ->
diff --git a/assets/scripts/app/components.coffee b/assets/scripts/app/components.coffee
index 09a177fb..da423edd 100644
--- a/assets/scripts/app/components.coffee
+++ b/assets/scripts/app/components.coffee
@@ -1,19 +1,9 @@
Travis.TravisSwitchComponent = Ember.Component.extend
tagName: 'a'
classNames: ['travis-switch']
- classNameBindings: ['_active:active']
+ classNameBindings: ['active']
- # TODO: how to handle overriding properties to
- # avoid naming it _action?
- _active: (->
- @get('target.active') || @get('active')
- ).property('target.active', 'active')
+ activeBinding: 'target.active'
click: ->
- if target = @get('target')
- @set('target.active', !@get('target.active'))
- else
- @set('active', !@get('active'))
- # allow for bindings to propagate
- Ember.run.next this, ->
- @sendAction('action', target)
+ @sendAction('action', @get('target'))
diff --git a/assets/scripts/app/controllers.coffee b/assets/scripts/app/controllers.coffee
index 488e3eb7..f1b4f520 100644
--- a/assets/scripts/app/controllers.coffee
+++ b/assets/scripts/app/controllers.coffee
@@ -48,18 +48,6 @@ Travis.FirstSyncController = Em.Controller.extend
isSyncing: Ember.computed.alias('user.isSyncing')
-Travis.IndexErrorController = Em.Controller.extend()
-
-Travis.RepoSettingsTabController = Em.ObjectController.extend()
-Travis.RepoSettingsController = Em.ObjectController.extend
- needs: ['repoSettingsTab']
- tab: Ember.computed.alias('controllers.repoSettingsTab.model.tab')
- settings: Ember.computed.alias('model.settings')
-
- save: ->
- @get('model').saveSettings(@get('settings')).then null, ->
- Travis.flash(error: 'There was an error while saving settings. Please try again.')
-
require 'controllers/accounts'
require 'controllers/build'
require 'controllers/builds'
diff --git a/assets/scripts/app/helpers/handlebars.coffee b/assets/scripts/app/helpers/handlebars.coffee
index 1074da90..8dfda033 100644
--- a/assets/scripts/app/helpers/handlebars.coffee
+++ b/assets/scripts/app/helpers/handlebars.coffee
@@ -3,293 +3,6 @@ require 'ext/ember/bound_helper'
safe = (string) ->
new Handlebars.SafeString(string)
-Travis.Tab = Ember.Object.extend
- show: ->
- @get('tabs').forEach( (t) -> t.hide() )
- @set('visible', true)
-
- hide: ->
- @set('visible', false)
-
-Travis.TabsView = Ember.View.extend
- tabBinding: 'controller.tab'
- tabsBinding: 'controller.tabs'
-
- tabDidChange: (->
- @activateTab(@get('tab'))
- ).observes('tab')
-
- tabsDidChange: (->
- tab = @get('tab')
- if tab
- @activateTab(tab)
- else if @get('tabs.length')
- @activateTab(@get('tabs.firstObject.id'))
- ).observes('tabs.length', 'tabs')
-
- activateTab: (tabId) ->
- tab = @get('tabs').findBy('id', tabId)
-
- return unless tab
-
- tab.show() unless tab.get('visible')
-
- # TODO: remove hardcoded link
- layout: Ember.Handlebars.compile(
- '
' +
- ' {{#each tab in tabs}}' +
- ' - ' +
- '
{{#linkTo "repo.settings.tab" tab.id}}{{tab.name}}{{/linkTo}}
' +
- ' ' +
- ' {{/each}}' +
- '
' +
- '{{yield}}')
-
-Travis.TabView = Ember.View.extend
- attributeBindings: ['style']
-
- style: (->
- if !@get('tab.visible')
- 'display: none'
- ).property('tab.visible')
-
-Ember.Handlebars.registerHelper('travis-tab', (id, name, options) ->
- controller = this
- controller.set('tabs', []) unless controller.get('tabs')
-
- tab = Travis.Tab.create(id: id, name: name, tabs: controller.get('tabs'))
-
- view = Travis.TabView.create(
- controller: this
- tab: tab
- )
-
- controller = this
- Ember.run.schedule('afterRender', ->
- if controller.get('tabs.length') == 0
- tab.show()
- controller.get('tabs').pushObject(tab)
- )
-
- Ember.Handlebars.helpers.view.call(this, view, options)
-)
-
-
-Ember.Handlebars.registerHelper('travis-tabs', (options) ->
- template = options.fn
- delete options.fn
-
- @set('tabs', [])
-
- view = Travis.TabsView.create(
- controller: this
- template: template
- )
-
- Ember.Handlebars.helpers.view.call(this, view, options)
-)
-
-Travis.SettingsMultiplierView = Ember.CollectionView.extend()
-
-createObjects = (path, offset) ->
- segments = path.split('.')
- if segments.length > offset
- for i in [1..(segments.length - offset)]
- path = segments.slice(0, i).join('.')
- if Ember.isNone(Ember.get(this, path))
- Ember.set(this, path, {})
-
- return segments
-
-Ember.Handlebars.registerHelper('settings-multiplier', (path, options) ->
- template = options.fn
- delete options.fn
-
- parentsPath = getSettingsPath(options.data.view)
- if parentsPath && parentsPath != ''
- path = parentsPath + '.' + path
-
- createObjects.call(this, path, 1)
-
- if Ember.isNone(@get(path))
- collection = [{}]
- @set(path, collection)
-
-
- itemViewClass = Ember.View.extend(
- template: template,
- controller: this,
- tagName: 'li',
- multiplier: true
- )
-
- view = Travis.SettingsMultiplierView.create(
- contentBinding: 'controller.' + path
- controller: this
- tagName: 'ul'
- itemViewClass: itemViewClass
- fields: []
- settingsPath: path
- )
-
- view.addObserver('content.length', ->
- if @get('content.length') == 0
- @get('content').pushObject({})
- )
-
- Ember.Handlebars.helpers.view.call(this, view, options)
-)
-
-Travis.FormSettingsView = Ember.View.extend Ember.TargetActionSupport,
- target: Ember.computed.alias('controller')
- actionContext: Ember.computed.alias('context'),
- action: 'submit'
- tagName: 'form'
- submit: (event) ->
- event.preventDefault()
- @triggerAction()
-
-
-Ember.Handlebars.registerHelper('settings-form', (path, options) ->
- if arguments.length == 1
- options = path
- path = 'settings'
-
- view = Travis.FormSettingsView.create(
- template: options.fn
- controller: this
- settingsPath: path
- )
-
- delete options.fn
-
- Ember.Handlebars.helpers.view.call(this, view, options)
-)
-
-Ember.Handlebars.helper('settings-select', (options) ->
- view = options.data.view
- optionValues = options.hash.options
- delete options.hash.options
-
- originalPath = options.hash.value
-
- parentsPath = getSettingsPath(view)
- #TODO: such checks should also check parents, not only current context view
- if !view.get('multiplier') && parentsPath && parentsPath != ''
- originalPath = parentsPath + '.' + originalPath
-
- fullPath = originalPath
-
- if view.get('multiplier')
- fullPath = 'view.content.' + fullPath
-
- createObjects.call(this, fullPath, 1)
-
- # TODO: setting a value here does not work and we still need
- # a valueBinding in the view, I'm not sure why
- options.hash.value = fullPath
-
- selectView = Ember.Select.create(
- content: [''].pushObjects(optionValues.split(','))
- controller: this
- valueBinding: 'controller.' + fullPath
- )
-
- Ember.Handlebars.helpers.view.call(this, selectView, options)
-)
-
-
-
-Ember.Handlebars.helper('settings-remove-link', (options) ->
- view = Ember.View.extend(
- tagName: 'a'
- attributeBindings: ['href', 'style']
- href: '#'
- style: (->
- # TODO: do not assume that we're direct child
- if @get('parentView.parentView.content.length') == 1
- 'display: none'
- ).property('parentView.parentView.content.length')
- template: Ember.Handlebars.compile('remove')
- controller: this
- click: (event) ->
- event.preventDefault()
-
- if content = @get('parentView.content')
- @get('parentView.parentView.content').removeObject(content)
- ).create()
-
- Ember.Handlebars.helpers.view.call(this, view, options)
-)
-
-Ember.Handlebars.registerHelper('settings-add-link', (path, options) ->
- parentsPath = getSettingsPath(options.data.view)
- if parentsPath && parentsPath != ''
- path = parentsPath + '.' + path
-
- view = Ember.View.create(
- tagName: 'a'
- attributeBindings: ['href']
- href: '#'
- template: options.fn
- controller: this
- click: (event) ->
- event.preventDefault()
-
- if collection = @get('controller.' + path)
- collection.pushObject({})
- )
-
- Ember.Handlebars.helpers.view.call(this, view, options)
-)
-
-getSettingsPath = (view) ->
- settingsPaths = []
- if settingsPath = view.get('settingsPath')
- settingsPaths.pushObject settingsPath
-
- parent = view
- while parent = parent.get('parentView')
- if settingsPath = parent.get('settingsPath')
- settingsPaths.pushObject settingsPath
-
- return settingsPaths.reverse().join('.')
-
-Ember.Handlebars.helper('settings-input', (options) ->
- view = options.data.view
-
- if options.hash.type == 'checkbox'
- originalPath = options.hash.checked
- else
- originalPath = options.hash.value
-
- parentsPath = getSettingsPath(view)
- #TODO: such checks should also check parents, not only current context view
- if !view.get('multiplier') && parentsPath && parentsPath != ''
- originalPath = parentsPath + '.' + originalPath
-
- fullPath = originalPath
-
- if view.get('multiplier')
- fullPath = 'view.content.' + fullPath
-
- if options.hash.type != 'password'
- createObjects.call(this, fullPath, 1)
- else
- createObjects.call(view, fullPath, 2)
- content = view.get('content')
- fullPath += ".value"
- if Ember.isNone(Ember.get(content, originalPath))
- Ember.set(content, originalPath, {})
- Ember.set(content, originalPath + ".type", 'password')
-
- if options.hash.type == 'checkbox'
- options.hash.checked = fullPath
- else
- options.hash.value = fullPath
- Ember.Handlebars.helpers.input.call(this, options)
-)
-
Handlebars.registerHelper 'tipsy', (text, tip) ->
safe '' + text + ''
diff --git a/assets/scripts/app/models/hook.coffee b/assets/scripts/app/models/hook.coffee
index 4126292b..677708d1 100644
--- a/assets/scripts/app/models/hook.coffee
+++ b/assets/scripts/app/models/hook.coffee
@@ -27,13 +27,3 @@ require 'travis/model'
return if @get('isSaving')
@set 'active', !@get('active')
@save()
-
- repo: (->
- # I don't want to make an ajax request for each repository showed in profile,
- # especially, because most of them does not have any builds anyway. That's why
- # I add an info which we have here to the store - this will allow to display
- # a link to the repo and if more info is needed, it will be requested when the
- # link is used
- Travis.loadOrMerge(Travis.Repo, @getProperties('id', 'slug', 'name', 'ownerName'), skipIfExists: true)
- Travis.Repo.find(@get('id'))
- ).property('id')
diff --git a/assets/scripts/app/models/repo.coffee b/assets/scripts/app/models/repo.coffee
index 3f94fc93..f582fb10 100644
--- a/assets/scripts/app/models/repo.coffee
+++ b/assets/scripts/app/models/repo.coffee
@@ -105,13 +105,6 @@ require 'travis/model'
regenerateKey: (options) ->
Travis.ajax.ajax '/repos/' + @get('id') + '/key', 'post', options
- fetchSettings: ->
- Travis.ajax.ajax('/repos/' + @get('id') + '/settings', 'get', forceAuth: true).then (data) ->
- data['settings']
-
- saveSettings: (settings) ->
- Travis.ajax.ajax('/repos/' + @get('id') + '/settings', 'patch', data: { settings: settings })
-
@Travis.Repo.reopenClass
recent: ->
@find()
@@ -147,10 +140,7 @@ require 'travis/model'
if repos.length > 0
repos[0]
else
- @fetch(slug: slug).then (repos) ->
- error = new Error('repo not found')
- error.slug = slug
- Ember.get(repos, 'firstObject') || throw(error)
+ @fetch(slug: slug).then (repos) -> Ember.get(repos, 'firstObject')
# buildURL: (slug) ->
# if slug then slug else 'repos'
diff --git a/assets/scripts/app/routes.coffee b/assets/scripts/app/routes.coffee
index f277b20d..711111a8 100644
--- a/assets/scripts/app/routes.coffee
+++ b/assets/scripts/app/routes.coffee
@@ -5,9 +5,41 @@ Ember.Router.reopen
handleURL: (url) ->
url = url.replace(/#.*?$/, '')
- @_super(url)
+ try
+ @_super(url)
+ catch error
+ if error.message.match(/No route matched the URL/)
+ @_super('/not-found')
+ else
+ throw(error)
+
+# TODO: don't reopen Ember.Route to add events, there should be
+# a better way (like "parent" resource for everything inside map)
+Ember.Route.reopen
+ _actions:
+ renderDefaultTemplate: ->
+ @renderDefaultTemplate() if @renderDefaultTemplate
+
+ error: (error) ->
+ if error == 'needs-auth'
+ authController = @container.lookup('controller:auth') || @generateController('auth')
+ authController.set('redirected', true)
+ @transitionTo('auth')
+ else
+ throw(error)
+
+ renderNoOwnedRepos: ->
+ @render('no_owned_repos', outlet: 'main')
+
+ renderFirstSync: ->
+ @renderFirstSync()
+
+ afterSignIn: (path) ->
+ @afterSignIn(path)
+
+ afterSignOut: ->
+ @afterSignOut()
-Travis.Route = Ember.Route.extend
afterSignIn: ->
if transition = Travis.auth.get('afterSignInTransition')
Travis.auth.set('afterSignInTransition', null)
@@ -46,37 +78,6 @@ Travis.Route = Ember.Route.extend
Travis.storeAfterSignInPath(path)
@transitionTo('auth')
-Travis.ApplicationRoute = Travis.Route.extend
- actions:
- renderDefaultTemplate: ->
- @renderDefaultTemplate() if @renderDefaultTemplate
-
- error: (error) ->
- if error == 'needs-auth'
- authController = @container.lookup('controller:auth') || @generateController('auth')
- authController.set('redirected', true)
- @transitionTo('auth')
- else
- return true
-
- renderNoOwnedRepos: ->
- @render('no_owned_repos', outlet: 'main')
-
- renderFirstSync: ->
- @renderFirstSync()
-
- afterSignIn: (path) ->
- @afterSignIn(path)
-
- afterSignOut: ->
- @afterSignOut()
-
-Travis.Router.reopen
- transitionTo: ->
- this.container.lookup('controller:repo').set('lineNumber', null)
-
- @_super.apply this, arguments
-
Travis.Router.map ->
@resource 'index', path: '/', ->
@route 'current', path: '/'
@@ -88,15 +89,11 @@ Travis.Router.map ->
@resource 'pullRequests', path: '/pull_requests'
@resource 'branches', path: '/branches'
- # this can't be nested in repo, because we want a set of different
- # templates rendered for settings (for example no "current", "builds", ... tabs)
- @resource 'repo.settings', path: '/:owner/:name/settings', ->
- @route 'tab', path: ':tab'
-
@route 'getting_started'
@route 'first_sync'
@route 'stats', path: '/stats'
@route 'auth', path: '/auth'
+ @route 'notFound', path: '/not-found'
@resource 'profile', path: '/profile', ->
@route 'index', path: '/'
@@ -104,8 +101,6 @@ Travis.Router.map ->
@route 'index', path: '/'
@route 'profile', path: '/profile'
- @route 'notFound', path: "/*path"
-
Travis.SetupLastBuild = Ember.Mixin.create
setupController: ->
@repoDidLoad()
@@ -116,9 +111,9 @@ Travis.SetupLastBuild = Ember.Mixin.create
repo = @controllerFor('repo').get('repo')
if repo && repo.get('isLoaded') && !repo.get('lastBuildId')
Ember.run.next =>
- @render('builds/not_found', into: 'repo', outlet: 'pane')
+ @render('builds/not_found', outlet: 'pane', into: 'repo')
-Travis.GettingStartedRoute = Travis.Route.extend
+Travis.GettingStartedRoute = Ember.Route.extend
setupController: ->
$('body').attr('id', 'home')
@container.lookup('controller:repos').activate()
@@ -130,8 +125,8 @@ Travis.GettingStartedRoute = Travis.Route.extend
@render 'repos', outlet: 'left'
@_super.apply(this, arguments)
-Travis.FirstSyncRoute = Travis.Route.extend
- actions:
+Travis.FirstSyncRoute = Ember.Route.extend
+ _actions:
renderNoOwnedRepos: (->)
# do nothing, we are showing first sync, so it's normal that there is
# no owned repos
@@ -146,10 +141,10 @@ Travis.FirstSyncRoute = Travis.Route.extend
@render 'top', outlet: 'top'
@_super.apply(this, arguments)
-Travis.IndexCurrentRoute = Travis.Route.extend Travis.SetupLastBuild,
+Travis.IndexCurrentRoute = Ember.Route.extend Travis.SetupLastBuild,
renderTemplate: ->
@render 'repo'
- @render 'build', into: 'repo', outlet: 'pane'
+ @render 'build', outlet: 'pane', into: 'repo'
setupController: ->
@_super.apply this, arguments
@@ -164,9 +159,9 @@ Travis.IndexCurrentRoute = Travis.Route.extend Travis.SetupLastBuild,
currentRepoDidChange: ->
@controllerFor('repo').set('repo', @controllerFor('repos').get('firstObject'))
-Travis.AbstractBuildsRoute = Travis.Route.extend
+Travis.AbstractBuildsRoute = Ember.Route.extend
renderTemplate: ->
- @render 'builds', into: 'repo', outlet: 'pane'
+ @render 'builds', outlet: 'pane', into: 'repo'
setupController: ->
@controllerFor('repo').activate(@get('contentType'))
@@ -189,9 +184,9 @@ Travis.BuildsRoute = Travis.AbstractBuildsRoute.extend(contentType: 'builds')
Travis.PullRequestsRoute = Travis.AbstractBuildsRoute.extend(contentType: 'pull_requests')
Travis.BranchesRoute = Travis.AbstractBuildsRoute.extend(contentType: 'branches')
-Travis.BuildRoute = Travis.Route.extend
+Travis.BuildRoute = Ember.Route.extend
renderTemplate: ->
- @render 'build', into: 'repo', outlet: 'pane'
+ @render 'build', outlet: 'pane', into: 'repo'
serialize: (model, params) ->
id = if model.get then model.get('id') else model
@@ -210,9 +205,9 @@ Travis.BuildRoute = Travis.Route.extend
model: (params) ->
Travis.Build.fetch(params.build_id)
-Travis.JobRoute = Travis.Route.extend
+Travis.JobRoute = Ember.Route.extend
renderTemplate: ->
- @render 'job', into: 'repo', outlet: 'pane'
+ @render 'job', outlet: 'pane', into: 'repo'
serialize: (model, params) ->
id = if model.get then model.get('id') else model
@@ -233,15 +228,15 @@ Travis.JobRoute = Travis.Route.extend
model: (params) ->
Travis.Job.fetch(params.job_id)
-Travis.RepoIndexRoute = Travis.Route.extend Travis.SetupLastBuild,
+Travis.RepoIndexRoute = Ember.Route.extend Travis.SetupLastBuild,
setupController: (controller, model) ->
@_super.apply this, arguments
@controllerFor('repo').activate('current')
renderTemplate: ->
- @render 'build', into: 'repo', outlet: 'pane'
+ @render 'build', outlet: 'pane', into: 'repo'
-Travis.RepoRoute = Travis.Route.extend
+Travis.RepoRoute = Ember.Route.extend
renderTemplate: ->
@render 'repo'
@@ -258,20 +253,15 @@ Travis.RepoRoute = Travis.Route.extend
model: (params) ->
slug = "#{params.owner}/#{params.name}"
+
Travis.Repo.fetchBySlug(slug)
actions:
- error: (error) ->
- # if error throwed has a slug (ie. it was probably repo not found)
- # set the slug on index.error controller to allow to properly
- # display the repo information
- if error.slug
- this.controllerFor('index.error').set('slug', error.slug)
+ error: ->
+ Ember.run.next this, ->
+ @render('repos/not_found', outlet: 'main')
- # bubble to the top
- return true
-
-Travis.IndexRoute = Travis.Route.extend
+Travis.IndexRoute = Ember.Route.extend
renderTemplate: ->
$('body').attr('id', 'home')
@@ -283,7 +273,11 @@ Travis.IndexRoute = Travis.Route.extend
@container.lookup('controller:repos').activate()
@container.lookup('controller:application').connectLayout 'home'
-Travis.StatsRoute = Travis.Route.extend
+Travis.IndexLoadingRoute = Ember.Route.extend
+ renderTemplate: ->
+ @render('index_loading')
+
+Travis.StatsRoute = Ember.Route.extend
renderTemplate: ->
$('body').attr('id', 'stats')
@@ -293,7 +287,7 @@ Travis.StatsRoute = Travis.Route.extend
setupController: ->
@container.lookup('controller:application').connectLayout('simple')
-Travis.NotFoundRoute = Travis.Route.extend
+Travis.NotFoundRoute = Ember.Route.extend
renderTemplate: ->
$('body').attr('id', 'not-found')
@@ -303,7 +297,7 @@ Travis.NotFoundRoute = Travis.Route.extend
setupController: ->
@container.lookup('controller:application').connectLayout('simple')
-Travis.ProfileRoute = Travis.Route.extend
+Travis.ProfileRoute = Ember.Route.extend
needsAuth: true
setupController: ->
@@ -316,16 +310,16 @@ Travis.ProfileRoute = Travis.Route.extend
@render 'top', outlet: 'top'
@render 'accounts', outlet: 'left'
@render 'flash', outlet: 'flash'
- @_super.apply(this, arguments)
+ @render 'profile'
-Travis.ProfileIndexRoute = Travis.Route.extend
+Travis.ProfileIndexRoute = Ember.Route.extend
setupController: ->
@container.lookup('controller:profile').activate 'hooks'
renderTemplate: ->
@render 'hooks', outlet: 'pane', into: 'profile', controller: 'profile'
-Travis.AccountRoute = Travis.Route.extend
+Travis.AccountRoute = Ember.Route.extend
setupController: (controller, account) ->
profileController = @container.lookup('controller:profile')
profileController.activate 'hooks'
@@ -358,21 +352,21 @@ Travis.AccountRoute = Travis.Route.extend
else
{}
-Travis.AccountIndexRoute = Travis.Route.extend
+Travis.AccountIndexRoute = Ember.Route.extend
setupController: ->
@container.lookup('controller:profile').activate 'hooks'
renderTemplate: ->
@render 'hooks', outlet: 'pane', into: 'profile'
-Travis.AccountProfileRoute = Travis.Route.extend
+Travis.AccountProfileRoute = Ember.Route.extend
setupController: ->
@container.lookup('controller:profile').activate 'user'
renderTemplate: ->
@render 'user', outlet: 'pane', into: 'profile'
-Travis.AuthRoute = Travis.Route.extend
+Travis.AuthRoute = Ember.Route.extend
renderTemplate: ->
$('body').attr('id', 'auth')
@@ -384,25 +378,3 @@ Travis.AuthRoute = Travis.Route.extend
deactivate: ->
@controllerFor('auth').set('redirected', false)
-
-Travis.RepoSettingsRoute = Travis.Route.extend
- setupController: (controller, model) ->
- # TODO: if repo is just a data hash with id and slug load it
- # as incomplete record
- model = Travis.Repo.find(model.id) if model && !model.get
- @_super(controller, model)
-
- serialize: (repo) ->
- slug = if repo.get then repo.get('slug') else repo.slug
- [owner, name] = slug.split('/')
- { owner: owner, name: name }
-
- model: (params) ->
- slug = "#{params.owner}/#{params.name}"
- Travis.Repo.fetchBySlug(slug)
-
- afterModel: (repo) ->
- # I'm using afterModel to fetch settings, because model is not always called.
- # If link-to already provides a model, it will be just set as a route context.
- repo.fetchSettings().then (settings) ->
- repo.set('settings', settings)
diff --git a/assets/scripts/app/templates/components/travis-switch.hbs b/assets/scripts/app/templates/components/travis-switch.hbs
index 18617602..e7b20837 100644
--- a/assets/scripts/app/templates/components/travis-switch.hbs
+++ b/assets/scripts/app/templates/components/travis-switch.hbs
@@ -1,4 +1,4 @@
-{{#if _active}}
+{{#if active}}
ON
{{else}}
OFF
diff --git a/assets/scripts/app/templates/index_loading.hbs b/assets/scripts/app/templates/index_loading.hbs
new file mode 100644
index 00000000..0277cf2e
--- /dev/null
+++ b/assets/scripts/app/templates/index_loading.hbs
@@ -0,0 +1 @@
+Loading
diff --git a/assets/scripts/app/templates/profile/tabs/hooks.hbs b/assets/scripts/app/templates/profile/tabs/hooks.hbs
index 8be19160..a937db01 100644
--- a/assets/scripts/app/templates/profile/tabs/hooks.hbs
+++ b/assets/scripts/app/templates/profile/tabs/hooks.hbs
@@ -23,7 +23,7 @@
{{hook.description}}
- {{#link-to "repo.settings" hook.repo class="repo-settings-icon tool-tip" title="Repository settings"}}{{/link-to}}
+
{{travis-switch action="toggle" target=hook}}
diff --git a/assets/scripts/app/templates/repos/not_found.hbs b/assets/scripts/app/templates/repos/not_found.hbs
new file mode 100644
index 00000000..57d6f053
--- /dev/null
+++ b/assets/scripts/app/templates/repos/not_found.hbs
@@ -0,0 +1,3 @@
+
+ The repository at {{slug}} was not found.
+
diff --git a/assets/scripts/app/templates/repos/show.hbs b/assets/scripts/app/templates/repos/show.hbs
index 9b80786a..c1bf53b9 100644
--- a/assets/scripts/app/templates/repos/show.hbs
+++ b/assets/scripts/app/templates/repos/show.hbs
@@ -24,3 +24,4 @@
{{/if}}
{{/if}}
+
diff --git a/assets/scripts/app/templates/repos/show/tools.hbs b/assets/scripts/app/templates/repos/show/tools.hbs
index 65f865b7..5fc4135e 100644
--- a/assets/scripts/app/templates/repos/show/tools.hbs
+++ b/assets/scripts/app/templates/repos/show/tools.hbs
@@ -11,12 +11,6 @@
{{/if}}
- {{#if view.displaySettingsLink}}
-
- {{#linkTo "repo.settings" view.repo}}Settings{{/linkTo}}
-
- {{/if}}
-