mirror of
https://github.com/TryGhost/Ghost.git
synced 2024-12-01 13:54:35 +03:00
Tags management api hookup
Ref #4248 - Added tags settings menu - Added basic new, edit, delete, and save actions - Show actionable edit buttons dynamically based on tag state - Infinite scroll - Closing the tag settings menu rollbacks your changes - Removed not-yet-implementable code
This commit is contained in:
parent
0c38a839b0
commit
bd0f5e0c5b
50
core/client/controllers/settings/tags.js
Normal file
50
core/client/controllers/settings/tags.js
Normal file
@ -0,0 +1,50 @@
|
|||||||
|
import PaginationMixin from 'ghost/mixins/pagination-controller';
|
||||||
|
|
||||||
|
var TagsController = Ember.ArrayController.extend(PaginationMixin, {
|
||||||
|
tags: Ember.computed.alias('model'),
|
||||||
|
activeTag: null,
|
||||||
|
init: function (options) {
|
||||||
|
options = options || {};
|
||||||
|
options.modelType = 'tag';
|
||||||
|
this._super(options);
|
||||||
|
},
|
||||||
|
actions: {
|
||||||
|
// Clear any unsaved changes until autosave is implemented
|
||||||
|
closeTagEditor: function () {
|
||||||
|
this.get('activeTag').rollback();
|
||||||
|
this.send('closeSettingsMenu');
|
||||||
|
},
|
||||||
|
newTag: function () {
|
||||||
|
this.set('activeTag', this.store.createRecord('tag'));
|
||||||
|
this.send('openSettingsMenu');
|
||||||
|
},
|
||||||
|
editTag: function (tag) {
|
||||||
|
this.set('activeTag', tag);
|
||||||
|
this.send('openSettingsMenu');
|
||||||
|
},
|
||||||
|
deleteTag: function (tag) {
|
||||||
|
var name = tag.get('name'),
|
||||||
|
self = this;
|
||||||
|
|
||||||
|
this.send('closeSettingsMenu');
|
||||||
|
|
||||||
|
tag.destroyRecord().then(function () {
|
||||||
|
self.notifications.showSuccess('Deleted ' + name);
|
||||||
|
}).catch(function (error) {
|
||||||
|
self.notifications.showAPIError(error);
|
||||||
|
});
|
||||||
|
},
|
||||||
|
saveTag: function (tag) {
|
||||||
|
var name = tag.get('name'),
|
||||||
|
self = this;
|
||||||
|
|
||||||
|
tag.save().then(function () {
|
||||||
|
self.notifications.showSuccess('Saved ' + name);
|
||||||
|
}).catch(function (error) {
|
||||||
|
self.notifications.showAPIError(error);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
export default TagsController;
|
@ -17,7 +17,7 @@ var PaginationControllerMixin = Ember.Mixin.create({
|
|||||||
* }
|
* }
|
||||||
*/
|
*/
|
||||||
init: function (options) {
|
init: function (options) {
|
||||||
this._super();
|
this._super(options);
|
||||||
|
|
||||||
var metadata = this.store.metadataFor(options.modelType);
|
var metadata = this.store.metadataFor(options.modelType);
|
||||||
|
|
||||||
|
@ -31,12 +31,15 @@ var ApplicationRoute = Ember.Route.extend(SimpleAuth.ApplicationRouteMixin, Shor
|
|||||||
this.toggleProperty('controller.showGlobalMobileNav');
|
this.toggleProperty('controller.showGlobalMobileNav');
|
||||||
},
|
},
|
||||||
|
|
||||||
toggleSettingsMenu: function () {
|
openSettingsMenu: function () {
|
||||||
this.toggleProperty('controller.showSettingsMenu');
|
this.set('controller.showSettingsMenu', true);
|
||||||
},
|
},
|
||||||
closeSettingsMenu: function () {
|
closeSettingsMenu: function () {
|
||||||
this.set('controller.showSettingsMenu', false);
|
this.set('controller.showSettingsMenu', false);
|
||||||
},
|
},
|
||||||
|
toggleSettingsMenu: function () {
|
||||||
|
this.toggleProperty('controller.showSettingsMenu');
|
||||||
|
},
|
||||||
|
|
||||||
closePopups: function () {
|
closePopups: function () {
|
||||||
this.get('dropdown').closeDropdowns();
|
this.get('dropdown').closeDropdowns();
|
||||||
|
@ -1,7 +1,8 @@
|
|||||||
import AuthenticatedRoute from 'ghost/routes/authenticated';
|
import AuthenticatedRoute from 'ghost/routes/authenticated';
|
||||||
import CurrentUserSettings from 'ghost/mixins/current-user-settings';
|
import CurrentUserSettings from 'ghost/mixins/current-user-settings';
|
||||||
|
import PaginationRouteMixin from 'ghost/mixins/pagination-route';
|
||||||
|
|
||||||
var TagsRoute = AuthenticatedRoute.extend(CurrentUserSettings, {
|
var TagsRoute = AuthenticatedRoute.extend(CurrentUserSettings, PaginationRouteMixin, {
|
||||||
|
|
||||||
beforeModel: function () {
|
beforeModel: function () {
|
||||||
if (!this.get('config.tagsUI')) {
|
if (!this.get('config.tagsUI')) {
|
||||||
@ -14,6 +15,20 @@ var TagsRoute = AuthenticatedRoute.extend(CurrentUserSettings, {
|
|||||||
|
|
||||||
model: function () {
|
model: function () {
|
||||||
return this.store.find('tag');
|
return this.store.find('tag');
|
||||||
|
},
|
||||||
|
|
||||||
|
setupController: function (controller, model) {
|
||||||
|
this._super(controller, model);
|
||||||
|
this.setupPagination();
|
||||||
|
},
|
||||||
|
|
||||||
|
renderTemplate: function (controller, model) {
|
||||||
|
this._super(controller, model);
|
||||||
|
this.render('settings/tags/settings-menu', {
|
||||||
|
into: 'application',
|
||||||
|
outlet: 'settings-menu',
|
||||||
|
view: 'settings/tags/settings-menu'
|
||||||
|
});
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -3,7 +3,7 @@
|
|||||||
{{render 'post-tags-input'}}
|
{{render 'post-tags-input'}}
|
||||||
|
|
||||||
<div class="publish-bar-actions">
|
<div class="publish-bar-actions">
|
||||||
<button type="button" class='post-settings' {{action "toggleSettingsMenu"}}></button>
|
<button type="button" class="post-settings" {{action "toggleSettingsMenu"}}></button>
|
||||||
{{view "editor-save-button" id="entry-actions" classNameBindings="isNew:unsaved"}}
|
{{view "editor-save-button" id="entry-actions" classNameBindings="isNew:unsaved"}}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
@ -2,84 +2,17 @@
|
|||||||
<a class="btn btn-default btn-back active" href="/ghost/settings/">Back</a>
|
<a class="btn btn-default btn-back active" href="/ghost/settings/">Back</a>
|
||||||
<h2 class="page-title">Tags</h2>
|
<h2 class="page-title">Tags</h2>
|
||||||
<section class="page-actions">
|
<section class="page-actions">
|
||||||
<button type="button" class="btn btn-green">New Tag</button>
|
<button type="button" class="btn btn-green" {{action "newTag"}}>New Tag</button>
|
||||||
<span class="tags-search">
|
|
||||||
<button href="#" class="btn btn-default">
|
|
||||||
<i class="icon-search"></i>
|
|
||||||
<span class="hidden">Search Tags</span>
|
|
||||||
</button>
|
|
||||||
<input type="text" class="tags-search-input">
|
|
||||||
</span>
|
|
||||||
</section>
|
</section>
|
||||||
</header>
|
</header>
|
||||||
|
|
||||||
<section class="content settings-tags">
|
<section class="content settings-tags">
|
||||||
{{#each}}
|
{{#each tag in tags}}
|
||||||
<div class="settings-tag">
|
<div class="settings-tag">
|
||||||
<a href="#" class="tag-title">{{name}}</a>
|
<button {{action "editTag" tag}} class="tag-title">{{tag.name}}</button>
|
||||||
<span class="label label-default">/{{slug}}</span>
|
<span class="label label-default">/{{tag.slug}}</span>
|
||||||
<p class="tag-description">{{description}}</p>
|
<p class="tag-description">{{tag.description}}</p>
|
||||||
<span class="tags-count">N/A</span>
|
<span class="tags-count">N/A</span>
|
||||||
</div>
|
</div>
|
||||||
{{/each}}
|
{{/each}}
|
||||||
</section>
|
</section>
|
||||||
{{!-- This is the example markup
|
|
||||||
<section class="content settings-tags">
|
|
||||||
|
|
||||||
<div class="settings-tag">
|
|
||||||
<a href="#" class="tag-title">News</a>
|
|
||||||
<span class="label label-default">/news</span>
|
|
||||||
<p class="tag-description">The latest news, reviews and information from around the world</p>
|
|
||||||
<span class="tags-count">20</span>
|
|
||||||
|
|
||||||
<div class="settings-tag">
|
|
||||||
<a href="#" class="tag-title">General</a>
|
|
||||||
<span class="label label-default">/news/general</span>
|
|
||||||
<p class="tag-description">My go-to category when I’m not really sure what else to file news</p>
|
|
||||||
<span class="tags-count">7</span>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="settings-tag">
|
|
||||||
<a href="#" class="tag-title">Image</a>
|
|
||||||
<span class="label label-alt">Private</span>
|
|
||||||
<p class="tag-description">All posts with the “image” post format</p>
|
|
||||||
<span class="tags-count">12</span>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="settings-tag">
|
|
||||||
<a href="#" class="tag-title">Kittens</a>
|
|
||||||
<span class="label label-default">/kittens</span>
|
|
||||||
<p class="tag-description">My sordid past and wrongdoings</p>
|
|
||||||
<span class="tags-count">9</span>
|
|
||||||
|
|
||||||
<div class="settings-tag">
|
|
||||||
<a href="#" class="tag-title">A Short History of Nearly Everything</a>
|
|
||||||
<span class="label label-default">/kittens/a-short-history</span>
|
|
||||||
<span class="tags-count">4</span>
|
|
||||||
|
|
||||||
<div class="settings-tag">
|
|
||||||
<a href="#" class="tag-title">In Parts</a>
|
|
||||||
<span class="label label-default">/kittens/a-short-history/in-parts</span>
|
|
||||||
<p class="tag-description">Lorem ipsum kittens innit</p>
|
|
||||||
<span class="tags-count">2</span>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="settings-tag">
|
|
||||||
<a href="#" class="tag-title">Video</a>
|
|
||||||
<span class="label label-default">Private</span>
|
|
||||||
<p class="tag-description">All posts containing a YouTube video link</p>
|
|
||||||
<span class="tags-count">6</span>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="settings-tag">
|
|
||||||
<a href="#" class="tag-title">The End</a>
|
|
||||||
<span class="label label-default">/the-end</span>
|
|
||||||
<p class="tag-description">The final frontier</p>
|
|
||||||
<span class="tags-count">1</span>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
</section>
|
|
||||||
--}}
|
|
34
core/client/templates/settings/tags/settings-menu.hbs
Normal file
34
core/client/templates/settings/tags/settings-menu.hbs
Normal file
@ -0,0 +1,34 @@
|
|||||||
|
<div class="content-cover" {{action "closeTagEditor"}}></div>
|
||||||
|
<div class="settings-menu-container">
|
||||||
|
<div class="settings-menu settings-menu-pane settings-menu-pane-in">
|
||||||
|
<div class="settings-menu-header">
|
||||||
|
<h4>Tag Settings</h4>
|
||||||
|
<button class="close icon-x settings-menu-header-action" {{action "closeTagEditor"}}>
|
||||||
|
<span class="hidden">Close</span>
|
||||||
|
</button>
|
||||||
|
</div>
|
||||||
|
<div class="settings-menu-content">
|
||||||
|
<form>
|
||||||
|
<div class="form-group">
|
||||||
|
<label>Tag Name</label>
|
||||||
|
{{input type="text" value=activeTag.name}}
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-group">
|
||||||
|
<label>Slug</label>{{!--@TODO show full url preview, not just slug--}}
|
||||||
|
{{input type="text" value=activeTag.slug}}
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-group">
|
||||||
|
<label>Description</label>
|
||||||
|
{{textarea value=activeTag.description}}
|
||||||
|
</div>
|
||||||
|
|
||||||
|
{{#unless activeTag.isNew}}
|
||||||
|
<button class="btn btn-red icon-trash" {{action "deleteTag" activeTag}}>Delete Tag</button>
|
||||||
|
{{/unless}}
|
||||||
|
<button class="btn btn-green tag-save-button" {{action "saveTag" activeTag}}>{{view.saveText}}</button>
|
||||||
|
</form>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
@ -1,5 +1,6 @@
|
|||||||
import BaseView from 'ghost/views/settings/content-base';
|
import BaseView from 'ghost/views/settings/content-base';
|
||||||
|
import PaginationScrollMixin from 'ghost/mixins/pagination-view-infinite-scroll';
|
||||||
|
|
||||||
var SettingsTagsView = BaseView.extend();
|
var SettingsTagsView = BaseView.extend(PaginationScrollMixin);
|
||||||
|
|
||||||
export default SettingsTagsView;
|
export default SettingsTagsView;
|
||||||
|
9
core/client/views/settings/tags/settings-menu.js
Normal file
9
core/client/views/settings/tags/settings-menu.js
Normal file
@ -0,0 +1,9 @@
|
|||||||
|
var TagsSettingsMenuView = Ember.View.extend({
|
||||||
|
saveText: Ember.computed('controller.model.isNew', function () {
|
||||||
|
return this.get('controller.model.isNew') ?
|
||||||
|
'Add Tag' :
|
||||||
|
'Save Tag';
|
||||||
|
})
|
||||||
|
});
|
||||||
|
|
||||||
|
export default TagsSettingsMenuView;
|
Loading…
Reference in New Issue
Block a user