How to access custom attributes and metadata from Vue.js

I’m using DotNet, Entity framework and Vue.js. Let’s suppose I have a model like

public class ModelA
{
  [CustomAtt]
  public string propertyA { get; set; }
  // ... some other properties 
}

[CustomAtt] could be a model data annotation or any other custom attribute. Then I have a ModelAController that simply returns a 1 modelA; like

{
  "propertyA" : "somevalue"
  // ... some other properties with their values
}

Then I have a crud.vue which look like this:

<template src="./Crud.html"/>

<script>

export default {
  name: 'crud',
  data () {
      return {
      model: ''
      }
  },

  ... CRUD implementation ...

In that crud.vue; how do I access that [CustomAtt] or any other attributes that may be applied to ModelA or to any other properties of ModelA?

Assuming you’ve downloaded the model as JSON, you can just assign it to the data, maybe something like:

axios.get("your-url").then(response => this.model = response.data);

from there bind the properties using v-model attributes in the UI, for example with vuetify you might do something like:

<v-text v-model="model.propertyA"></v-text>

I hope that gets you started!

This allows me to get the data from my model, which is rather easy. But it does not allow me to get the metadata/attribute [CustomAtt]

So far, I thought about using reflection in my back-end to get the attributes and then send both the data itself and the metadata in a DTO. Is there a better way?

Sorry - I’ve no idea what this means

Hi. What is you use case, I mean what are you using the metadata for in the frontend?

To tell the front-end general info about which field/property of a generic model ought to be displayed, how to display each field/property, which field/property is editable, which field/property is optional or required, what front-end validation to apply to each field/property. That sorts of things. As much as possible I want the front-end to be generic and able to deal with generic models. No “hard coding” of my models in the front-end.

For instance if I pass a generic object to my front-end I’d like each field/property to be displayed considering their respective attributes;

  • If a field/property as an attribute [FieldNameToDisplay(“My Field Name”)], then the front-end ought to display “My Field Name” instead of the field/property’s identifier from the model definition;

My field Name : ... some data/value ...

instead of;

propertyA : ... some data/value ...

  • If a field/property as an attribute [NoDisplay], then that field’s data ought not to be displayed.
  • If a field/property as an attribute [DisplayAsList(“Vertical”)], then that field’s data ought to be displayed in a list.vue which is going to display the data as a vertical list.
  • If a field/property as an attribute [DisplayAsMatrix()], then that field’s data ought to be displayed in a matrix.vue which is going to display the data as a matrix.
  • If a field/property has an attribute [Editable(true,10)] then it allows that field/property to be edited as an input text of max length 10.
  • If a field/property has an attribute [Editable(true,dropdownlist)] then it allows that field/property to be edited as a dropdownlist. My front-end would then use a dropdownlist.vue component to display a dropdownlist with the list of element from that field/property. (That component is already done).

So far the only thing missing is an elegant way of passing metadata from the back-end to the front-end.

Nice explination. Now I understand. I don’t enough dotnet to know if you can get these by any other means but by reflection. But maybe this is a little bit of an antipattern. Usually doesn’t the backend know what the frontend will do with or how it will displsy the data. This make the coupling between them very strong. It also make the backend specific and the frontend generic instead of the other way around which usually is. Do you make sense out of my ramblings?