0
Fork 0
mirror of https://github.com/TryGhost/Ghost.git synced 2025-02-10 23:36:14 -05:00

🎨 fix previos/current date comparison (isEqual in bookshelf) (#8357)

no issue

- client dates are sent as ISO format (moment(..).format())
- server dates are in JS Date format
  >> when bookshelf fetches data from the database, all dates are transformed into JS dates
  >> see `parse` helper function
- Bookshelf updates the model with the client data via Bookshelf's `set` function
- therefor Bookshelf uses a simple `isEqual` function from lodash to detect changes
- .previous(attr) and .get(attr) return false
- that has the concequence that dates are always marked as "changed"
- internally we use our `hasDateChanged` if we have to compare previous/updated dates
- but Bookshelf is not in our control for this case
This commit is contained in:
Katharina Irrgang 2017-04-19 10:59:09 +02:00 committed by GitHub
parent f7393686f8
commit f2fd075075
2 changed files with 44 additions and 10 deletions

View file

@ -308,14 +308,51 @@ ghostBookshelf.Model = ghostBookshelf.Model.extend({
/** /**
* Filters potentially unsafe model attributes, so you can pass them to Bookshelf / Knex. * Filters potentially unsafe model attributes, so you can pass them to Bookshelf / Knex.
* This filter should be called before each insert/update operation.
*
* @param {Object} data Has keys representing the model's attributes/fields in the database. * @param {Object} data Has keys representing the model's attributes/fields in the database.
* @return {Object} The filtered results of the passed in data, containing only what's allowed in the schema. * @return {Object} The filtered results of the passed in data, containing only what's allowed in the schema.
*/ */
filterData: function filterData(data) { filterData: function filterData(data) {
var permittedAttributes = this.prototype.permittedAttributes(), var permittedAttributes = this.prototype.permittedAttributes(),
filteredData = _.pick(data, permittedAttributes); filteredData = _.pick(data, permittedAttributes),
sanitizedData = this.sanitizeData(filteredData);
return filteredData; return sanitizedData;
},
/**
* `sanitizeData` ensures that client data is in the correct format for further operations.
*
* Dates:
* - client dates are sent as ISO format (moment(..).format())
* - server dates are in JS Date format
* >> when bookshelf fetches data from the database, all dates are in JS Dates
* >> see `parse`
* - Bookshelf updates the model with the new client data via the `set` function
* - Bookshelf uses a simple `isEqual` function from lodash to detect real changes
* - .previous(attr) and .get(attr) returns false obviously
* - internally we use our `hasDateChanged` if we have to compare previous/updated dates
* - but Bookshelf is not in our control for this case
*
* @IMPORTANT
* Before the new client data get's inserted again, the dates get's retransformed into
* proper strings, see `format`.
*/
sanitizeData: function sanitizeData(data) {
var tableName = _.result(this.prototype, 'tableName');
_.each(data, function (value, key) {
if (value !== null
&& schema.tables[tableName].hasOwnProperty(key)
&& schema.tables[tableName][key].type === 'dateTime'
&& typeof value === 'string'
) {
data[key] = moment(value).toDate();
}
});
return data;
}, },
/** /**

View file

@ -528,19 +528,16 @@ Post = ghostBookshelf.Model.extend({
}, },
/** /**
* Filters potentially unsafe model attributes, so you can pass them to Bookshelf / Knex. * Manually add 'tags' attribute since it's not in the schema and call parent.
*
* @param {Object} data Has keys representing the model's attributes/fields in the database. * @param {Object} data Has keys representing the model's attributes/fields in the database.
* @return {Object} The filtered results of the passed in data, containing only what's allowed in the schema. * @return {Object} The filtered results of the passed in data, containing only what's allowed in the schema.
*/ */
filterData: function filterData(data) { filterData: function filterData(data) {
var permittedAttributes = this.prototype.permittedAttributes(), var filteredData = ghostBookshelf.Model.filterData.apply(this, arguments),
filteredData; extraData = _.pick(data, ['tags']);
// manually add 'tags' attribute since it's not in the schema
permittedAttributes.push('tags');
filteredData = _.pick(data, permittedAttributes);
_.merge(filteredData, extraData);
return filteredData; return filteredData;
}, },