Merge "Policy types schemas should only be parsed once"
diff --git a/dashboard/webapp-frontend/src/app/interfaces/policy.types.ts b/dashboard/webapp-frontend/src/app/interfaces/policy.types.ts
index ee0c447..e694bb6 100644
--- a/dashboard/webapp-frontend/src/app/interfaces/policy.types.ts
+++ b/dashboard/webapp-frontend/src/app/interfaces/policy.types.ts
@@ -24,6 +24,7 @@
   policy_type_id: number;
   name: string;
   schema: string;
+  schemaObject: any;
 }
 
 export interface PolicyInstance {
diff --git a/dashboard/webapp-frontend/src/app/policy-control/policy-control.component.html b/dashboard/webapp-frontend/src/app/policy-control/policy-control.component.html
index e71fd8a..f185207 100644
--- a/dashboard/webapp-frontend/src/app/policy-control/policy-control.component.html
+++ b/dashboard/webapp-frontend/src/app/policy-control/policy-control.component.html
@@ -24,7 +24,7 @@
     class="policy-type-table mat-elevation-z8">
 
     <ng-container matColumnDef="name">
-        <mat-header-cell *matHeaderCellDef mat-sort-header>Policy Type</mat-header-cell>
+        <mat-header-cell *matHeaderCellDef>Policy Type</mat-header-cell>
         <mat-cell *matCellDef="let policyType">
             <mat-icon matTooltip="Properties">{{isInstancesShown(policyType)  ? 'expand_less' : 'expand_more'}}
             </mat-icon>
@@ -34,7 +34,7 @@
 
     <ng-container matColumnDef="description">
         <mat-header-cell *matHeaderCellDef> Description </mat-header-cell>
-        <mat-cell *matCellDef="let policyType"> {{this.getDescription(policyType)}}
+        <mat-cell *matCellDef="let policyType"> {{policyType.schemaObject.description}}
         </mat-cell>
     </ng-container>
 
diff --git a/dashboard/webapp-frontend/src/app/policy-control/policy-control.component.ts b/dashboard/webapp-frontend/src/app/policy-control/policy-control.component.ts
index d57019f..a81fb2e 100644
--- a/dashboard/webapp-frontend/src/app/policy-control/policy-control.component.ts
+++ b/dashboard/webapp-frontend/src/app/policy-control/policy-control.component.ts
@@ -91,11 +91,8 @@
     }
 
     toggleListInstances(policyType: PolicyType): void {
-        console.log('1toggleListInstances ' + + policyType.name + ' ' + this.getPolicyTypeInfo(policyType).isExpanded.getValue());
         const info = this.getPolicyTypeInfo(policyType);
         info.isExpanded.next(!info.isExpanded.getValue());
-        console.log('2toggleListInstances ' + + policyType.name + ' ' + this.getPolicyTypeInfo(policyType).isExpanded.getValue());
-
     }
 
     getPolicyTypeInfo(policyType: PolicyType): PolicyTypeInfo {
@@ -107,13 +104,8 @@
         return info;
     }
 
-    getDescription(policyType: PolicyType): string {
-        return JSON.parse(policyType.schema).description;
-    }
-
     getName(policyType: PolicyType): string {
-        const title = JSON.parse(policyType.schema).title;
-        if (title) { return title; }
+        if (policyType.schemaObject.title) { return policyType.schemaObject.title; }
         return policyType.name;
     }
 
diff --git a/dashboard/webapp-frontend/src/app/policy-control/policy-instance-dialog.component.ts b/dashboard/webapp-frontend/src/app/policy-control/policy-instance-dialog.component.ts
index f929342..d69400d 100644
--- a/dashboard/webapp-frontend/src/app/policy-control/policy-instance-dialog.component.ts
+++ b/dashboard/webapp-frontend/src/app/policy-control/policy-instance-dialog.component.ts
@@ -94,7 +94,8 @@
         this.policyInstanceId = data.instanceId;
         this.policyTypeName = data.name;
         this.policyTypeId = data.policyTypeId;
-        this.parseJson(data.createSchema, data.instanceJson);
+        this.jsonSchemaObject = data.createSchema;
+        this.jsonObject = this.parseJson(data.instanceJson);
     }
 
     ngOnInit() {
@@ -174,18 +175,17 @@
         return errorArray.join('<br>');
     }
 
-    private parseJson(createSchema: string, instanceJson: string): void {
+    private parseJson(str: string): string {
         try {
-            this.jsonSchemaObject = JSON.parse(createSchema);
-            if (instanceJson != null) {
-                this.jsonObject = JSON.parse(instanceJson);
+            if (str != null) {
+                return JSON.parse(str);
             }
         } catch (jsonError) {
             this.jsonFormStatusMessage =
                 'Invalid JSON\n' +
                 'parser returned:\n\n' + jsonError;
-            return;
         }
+        return null;
     }
 
     public toggleVisible(item: string) {
@@ -195,7 +195,7 @@
 
 export function getPolicyDialogProperties(policyType: PolicyType, instance: PolicyInstance, darkMode: boolean): MatDialogConfig {
     const policyTypeId = policyType.policy_type_id;
-    const createSchema = policyType.schema;
+    const createSchema = policyType.schemaObject;
     const instanceId = instance ? instance.instanceId : null;
     const instanceJson = instance ? instance.instance : null;
     const name = policyType.name;
diff --git a/dashboard/webapp-frontend/src/app/policy-control/policy-type.datasource.ts b/dashboard/webapp-frontend/src/app/policy-control/policy-type.datasource.ts
index 1b2b93e..8d9dec7 100644
--- a/dashboard/webapp-frontend/src/app/policy-control/policy-type.datasource.ts
+++ b/dashboard/webapp-frontend/src/app/policy-control/policy-type.datasource.ts
@@ -58,6 +58,10 @@
             )
             .subscribe((types: PolicyType[]) => {
                 this.rowCount = types.length;
+                for (let i = 0; i < types.length; i++) {
+                    const policyType = types[i];
+                    policyType.schemaObject = JSON.parse(policyType.schema);
+                }
                 this.policyTypeSubject.next(types);
             });
     }