mirror of
https://github.com/strapi/strapi.git
synced 2025-11-02 19:04:38 +00:00
Improve errors display and display only existing link
This commit is contained in:
parent
744bf74069
commit
06549e6bb7
@ -41,7 +41,9 @@ module.exports = {
|
|||||||
default:
|
default:
|
||||||
throw {
|
throw {
|
||||||
status: 403,
|
status: 403,
|
||||||
body: 'Invalid HTTP method'
|
body: {
|
||||||
|
message: 'Invalid HTTP method'
|
||||||
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@ -69,22 +71,30 @@ module.exports = {
|
|||||||
if (!body.hasOwnProperty('data')) {
|
if (!body.hasOwnProperty('data')) {
|
||||||
throw {
|
throw {
|
||||||
status: 403,
|
status: 403,
|
||||||
body: 'Missing `data` member'
|
body: {
|
||||||
|
message: 'Missing `data` member'
|
||||||
|
}
|
||||||
};
|
};
|
||||||
} else if (!utils.isRessourceObject(body.data) && ctx.method !== 'POST') {
|
} else if (!utils.isRessourceObject(body.data) && ctx.method !== 'POST') {
|
||||||
throw {
|
throw {
|
||||||
status: 403,
|
status: 403,
|
||||||
body: 'Invalid ressource object'
|
body: {
|
||||||
|
message: 'Invalid ressource object'
|
||||||
|
}
|
||||||
};
|
};
|
||||||
} else if (!body.data.hasOwnProperty('type') && ctx.method === 'POST') {
|
} else if (!body.data.hasOwnProperty('type') && ctx.method === 'POST') {
|
||||||
throw {
|
throw {
|
||||||
status: 403,
|
status: 403,
|
||||||
body: 'Invalid ressource object'
|
body: {
|
||||||
|
message: 'Invalid ressource object'
|
||||||
|
}
|
||||||
};
|
};
|
||||||
} else if (!strapi.models.hasOwnProperty(body.data.type)) {
|
} else if (!strapi.models.hasOwnProperty(body.data.type)) {
|
||||||
throw {
|
throw {
|
||||||
status: 403,
|
status: 403,
|
||||||
body: 'Unknow `type` ' + body.data.type
|
body: {
|
||||||
|
message: 'Unknow `type` ' + body.data.type
|
||||||
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -98,7 +108,9 @@ module.exports = {
|
|||||||
if (!_.isEmpty(missingAttributes)) {
|
if (!_.isEmpty(missingAttributes)) {
|
||||||
throw {
|
throw {
|
||||||
status: 403,
|
status: 403,
|
||||||
body: 'Missing required attributes (' + missingAttributes.toString() + ')'
|
body: {
|
||||||
|
message: 'Missing required attributes (' + missingAttributes.toString() + ')'
|
||||||
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -112,7 +124,9 @@ module.exports = {
|
|||||||
if (!_.isEmpty(missingRelationships)) {
|
if (!_.isEmpty(missingRelationships)) {
|
||||||
throw {
|
throw {
|
||||||
status: 403,
|
status: 403,
|
||||||
body: 'Missing required relationships (' + missingRelationships.toString() + ')'
|
body: {
|
||||||
|
message: 'Missing required relationships (' + missingRelationships.toString() + ')'
|
||||||
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -120,15 +134,22 @@ module.exports = {
|
|||||||
if (_.size(requiredRelationships)) {
|
if (_.size(requiredRelationships)) {
|
||||||
const errors = _.remove(_.flattenDeep(_.map(body.data.relationships, function (relation, key) {
|
const errors = _.remove(_.flattenDeep(_.map(body.data.relationships, function (relation, key) {
|
||||||
if (!relation.hasOwnProperty('data')) {
|
if (!relation.hasOwnProperty('data')) {
|
||||||
return 'Missing `data` member for relationships ' + relation;
|
return {
|
||||||
|
message: 'Missing `data` member for relationships ' + relation
|
||||||
|
};
|
||||||
} else if (_.isArray(relation.data)) {
|
} else if (_.isArray(relation.data)) {
|
||||||
return _.map(relation.data, function (ressource) {
|
return _.map(relation.data, function (ressource, position) {
|
||||||
if (!utils.isRessourceObject(ressource)) {
|
if (!utils.isRessourceObject(ressource)) {
|
||||||
return 'Invalid ressource object in relationships ' + key;
|
return {
|
||||||
|
position: position,
|
||||||
|
message: 'Invalid ressource object in relationships ' + key
|
||||||
|
};
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
} else if (!utils.isRessourceObject(relation.data)) {
|
} else if (!utils.isRessourceObject(relation.data)) {
|
||||||
return 'Invalid ressource object for relationships ' + key;
|
return {
|
||||||
|
message: 'Invalid ressource object for relationships ' + key
|
||||||
|
};
|
||||||
}
|
}
|
||||||
})), function (n) {
|
})), function (n) {
|
||||||
return !_.isUndefined(n);
|
return !_.isUndefined(n);
|
||||||
@ -137,7 +158,7 @@ module.exports = {
|
|||||||
if (!_.isEmpty(errors)) {
|
if (!_.isEmpty(errors)) {
|
||||||
throw {
|
throw {
|
||||||
status: 403,
|
status: 403,
|
||||||
body: errors.toString()
|
body: errors
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -31,18 +31,20 @@ module.exports = {
|
|||||||
ctx.response.status = 404;
|
ctx.response.status = 404;
|
||||||
ctx.response.body = '';
|
ctx.response.body = '';
|
||||||
|
|
||||||
return false;
|
return;
|
||||||
} else if (ctx.method === 'DELETE') {
|
} else if (ctx.method === 'DELETE') {
|
||||||
// Request successful and responds with only top-level meta data or nothing.
|
// Request successful and responds with only top-level meta data or nothing.
|
||||||
ctx.response.body = '';
|
ctx.response.body = '';
|
||||||
|
|
||||||
return false;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Fetch and format value
|
// Fetch and format value
|
||||||
const value = this.fetchValue(ctx, object);
|
const value = this.fetchValue(ctx, object);
|
||||||
|
|
||||||
ctx.response.body = this.serialize(ctx, type, object, value);
|
if (!_.isEmpty(value)) {
|
||||||
|
ctx.response.body = this.serialize(ctx, type, object, value);
|
||||||
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -132,6 +134,11 @@ module.exports = {
|
|||||||
if (strapi.models.hasOwnProperty(type)) {
|
if (strapi.models.hasOwnProperty(type)) {
|
||||||
_.forEach(strapi.models[type].associations, function (relation) {
|
_.forEach(strapi.models[type].associations, function (relation) {
|
||||||
const PK = utils.getPK(relation.model) || utils.getPK(relation.collection);
|
const PK = utils.getPK(relation.model) || utils.getPK(relation.collection);
|
||||||
|
const availableRoutes = {
|
||||||
|
relSlSelf: utils.isRoute('GET /' + type + '/:' + PK + '/relationships/:relation'),
|
||||||
|
relSlRelated: utils.isRoute('GET /' + type + '/:' + PK),
|
||||||
|
incSelf: relation.model ? utils.isRoute('GET /' + relation.model + '/:' + PK) : utils.isRoute('GET /' + relation.collection + '/:' + PK)
|
||||||
|
};
|
||||||
|
|
||||||
switch (relation.nature) {
|
switch (relation.nature) {
|
||||||
case 'oneToOne':
|
case 'oneToOne':
|
||||||
@ -139,24 +146,30 @@ module.exports = {
|
|||||||
// Object
|
// Object
|
||||||
toSerialize[relation.alias] = {
|
toSerialize[relation.alias] = {
|
||||||
ref: PK,
|
ref: PK,
|
||||||
attributes: _.keys(strapi.models[type].attributes),
|
attributes: _.keys(_.omit(strapi.models[type].attributes, _.isFunction)),
|
||||||
relationshipLinks: {
|
relationshipLinks: {
|
||||||
self: function (record) {
|
self: function (record) {
|
||||||
if (record.hasOwnProperty(PK)) {
|
if (record.hasOwnProperty(PK) && availableRoutes.relSlSelf) {
|
||||||
return ctx.request.origin + '/' + type + '/' + record[PK] + '/relationships/' + relation.alias;
|
return ctx.request.origin + '/' + type + '/' + record[PK] + '/relationships/' + relation.alias;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return undefined;
|
||||||
},
|
},
|
||||||
related: function (record) {
|
related: function (record) {
|
||||||
if (record.hasOwnProperty(PK)) {
|
if (record.hasOwnProperty(PK) && availableRoutes.relSlRelated) {
|
||||||
return ctx.request.origin + '/' + type + '/' + record[PK];
|
return ctx.request.origin + '/' + type + '/' + record[PK];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return undefined;
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
includedLinks: {
|
includedLinks: {
|
||||||
self: function (data, record) {
|
self: function (data, record) {
|
||||||
if (!_.isUndefined(record) && record.hasOwnProperty(PK)) {
|
if (!_.isUndefined(record) && record.hasOwnProperty(PK) && availableRoutes.incSelf) {
|
||||||
return ctx.request.origin + '/' + relation.model + '/' + record[PK];
|
return ctx.request.origin + '/' + relation.model + '/' + record[PK];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return undefined;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
@ -167,24 +180,30 @@ module.exports = {
|
|||||||
toSerialize[relation.alias] = {
|
toSerialize[relation.alias] = {
|
||||||
ref: PK,
|
ref: PK,
|
||||||
typeForAttribute: relation.collection,
|
typeForAttribute: relation.collection,
|
||||||
attributes: _.keys(strapi.models[type].attributes),
|
attributes: _.keys(_.omit(strapi.models[type].attributes, _.isFunction)),
|
||||||
relationshipLinks: {
|
relationshipLinks: {
|
||||||
self: function (record) {
|
self: function (record) {
|
||||||
if (record.hasOwnProperty(PK)) {
|
if (record.hasOwnProperty(PK) && availableRoutes.relSlSelf) {
|
||||||
return ctx.request.origin + '/' + type + '/' + record[PK] + '/relationships/' + relation.alias;
|
return ctx.request.origin + '/' + type + '/' + record[PK] + '/relationships/' + relation.alias;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return undefined;
|
||||||
},
|
},
|
||||||
related: function (record) {
|
related: function (record) {
|
||||||
if (record.hasOwnProperty(PK)) {
|
if (record.hasOwnProperty(PK) && availableRoutes.relSlRelated) {
|
||||||
return ctx.request.origin + '/' + type + '/' + record[PK];
|
return ctx.request.origin + '/' + type + '/' + record[PK];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return undefined;
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
includedLinks: {
|
includedLinks: {
|
||||||
self: function (data, record) {
|
self: function (data, record) {
|
||||||
if (record.hasOwnProperty(PK)) {
|
if (record.hasOwnProperty(PK) && availableRoutes.incSelf) {
|
||||||
return ctx.request.origin + '/' + relation.collection + '/' + record[PK];
|
return ctx.request.origin + '/' + relation.collection + '/' + record[PK];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return undefined;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|||||||
@ -31,6 +31,9 @@ module.exports = function (strapi) {
|
|||||||
|
|
||||||
// Exclude administration routes
|
// Exclude administration routes
|
||||||
if (this.request.url.indexOf('admin') === -1) {
|
if (this.request.url.indexOf('admin') === -1) {
|
||||||
|
// Set the required header
|
||||||
|
this.response.type = 'application/vnd.api+json';
|
||||||
|
|
||||||
// Verify Content-Type header
|
// Verify Content-Type header
|
||||||
if (this.request.type !== 'application/vnd.api+json') {
|
if (this.request.type !== 'application/vnd.api+json') {
|
||||||
this.status = 406;
|
this.status = 406;
|
||||||
@ -56,7 +59,7 @@ module.exports = function (strapi) {
|
|||||||
} else {
|
} else {
|
||||||
// Intercept error requests
|
// Intercept error requests
|
||||||
this.body = {
|
this.body = {
|
||||||
error: this.body
|
errors: this.body
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -21,6 +21,14 @@ module.exports = {
|
|||||||
return _.isObject(object) && object.hasOwnProperty('id') && object.hasOwnProperty('type');
|
return _.isObject(object) && object.hasOwnProperty('id') && object.hasOwnProperty('type');
|
||||||
},
|
},
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Verify if the route exists
|
||||||
|
*/
|
||||||
|
|
||||||
|
isRoute: function (link) {
|
||||||
|
return strapi.config.routes.hasOwnProperty(link);
|
||||||
|
},
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Find data object
|
* Find data object
|
||||||
*/
|
*/
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user