mirror of
https://github.com/TryGhost/Ghost-Admin.git
synced 2023-12-14 02:33:04 +01:00
Ember Data with Posts
Ref #2699 - Introduce ember data dependency - Add loadInitializers and refactor most initializers into one combined - Add Post ember data model - Refactor generateSlug to use title of post and ghostPaths - Refactor post controller to not reference model.property everywhere - Use RESTAdapter for posts, users and tags - Setup author and tag relations in Post model - Fix broken API calls by adding CSRF header - Add initiaizer for csrf value - Use actual User model for current user initializer - Add action for setting featured post, test with actual api call - Fix the sending of UUID's up to the server - Refactor current-user to use ember-data store - If a user is preloaded in the application, use pushPayload to put it in the store - Do a lookup on the store to get an actual User model for injection - Fix posts/post controllerName in route/new.js - Alter signup process to push user into ember data store
This commit is contained in:
parent
3d02e1c555
commit
20bd112e6d
21 changed files with 244 additions and 204 deletions
22
adapters/application.js
Normal file
22
adapters/application.js
Normal file
|
@ -0,0 +1,22 @@
|
|||
import ghostPaths from 'ghost/utils/ghost-paths';
|
||||
|
||||
// export default DS.FixtureAdapter.extend({});
|
||||
|
||||
export default DS.RESTAdapter.extend({
|
||||
host: window.location.origin,
|
||||
namespace: ghostPaths().apiRoot.slice(1),
|
||||
headers: {
|
||||
'X-CSRF-Token': $('meta[name="csrf-param"]').attr('content')
|
||||
},
|
||||
|
||||
buildURL: function (type, id) {
|
||||
// Ensure trailing slashes
|
||||
var url = this._super(type, id);
|
||||
|
||||
if (url.slice(-1) !== '/') {
|
||||
url += '/';
|
||||
}
|
||||
|
||||
return url;
|
||||
}
|
||||
});
|
15
app.js
15
app.js
|
@ -1,13 +1,11 @@
|
|||
import Resolver from 'ember/resolver';
|
||||
import initFixtures from 'ghost/fixtures/init';
|
||||
import injectCurrentUser from 'ghost/initializers/current-user';
|
||||
import injectCsrf from 'ghost/initializers/csrf';
|
||||
import {registerNotifications, injectNotifications} from 'ghost/initializers/notifications';
|
||||
import registerTrailingLocationHistory from 'ghost/initializers/trailing-history';
|
||||
import injectGhostPaths from 'ghost/initializers/ghost-paths';
|
||||
import loadInitializers from 'ember/load-initializers';
|
||||
import 'ghost/utils/link-view';
|
||||
import 'ghost/utils/text-field';
|
||||
|
||||
Ember.MODEL_FACTORY_INJECTIONS = true;
|
||||
|
||||
var App = Ember.Application.extend({
|
||||
/**
|
||||
* These are debugging flags, they are useful during development
|
||||
|
@ -23,11 +21,6 @@ var App = Ember.Application.extend({
|
|||
|
||||
initFixtures();
|
||||
|
||||
App.initializer(injectCurrentUser);
|
||||
App.initializer(injectCsrf);
|
||||
App.initializer(injectGhostPaths);
|
||||
App.initializer(registerNotifications);
|
||||
App.initializer(injectNotifications);
|
||||
App.initializer(registerTrailingLocationHistory);
|
||||
loadInitializers(App, 'ghost');
|
||||
|
||||
export default App;
|
||||
|
|
|
@ -13,49 +13,26 @@ var PostController = Ember.ObjectController.extend({
|
|||
isDraft: equal('status', 'draft'),
|
||||
willPublish: Ember.computed.oneWay('isPublished'),
|
||||
isStaticPage: function (key, val) {
|
||||
var self = this;
|
||||
|
||||
if (arguments.length > 1) {
|
||||
this.set('model.page', val ? 1 : 0);
|
||||
this.get('model').save('page').then(function () {
|
||||
this.notifications.showSuccess('Succesfully converted ' + (val ? 'to static page' : 'to post'));
|
||||
this.set('page', val ? 1 : 0);
|
||||
|
||||
return this.get('model').save().then(function () {
|
||||
self.notifications.showSuccess('Succesfully converted to ' + (val ? 'static page' : 'post'));
|
||||
|
||||
return !!self.get('page');
|
||||
}, this.notifications.showErrors);
|
||||
}
|
||||
return !!this.get('model.page');
|
||||
}.property('model.page'),
|
||||
|
||||
isOnServer: function () {
|
||||
return this.get('model.id') !== undefined;
|
||||
}.property('model.id'),
|
||||
return !!this.get('page');
|
||||
}.property('page'),
|
||||
|
||||
newSlugBinding: Ember.Binding.oneWay('model.slug'),
|
||||
slugPlaceholder: null,
|
||||
// Requests a new slug when the title was changed
|
||||
updateSlugPlaceholder: function () {
|
||||
var model,
|
||||
self = this,
|
||||
title = this.get('title');
|
||||
newSlugBinding: Ember.computed.oneWay('slug'),
|
||||
|
||||
// If there's a title present we want to
|
||||
// validate it against existing slugs in the db
|
||||
// and then update the placeholder value.
|
||||
if (title) {
|
||||
model = self.get('model');
|
||||
model.generateSlug().then(function (slug) {
|
||||
self.set('slugPlaceholder', slug);
|
||||
}, function () {
|
||||
self.notifications.showWarn('Unable to generate a slug for "' + title + '"');
|
||||
});
|
||||
} else {
|
||||
// If there's no title set placeholder to blank
|
||||
// and don't make an ajax request to server
|
||||
// for a proper slug (as there won't be any).
|
||||
self.set('slugPlaceholder', '');
|
||||
}
|
||||
}.observes('model.title'),
|
||||
|
||||
publishedAt: null,
|
||||
publishedAtChanged: function () {
|
||||
this.set('publishedAt', formatDate(this.get('model.published_at')));
|
||||
}.observes('model.published_at'),
|
||||
slugPlaceholder: function () {
|
||||
return this.get('model').generateSlug();
|
||||
}.property('title'),
|
||||
|
||||
actions: {
|
||||
save: function () {
|
||||
|
@ -78,6 +55,11 @@ var PostController = Ember.ObjectController.extend({
|
|||
console.warn('Received invalid save type; ignoring.');
|
||||
}
|
||||
},
|
||||
toggleFeatured: function () {
|
||||
this.set('featured', !this.get('featured'));
|
||||
|
||||
this.get('model').save();
|
||||
},
|
||||
editSettings: function () {
|
||||
var isEditing = this.toggleProperty('isEditingSettings');
|
||||
if (isEditing) {
|
||||
|
@ -91,9 +73,10 @@ var PostController = Ember.ObjectController.extend({
|
|||
});
|
||||
}
|
||||
},
|
||||
|
||||
updateSlug: function () {
|
||||
var newSlug = this.get('newSlug'),
|
||||
slug = this.get('model.slug'),
|
||||
slug = this.get('slug'),
|
||||
placeholder = this.get('slugPlaceholder'),
|
||||
self = this;
|
||||
|
||||
|
@ -110,17 +93,17 @@ var PostController = Ember.ObjectController.extend({
|
|||
}
|
||||
|
||||
//Validation complete
|
||||
this.set('model.slug', newSlug);
|
||||
this.set('slug', newSlug);
|
||||
|
||||
// If the model doesn't currently
|
||||
// exist on the server
|
||||
// then just update the model's value
|
||||
if (!this.get('isOnServer')) {
|
||||
if (!this.get('isNew')) {
|
||||
return;
|
||||
}
|
||||
|
||||
this.get('model').save('slug').then(function () {
|
||||
self.notifications.showSuccess('Permalink successfully changed to <strong>' + this.get('model.slug') + '</strong>.');
|
||||
|
||||
this.get('model').save().then(function () {
|
||||
self.notifications.showSuccess('Permalink successfully changed to <strong>' + this.get('slug') + '</strong>.');
|
||||
}, this.notifications.showErrors);
|
||||
},
|
||||
|
||||
|
@ -182,20 +165,20 @@ var PostController = Ember.ObjectController.extend({
|
|||
}
|
||||
|
||||
//Validation complete
|
||||
this.set('model.published_at', newPubDateMoment.toDate());
|
||||
this.set('published_at', newPubDateMoment.toDate());
|
||||
|
||||
// If the model doesn't currently
|
||||
// exist on the server
|
||||
// then just update the model's value
|
||||
if (!this.get('isOnServer')) {
|
||||
if (!this.get('isNew')) {
|
||||
return;
|
||||
}
|
||||
|
||||
this.get('model').save('published_at').then(function () {
|
||||
this.get('model').save().then(function () {
|
||||
this.notifications.showSuccess('Publish date successfully changed to <strong>' + this.get('publishedAt') + '</strong>.');
|
||||
}, this.notifications.showErrors);
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
export default PostController;
|
||||
export default PostController;
|
||||
|
|
11
initializers/csrf-token.js
Normal file
11
initializers/csrf-token.js
Normal file
|
@ -0,0 +1,11 @@
|
|||
export default {
|
||||
name: 'csrf-token',
|
||||
|
||||
initialize: function (container) {
|
||||
container.register('csrf:token', $('meta[name="csrf-param"]').attr('content'), { instantiate: false });
|
||||
|
||||
container.injection('route', 'csrf', 'csrf:token');
|
||||
container.injection('model', 'csrf', 'csrf:token');
|
||||
container.injection('controller', 'csrf', 'csrf:token');
|
||||
}
|
||||
};
|
|
@ -1,14 +1,34 @@
|
|||
import User from 'ghost/models/user';
|
||||
|
||||
export default {
|
||||
name: 'currentUser',
|
||||
after: 'store',
|
||||
|
||||
initialize: function (container, application) {
|
||||
var user = User.create(application.get('user') || {});
|
||||
var store = container.lookup('store:main'),
|
||||
preloadedUser = application.get('user');
|
||||
|
||||
container.register('user:current', user, { instantiate: false });
|
||||
// If we don't have a user, don't do the injection
|
||||
if (!preloadedUser) {
|
||||
return;
|
||||
}
|
||||
|
||||
container.injection('route', 'user', 'user:current');
|
||||
container.injection('controller', 'user', 'user:current');
|
||||
// Push the preloaded user into the data store
|
||||
store.pushPayload({
|
||||
users: [preloadedUser]
|
||||
});
|
||||
|
||||
// Signal to wait until the user is loaded before continuing.
|
||||
application.deferReadiness();
|
||||
|
||||
// Find the user (which should be fast since we just preloaded it in the store)
|
||||
store.find('user', preloadedUser.id).then(function (user) {
|
||||
// Register the value for injection
|
||||
container.register('user:current', user, { instantiate: false });
|
||||
|
||||
// Inject into the routes and controllers as the user property.
|
||||
container.injection('route', 'user', 'user:current');
|
||||
container.injection('controller', 'user', 'user:current');
|
||||
|
||||
application.advanceReadiness();
|
||||
});
|
||||
}
|
||||
};
|
|
@ -2,6 +2,7 @@ import ghostPaths from 'ghost/utils/ghost-paths';
|
|||
|
||||
export default {
|
||||
name: 'ghost-paths',
|
||||
after: 'store',
|
||||
|
||||
initialize: function (container) {
|
||||
container.register('ghost:paths', ghostPaths(), {instantiate: false});
|
||||
|
|
|
@ -1,21 +1,13 @@
|
|||
import Notifications from 'ghost/utils/notifications';
|
||||
|
||||
var registerNotifications = {
|
||||
name: 'registerNotifications',
|
||||
|
||||
initialize: function (container, application) {
|
||||
application.register('notifications:main', Notifications);
|
||||
}
|
||||
};
|
||||
|
||||
var injectNotifications = {
|
||||
export default {
|
||||
name: 'injectNotifications',
|
||||
|
||||
initialize: function (container, application) {
|
||||
application.register('notifications:main', Notifications);
|
||||
|
||||
application.inject('controller', 'notifications', 'notifications:main');
|
||||
application.inject('component', 'notifications', 'notifications:main');
|
||||
application.inject('route', 'notifications', 'notifications:main');
|
||||
}
|
||||
};
|
||||
|
||||
export {registerNotifications, injectNotifications};
|
||||
};
|
|
@ -1,56 +1,45 @@
|
|||
import BaseModel from 'ghost/models/base';
|
||||
|
||||
var PostModel = BaseModel.extend({
|
||||
url: BaseModel.apiRoot + '/posts/',
|
||||
var Post = DS.Model.extend({
|
||||
uuid: DS.attr('string'),
|
||||
title: DS.attr('string'),
|
||||
slug: DS.attr('string'),
|
||||
markdown: DS.attr('string'),
|
||||
html: DS.attr('string'),
|
||||
image: DS.attr('string'),
|
||||
featured: DS.attr('boolean'),
|
||||
page: DS.attr('boolean'),
|
||||
status: DS.attr('string'),
|
||||
language: DS.attr('string'),
|
||||
meta_title: DS.attr('string'),
|
||||
meta_description: DS.attr('string'),
|
||||
author: DS.belongsTo('user', { async: true }),
|
||||
created_at: DS.attr('date'),
|
||||
created_by: DS.belongsTo('user', { async: true }),
|
||||
updated_at: DS.attr('date'),
|
||||
updated_by: DS.belongsTo('user', { async: true }),
|
||||
published_at: DS.attr('date'),
|
||||
published_by: DS.belongsTo('user', { async: true }),
|
||||
tags: DS.hasMany('tag', { async: true }),
|
||||
|
||||
generateSlug: function () {
|
||||
// @TODO Make this request use this.get('title') once we're an actual user
|
||||
var url = this.get('url') + 'slug/' + encodeURIComponent('test title') + '/';
|
||||
var title = this.get('title'),
|
||||
url = this.get('ghostPaths').apiUrl('posts', 'slug', encodeURIComponent(title));
|
||||
|
||||
return ic.ajax.request(url, {
|
||||
type: 'GET'
|
||||
});
|
||||
},
|
||||
|
||||
save: function (properties) {
|
||||
var url = this.url,
|
||||
self = this,
|
||||
type,
|
||||
validationErrors = this.validate();
|
||||
|
||||
if (validationErrors.length) {
|
||||
return Ember.RSVP.Promise(function (resolve, reject) {
|
||||
return reject(validationErrors);
|
||||
type: 'GET'
|
||||
});
|
||||
}
|
||||
|
||||
//If specific properties are being saved,
|
||||
//this is an edit. Otherwise, it's an add.
|
||||
if (properties && properties.length > 0) {
|
||||
type = 'PUT';
|
||||
url += this.get('id');
|
||||
} else {
|
||||
type = 'POST';
|
||||
properties = Ember.keys(this);
|
||||
}
|
||||
|
||||
return ic.ajax.request(url, {
|
||||
type: type,
|
||||
data: this.getProperties(properties)
|
||||
}).then(function (model) {
|
||||
return self.setProperties(model);
|
||||
});
|
||||
},
|
||||
validate: function () {
|
||||
|
||||
validationErrors: function () {
|
||||
var validationErrors = [];
|
||||
|
||||
if (!(this.get('title') && this.get('title').length)) {
|
||||
if (!this.get('title.length')) {
|
||||
validationErrors.push({
|
||||
message: "You must specify a title for the post."
|
||||
});
|
||||
}
|
||||
|
||||
return validationErrors;
|
||||
}
|
||||
}.property('title')
|
||||
});
|
||||
|
||||
export default PostModel;
|
||||
export default Post;
|
13
models/tag.js
Normal file
13
models/tag.js
Normal file
|
@ -0,0 +1,13 @@
|
|||
export default DS.Model.extend({
|
||||
uuid: DS.attr('string'),
|
||||
name: DS.attr('string'),
|
||||
slug: DS.attr('string'),
|
||||
description: DS.attr('string'),
|
||||
parent_id: DS.attr('number'),
|
||||
meta_title: DS.attr('string'),
|
||||
meta_description: DS.attr('string'),
|
||||
created_at: DS.attr('date'),
|
||||
created_by: DS.attr('number'),
|
||||
updated_at: DS.attr('date'),
|
||||
updated_by: DS.attr('number'),
|
||||
});
|
|
@ -1,24 +1,28 @@
|
|||
import BaseModel from 'ghost/models/base';
|
||||
|
||||
var UserModel = BaseModel.extend({
|
||||
id: null,
|
||||
name: null,
|
||||
image: null,
|
||||
var User = DS.Model.extend({
|
||||
uuid: DS.attr('string'),
|
||||
name: DS.attr('string'),
|
||||
slug: DS.attr('string'),
|
||||
password: DS.attr('string'),
|
||||
email: DS.attr('string'),
|
||||
image: DS.attr('string'),
|
||||
cover: DS.attr('string'),
|
||||
bio: DS.attr('string'),
|
||||
website: DS.attr('string'),
|
||||
location: DS.attr('string'),
|
||||
accessibility: DS.attr('string'),
|
||||
status: DS.attr('string'),
|
||||
language: DS.attr('string'),
|
||||
meta_title: DS.attr('string'),
|
||||
meta_description: DS.attr('string'),
|
||||
last_login: DS.attr('date'),
|
||||
created_at: DS.attr('date'),
|
||||
created_by: DS.attr('number'),
|
||||
updated_at: DS.attr('date'),
|
||||
updated_by: DS.attr('number'),
|
||||
|
||||
isSignedIn: Ember.computed.bool('id'),
|
||||
|
||||
url: BaseModel.apiRoot + '/users/me/',
|
||||
forgottenUrl: BaseModel.apiRoot + '/forgotten/',
|
||||
resetUrl: BaseModel.apiRoot + '/reset/',
|
||||
|
||||
save: function () {
|
||||
return ic.ajax.request(this.url, {
|
||||
type: 'POST',
|
||||
data: this.getProperties(Ember.keys(this))
|
||||
});
|
||||
},
|
||||
|
||||
validate: function () {
|
||||
validationErrors: function () {
|
||||
var validationErrors = [];
|
||||
|
||||
if (!validator.isLength(this.get('name'), 0, 150)) {
|
||||
|
@ -44,25 +48,20 @@ var UserModel = BaseModel.extend({
|
|||
}
|
||||
}
|
||||
|
||||
if (validationErrors.length > 0) {
|
||||
this.set('isValid', false);
|
||||
} else {
|
||||
this.set('isValid', true);
|
||||
}
|
||||
return validationErrors;
|
||||
}.property('name', 'bio', 'email', 'location', 'website'),
|
||||
|
||||
this.set('errors', validationErrors);
|
||||
|
||||
return this;
|
||||
},
|
||||
isValid: Ember.computed.empty('validationErrors.[]'),
|
||||
|
||||
saveNewPassword: function (password) {
|
||||
return ic.ajax.request(BaseModel.subdir + '/ghost/changepw/', {
|
||||
var url = this.get('ghostPaths').adminUrl('changepw');
|
||||
return ic.ajax.request(url, {
|
||||
type: 'POST',
|
||||
data: password
|
||||
});
|
||||
},
|
||||
|
||||
validatePassword: function (password) {
|
||||
passwordValidationErrors: function (password) {
|
||||
var validationErrors = [];
|
||||
|
||||
if (!validator.equals(password.newPassword, password.ne2Password)) {
|
||||
|
@ -73,24 +72,17 @@ var UserModel = BaseModel.extend({
|
|||
validationErrors.push("Your password is not long enough. It must be at least 8 characters long.");
|
||||
}
|
||||
|
||||
if (validationErrors.length > 0) {
|
||||
this.set('passwordIsValid', false);
|
||||
} else {
|
||||
this.set('passwordIsValid', true);
|
||||
}
|
||||
|
||||
this.set('passwordErrors', validationErrors);
|
||||
|
||||
return this;
|
||||
return validationErrors;
|
||||
},
|
||||
|
||||
fetchForgottenPasswordFor: function (email) {
|
||||
var self = this;
|
||||
var forgottenUrl = this.get('ghostPaths').apiUrl('forgotten');
|
||||
|
||||
return new Ember.RSVP.Promise(function (resolve, reject) {
|
||||
if (!validator.isEmail(email)) {
|
||||
reject(new Error('Please enter a correct email address.'));
|
||||
} else {
|
||||
resolve(ic.ajax.request(self.forgottenUrl, {
|
||||
resolve(ic.ajax.request(forgottenUrl, {
|
||||
type: 'POST',
|
||||
headers: {
|
||||
// @TODO Find a more proper way to do this.
|
||||
|
@ -105,12 +97,14 @@ var UserModel = BaseModel.extend({
|
|||
},
|
||||
|
||||
resetPassword: function (passwords, token) {
|
||||
var self = this;
|
||||
var self = this,
|
||||
resetUrl = this.get('ghostPaths').apiUrl('reset');
|
||||
|
||||
return new Ember.RSVP.Promise(function (resolve, reject) {
|
||||
if (!self.validatePassword(passwords).get('passwordIsValid')) {
|
||||
reject(new Error('Errors found! ' + JSON.stringify(self.get('passwordErrors'))));
|
||||
} else {
|
||||
resolve(ic.ajax.request(self.resetUrl, {
|
||||
resolve(ic.ajax.request(resetUrl, {
|
||||
type: 'POST',
|
||||
headers: {
|
||||
// @TODO: find a more proper way to do this.
|
||||
|
@ -127,4 +121,4 @@ var UserModel = BaseModel.extend({
|
|||
}
|
||||
});
|
||||
|
||||
export default UserModel;
|
||||
export default User;
|
||||
|
|
|
@ -1,15 +1,27 @@
|
|||
var ApplicationRoute = Ember.Route.extend({
|
||||
actions: {
|
||||
signedIn: function (user) {
|
||||
this.container.lookup('user:current').setProperties(user);
|
||||
// Update the user on all routes and controllers
|
||||
this.container.unregister('user:current');
|
||||
this.container.register('user:current', user, { instantiate: false });
|
||||
|
||||
this.container.injection('route', 'user', 'user:current');
|
||||
this.container.injection('controller', 'user', 'user:current');
|
||||
|
||||
this.set('user', user);
|
||||
this.set('controller.user', user);
|
||||
},
|
||||
|
||||
signedOut: function () {
|
||||
this.container.lookup('user:current').setProperties({
|
||||
id: null,
|
||||
name: null,
|
||||
image: null
|
||||
});
|
||||
// Nullify the user on all routes and controllers
|
||||
this.container.unregister('user:current');
|
||||
this.container.register('user:current', null, { instantiate: false });
|
||||
|
||||
this.container.injection('route', 'user', 'user:current');
|
||||
this.container.injection('controller', 'user', 'user:current');
|
||||
|
||||
this.set('user', null);
|
||||
this.set('controller.user', null);
|
||||
},
|
||||
|
||||
openModal: function (modalName, model) {
|
||||
|
|
|
@ -1,6 +1,8 @@
|
|||
var AuthenticatedRoute = Ember.Route.extend({
|
||||
beforeModel: function () {
|
||||
if (!this.get('user.isSignedIn')) {
|
||||
var user = this.container.lookup('user:current');
|
||||
|
||||
if (!user || !user.get('isSignedIn')) {
|
||||
this.notifications.showError('Please sign in');
|
||||
|
||||
this.transitionTo('signin');
|
||||
|
@ -9,7 +11,7 @@ var AuthenticatedRoute = Ember.Route.extend({
|
|||
|
||||
actions: {
|
||||
error: function (error) {
|
||||
if (error.jqXHR.status === 401) {
|
||||
if (error.jqXHR && error.jqXHR.status === 401) {
|
||||
this.transitionTo('signin');
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,14 +1,11 @@
|
|||
import ajax from 'ghost/utils/ajax';
|
||||
import styleBody from 'ghost/mixins/style-body';
|
||||
import AuthenticatedRoute from 'ghost/routes/authenticated';
|
||||
import Post from 'ghost/models/post';
|
||||
|
||||
var EditorRoute = AuthenticatedRoute.extend(styleBody, {
|
||||
classNames: ['editor'],
|
||||
controllerName: 'posts.post',
|
||||
model: function (params) {
|
||||
return ajax('/ghost/api/v0.1/posts/' + params.post_id).then(function (post) {
|
||||
return Post.create(post);
|
||||
});
|
||||
return this.store.find('post', params.post_id);
|
||||
}
|
||||
});
|
||||
|
||||
|
|
|
@ -1,9 +1,8 @@
|
|||
import AuthenticatedRoute from 'ghost/routes/authenticated';
|
||||
import styleBody from 'ghost/mixins/style-body';
|
||||
import Post from 'ghost/models/post';
|
||||
|
||||
var NewRoute = AuthenticatedRoute.extend(styleBody, {
|
||||
controllerName: 'posts/post',
|
||||
controllerName: 'posts.post',
|
||||
classNames: ['editor'],
|
||||
|
||||
renderTemplate: function () {
|
||||
|
@ -11,7 +10,9 @@ var NewRoute = AuthenticatedRoute.extend(styleBody, {
|
|||
},
|
||||
|
||||
model: function () {
|
||||
return Post.create();
|
||||
return this.store.createRecord('post', {
|
||||
title: 'New Post'
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
|
|
|
@ -1,17 +1,11 @@
|
|||
import ajax from 'ghost/utils/ajax';
|
||||
import styleBody from 'ghost/mixins/style-body';
|
||||
import AuthenticatedRoute from 'ghost/routes/authenticated';
|
||||
import Post from 'ghost/models/post';
|
||||
|
||||
var PostsRoute = AuthenticatedRoute.extend(styleBody, {
|
||||
classNames: ['manage'],
|
||||
|
||||
model: function () {
|
||||
return ajax('/ghost/api/v0.1/posts').then(function (response) {
|
||||
return response.posts.map(function (post) {
|
||||
return Post.create(post);
|
||||
});
|
||||
});
|
||||
return this.store.find('post', { status: 'all', staticPages: 'all' });
|
||||
},
|
||||
|
||||
actions: {
|
||||
|
|
|
@ -1,11 +1,5 @@
|
|||
/*global ajax */
|
||||
import Post from 'ghost/models/post';
|
||||
var PostsPostRoute = Ember.Route.extend({
|
||||
export default Ember.Route.extend({
|
||||
model: function (params) {
|
||||
return ajax('/ghost/api/v0.1/posts/' + params.post_id).then(function (post) {
|
||||
return Post.create(post);
|
||||
});
|
||||
return this.store.find('post', params.post_id);
|
||||
}
|
||||
});
|
||||
|
||||
export default PostsPostRoute;
|
||||
|
|
|
@ -15,7 +15,7 @@ var SigninRoute = Ember.Route.extend(styleBody, {
|
|||
if (!isEmpty(data.email) && !isEmpty(data.password)) {
|
||||
|
||||
ajax({
|
||||
url: '/ghost/signin/',
|
||||
url: this.get('ghostPaths').adminUrl('signin'),
|
||||
type: 'POST',
|
||||
headers: {
|
||||
"X-CSRF-Token": this.get('csrf')
|
||||
|
@ -23,11 +23,12 @@ var SigninRoute = Ember.Route.extend(styleBody, {
|
|||
data: data
|
||||
}).then(
|
||||
function (response) {
|
||||
self.send('signedIn', response.userData);
|
||||
|
||||
self.notifications.clear();
|
||||
|
||||
self.transitionTo('posts');
|
||||
self.store.pushPayload({ users: [response.userData]});
|
||||
self.store.find('user', response.userData.id).then(function (user) {
|
||||
self.send('signedIn', user);
|
||||
self.notifications.clear();
|
||||
self.transitionTo('posts');
|
||||
});
|
||||
}, function (resp) {
|
||||
// This path is ridiculous, should be a helper in notifications; e.g. notifications.showAPIError
|
||||
self.notifications.showAPIError(resp, 'There was a problem logging in, please try again.');
|
||||
|
|
|
@ -26,11 +26,12 @@ var SignupRoute = Ember.Route.extend(styleBody, {
|
|||
data: data
|
||||
}).then(function (resp) {
|
||||
if (resp && resp.userData) {
|
||||
self.send('signedIn', resp.userData);
|
||||
|
||||
self.notifications.clear();
|
||||
|
||||
self.transitionTo('posts');
|
||||
self.store.pushPayload({ users: [resp.userData]});
|
||||
self.store.find('user', resp.userData.id).then(function (user) {
|
||||
self.send('signedIn', user);
|
||||
self.notifications.clear();
|
||||
self.transitionTo('posts');
|
||||
});
|
||||
} else {
|
||||
self.transitionTo('signin');
|
||||
}
|
||||
|
|
16
serializers/application.js
Normal file
16
serializers/application.js
Normal file
|
@ -0,0 +1,16 @@
|
|||
export default DS.RESTSerializer.extend({
|
||||
serializeIntoHash: function (hash, type, record, options) {
|
||||
// Our API expects an id on the posted object
|
||||
options = options || {};
|
||||
options.includeId = true;
|
||||
|
||||
// We have a plural root in the API
|
||||
var root = Ember.String.pluralize(type.typeKey),
|
||||
data = this.serialize(record, options);
|
||||
|
||||
// Don't ever pass uuid's
|
||||
delete data.uuid;
|
||||
|
||||
hash[root] = [data];
|
||||
}
|
||||
});
|
|
@ -1,7 +1,7 @@
|
|||
<header class="floatingheader">
|
||||
<button class="button-back" href="#">Back</button>
|
||||
{{!-- @TODO: add back title updates depending on featured state --}}
|
||||
<a {{bind-attr class="featured:featured:unfeatured"}} href="#" title="Feature this post">
|
||||
<a {{bind-attr class="featured:featured:unfeatured"}} href="#" title="Feature this post" {{action "toggleFeatured"}}>
|
||||
<span class="hidden">Star</span>
|
||||
</a>
|
||||
<small>
|
||||
|
|
|
@ -2,7 +2,11 @@
|
|||
<nav>
|
||||
<section id="entry-tags" href="#" class="left">
|
||||
<label class="tag-label" for="tags" title="Tags"><span class="hidden">Tags</span></label>
|
||||
<div class="tags"></div>
|
||||
<div class="tags">
|
||||
{{#each tags}}
|
||||
<span class="tag">{{name}}</span>
|
||||
{{/each}}
|
||||
</div>
|
||||
<input type="hidden" class="tags-holder" id="tags-holder">
|
||||
<input class="tag-input" id="tags" type="text" data-input-behaviour="tag" />
|
||||
<ul class="suggestions overlay"></ul>
|
||||
|
|
Loading…
Reference in a new issue