aarondfrancis / vue-model

Model component for Vue.js
MIT License
857 stars 42 forks source link

JSON-API style errors #30

Open markkimsal opened 4 years ago

markkimsal commented 4 years ago

Json API defines errors like this

  "errors": [
    {
      "code":   "123",
      "status": "422",
      "source": { "pointer": "/data/attributes/firstName" },
      "title":  "Value is too short",
      "detail": "First name must contain at least three characters."
    },
    {
      "code":   "225",
      "status": "304",
      "source": { "pointer": "/data/attributes/password" },
      "title": "Passwords must contain a letter, number, and punctuation character.",
      "detail": "The password provided is missing a punctuation character."
    },
    {
      "code":   "226",
      "status": "200",
      "source": { "pointer": "/data/attributes/password" },
      "title": "Password and password confirmation do not match."
    }
  ]

I sub-classed the Model to customize my own setValidationErrors (awesome that injecting your own model definition is possible btw)

const Model = require('vue-model/src/Model.js');

Model.prototype.setValidationErrors = function(error) {

    var http = this.settings.http;
    if (!http.isValidationError(error)) {
        return;
    }
    var errors = http.getErrorsFromResponse(error.response);
    //filter for json-api compatibility
    var flippedErrors = {};
    for (const idx in errors) {
        const err = errors[idx];
        if (err.status == 422) {
            flippedErrors[err.source] = err.details;
        }
    }

    // errorKey can be a dot delimited path
    Vue.setNested(this.data, http.errorKey, new this.classes.errors(flippedErrors));
}
module.exports = Model;

(I don't use the source: { pointer: '/schema/string'} style, just regular string as the field name)

It would be awesome to support this style of error response out of the box.