[CORD-1630] Adding model verbose_name and description

Change-Id: If50b38f0328f59852c6ac0a925fb724fdf86782e
diff --git a/src/app/core/services/helpers/config.helpers.spec.ts b/src/app/core/services/helpers/config.helpers.spec.ts
index ed1cc3b..f06fc4f 100644
--- a/src/app/core/services/helpers/config.helpers.spec.ts
+++ b/src/app/core/services/helpers/config.helpers.spec.ts
@@ -76,7 +76,9 @@
       name: 'updated',
       validators: []
     },
-  ]
+  ],
+  description: '',
+  verbose_name: ''
 };
 
 describe('The ConfigHelpers service', () => {
@@ -190,7 +192,7 @@
 
   describe('the modelFieldsToColumnsCfg method', () => {
     it('should return an array of columns', () => {
-      const cols = service.modelFieldsToColumnsCfg({fields: model.fields, name: 'testUrl', app: 'test'});
+      const cols = service.modelFieldsToColumnsCfg({fields: model.fields, name: 'testUrl', app: 'test', description: '', verbose_name: ''});
       expect(cols[0].label).toBe('Id');
       expect(cols[0].prop).toBe('id');
       expect(cols[0].link).toBeDefined();
diff --git a/src/app/datasources/helpers/model-discoverer.service.ts b/src/app/datasources/helpers/model-discoverer.service.ts
index bab0873..c6dcb7e 100644
--- a/src/app/datasources/helpers/model-discoverer.service.ts
+++ b/src/app/datasources/helpers/model-discoverer.service.ts
@@ -37,6 +37,8 @@
   clientUrl?: string; // the view url
   tableCfg?: IXosTableCfg;
   formCfg?: IXosFormCfg;
+  description: string;
+  verbose_name: string;
 }
 
 // Service
@@ -237,8 +239,9 @@
     const parentState: string = this.getParentStateFromModel(model);
 
     try {
+      const name = model.verbose_name ? model.verbose_name : model.name;
       this.XosNavigationService.add({
-        label: this.ConfigHelpers.pluralize(model.name),
+        label: this.ConfigHelpers.pluralize(name),
         state: stateName,
         parent: parentState
       });
diff --git a/src/app/datasources/helpers/model.discoverer.service.spec.ts b/src/app/datasources/helpers/model.discoverer.service.spec.ts
index 94a98e6..7a9e54f 100644
--- a/src/app/datasources/helpers/model.discoverer.service.spec.ts
+++ b/src/app/datasources/helpers/model.discoverer.service.spec.ts
@@ -31,7 +31,9 @@
     ],
     relations: [],
     name: 'Node',
-    app: 'core'
+    app: 'core',
+    description: '',
+    verbose_name: ''
   },
   {
     fields: [
@@ -40,7 +42,9 @@
     ],
     relations: [],
     name: 'VSGTenant',
-    app: 'service.vsg'
+    app: 'service.vsg',
+    description: '',
+    verbose_name: ''
   }
 ];
 
@@ -130,7 +134,9 @@
     const model = {
       name: 'Node',
       app: 'core',
-      fields: []
+      fields: [],
+      description: '',
+      verbose_name: ''
     };
     expect(service.getApiUrlFromModel(model)).toBe('/core/nodes');
   });
@@ -139,7 +145,9 @@
     const model = {
       name: 'Tenant',
       app: 'services.test',
-      fields: []
+      fields: [],
+      description: '',
+      verbose_name: ''
     };
     expect(service.getApiUrlFromModel(model)).toBe('/test/tenants');
   });
@@ -239,6 +247,13 @@
       state: 'xos.vsg.tenant',
       parent: 'xos.vsg'
     });
+
+    service['addNavItem']({name: 'Tenant', verbose_name: 'Verbose', app: 'services.vsg'});
+    expect(MockXosNavigationService.add).toHaveBeenCalledWith({
+      label: 'Verboses',
+      state: 'xos.vsg.tenant',
+      parent: 'xos.vsg'
+    });
   });
 
   it('should cache a model', () => {
diff --git a/src/app/datasources/helpers/search.service.ts b/src/app/datasources/helpers/search.service.ts
index 66748b1..80cef29 100644
--- a/src/app/datasources/helpers/search.service.ts
+++ b/src/app/datasources/helpers/search.service.ts
@@ -66,7 +66,7 @@
   public search(query: string): IXosSearchResult[] {
     this.$log.debug(`[XosSearchService] Searching for: ${query}`);
     const routes: IXosSearchResult[] = _.filter(this.states, s => {
-      return s.label.toLowerCase().indexOf(query) > -1;
+      return s.label.toLowerCase().indexOf(query.toLowerCase()) > -1;
     }).map(r => {
       r.type = 'View';
       return r;
diff --git a/src/app/datasources/rest/modeldefs.rest.ts b/src/app/datasources/rest/modeldefs.rest.ts
index 981cac2..300b71b 100644
--- a/src/app/datasources/rest/modeldefs.rest.ts
+++ b/src/app/datasources/rest/modeldefs.rest.ts
@@ -42,6 +42,8 @@
   relations?: IXosModelDefsRelation[];
   name: string;
   app: string;
+  description: string;
+  verbose_name: string;
 }
 
 export interface IXosModeldefsService {
diff --git a/src/app/views/crud/crud.html b/src/app/views/crud/crud.html
index adeaaa4..b347c31 100644
--- a/src/app/views/crud/crud.html
+++ b/src/app/views/crud/crud.html
@@ -22,16 +22,17 @@
             <div class="pull-right text-right" style="line-height: 14px">
                 <!--<small>UI Elements<br>General<br> <span class="c-white">Grid system</span></small>-->
                 <a class="btn btn-default" ng-if="vm.list" href="{{vm.baseUrl}}add">Add</a>
-                <a class="btn btn-default" ng-if="!vm.list" href="{{vm.baseUrl}}">Back to {{vm.title.toLowerCase()}} list</a>
+                <a class="btn btn-default" ng-if="!vm.list" href="{{vm.baseUrl}}">Back to {{vm.pluralTitle.toLowerCase()}} list</a>
             </div>
             <div class="header-icon">
                 <i class="pe page-header-icon pe-7s-note2"></i>
             </div>
             <div class="header-title">
-                <h3>{{vm.title}}</h3>
-                <!--<small>-->
-                    <!--Responsive, mobile first fluid grid system.-->
-                <!--</small>-->
+                <h3 ng-if="vm.list">{{vm.pluralTitle}}</h3>
+                <h3 ng-if="!vm.list">{{vm.singularTitle}}</h3>
+                <small>
+                    {{vm.modelDef.description}}
+                </small>
             </div>
         </div>
         <hr>
diff --git a/src/app/views/crud/crud.ts b/src/app/views/crud/crud.ts
index 325790f..bcac6a9 100644
--- a/src/app/views/crud/crud.ts
+++ b/src/app/views/crud/crud.ts
@@ -22,7 +22,7 @@
 import * as _ from 'lodash';
 import {IXosResourceService} from '../../datasources/rest/model.rest';
 import {IStoreHelpersService} from '../../datasources/helpers/store.helpers';
-import {IXosModelDiscovererService} from '../../datasources/helpers/model-discoverer.service';
+import {IXosModelDiscovererService, IXosModel} from '../../datasources/helpers/model-discoverer.service';
 import './crud.scss';
 import {IXosCrudRelationService} from './crud.relations.service';
 import {IXosDebugService, IXosDebugStatus} from '../../core/debug/debug.service';
@@ -57,9 +57,12 @@
   public formCfg: any;
   public baseUrl: string;
   public list: boolean;
-  public title: string;
+  public modelName: string;
+  public pluralTitle: string;
+  public singularTitle: string;
   public tableData: any[];
-  public model: any;
+  public model: any; // holds the real model
+  public modelDef: IXosModel;
   public related: {manytoone: IXosModelRelation[], onetomany: IXosModelRelation[]} = {
     manytoone: [],
     onetomany: []
@@ -87,16 +90,18 @@
     this.$log.info('[XosCrud] Setup', $state.current.data);
 
     this.data = this.$state.current.data;
-    this.model = this.XosModelDiscovererService.get(this.data.model);
-    this.title = this.ConfigHelpers.pluralize(this.data.model);
+    this.modelDef = this.XosModelDiscovererService.get(this.data.model);
+    this.modelName = this.modelDef.verbose_name ? this.modelDef.verbose_name : this.modelDef.name;
+    this.pluralTitle = this.ConfigHelpers.pluralize(this.modelName);
+    this.singularTitle = this.ConfigHelpers.pluralize(this.modelName, 1);
 
     this.list = true;
 
     // TODO get the proper URL from model discoverer
-    this.baseUrl = '#/' + this.model.clientUrl.replace(':id?', '');
+    this.baseUrl = '#/' + this.modelDef.clientUrl.replace(':id?', '');
 
-    this.tableCfg = this.model.tableCfg;
-    this.formCfg = this.model.formCfg;
+    this.tableCfg = this.modelDef.tableCfg;
+    this.formCfg = this.modelDef.formCfg;
 
     this.debugTab = this.XosDebug.status.modelsTab;
     this.$scope.$on('xos.debug.status', (e, status: IXosDebugStatus) => {
@@ -109,7 +114,6 @@
         (event) => {
           // NOTE Observable mess with $digest cycles, we need to schedule the expression later
           $scope.$evalAsync(() => {
-            this.title = this.ConfigHelpers.pluralize(this.data.model, event.length);
             this.tableData = event;
 
             // if it is a detail page for an existing model