blob: 41f3d76ada7aac5f32a1eea2f4bd2cafd0accad8 [file] [log] [blame]
kumaran.m3b4814a2020-05-01 19:48:54 +05301/*
2 Copyright 2020 TATA ELXSI
3
4 Licensed under the Apache License, Version 2.0 (the 'License');
5 you may not use this file except in compliance with the License.
6 You may obtain a copy of the License at
7
8 http://www.apache.org/licenses/LICENSE-2.0
9
10 Unless required by applicable law or agreed to in writing, software
11 distributed under the License is distributed on an "AS IS" BASIS,
12 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 See the License for the specific language governing permissions and
14 limitations under the License.
15
16 Author: KUMARAN M (kumaran.m@tataelxsi.co.in), RAJESH S (rajesh.s@tataelxsi.co.in), BARATH KUMAR R (barath.r@tataelxsi.co.in)
17 */
18/**
19 * @file Provider for Shared Service
20 */
21import { HttpErrorResponse, HttpHeaders } from '@angular/common/http';
22import { EventEmitter, Injectable, Output } from '@angular/core';
23import { FormArray, FormGroup } from '@angular/forms';
24import { Router } from '@angular/router';
25import { CONSTANTNUMBER, ERRORDATA, GETAPIURLHEADER, PACKAGEINFO, PAGERSMARTTABLE, SMARTTABLECLASS, TARSETTINGS } from 'CommonModel';
26import { environment } from 'environment';
27import * as HttpStatus from 'http-status-codes';
28import * as untar from 'js-untar';
29import * as pako from 'pako';
30import { RestService } from 'RestService';
31import { isNullOrUndefined } from 'util';
32
33/** This is added globally by the tar.js library */
34// tslint:disable-next-line: no-any
35declare const Tar: any;
36
37/**
38 * An Injectable is a class adorned with the @Injectable decorator function.
39 * @Injectable takes a metadata object that tells Angular how to compile and run module code
40 */
41@Injectable({
42 providedIn: 'root'
43})
44/** Exporting a class @exports SharedService */
45export class SharedService {
46 /** call the parent using event information @private */
47 @Output() public dataEvent: EventEmitter<{}> = new EventEmitter<{}>();
48
49 /** Variables to hold regexp pattern for URL */
50 // tslint:disable-next-line: max-line-length
51 public REGX_URL_PATTERN: RegExp = new RegExp(/^(http?|ftp|https):\/\/([a-zA-Z0-9.-]+(:[a-zA-Z0-9.&%$-]+)*@)*((25[0-5]|2[0-4][0-9]|1[0-9]{2}|[1-9][0-9]?)(\.(25[0-5]|2[0-4][0-9]|1[0-9]{2}|[1-9]?[0-9])){3}|([a-zA-Z0-9-]+\.)*[a-zA-Z0-9-]+\.[a-zA-Z0-9]{2,15})(:((6553[0-5])|(655[0-2][0-9])|(65[0-4][0-9]{2})|(6[0-4][0-9]{3})|([1-5][0-9]{4})|([0-5]{0,5})|([0-9]{1,4})))*(\/($|[a-zA-Z0-9.,?'\\+&%$#=~_-]+))*$/);
52
53 /** Variables to hold regexp pattern for IP Address */
54 public REGX_IP_PATTERN: RegExp = new RegExp(/^(?:(25[0-5]|2[0-4][0-9]|1[0-9]{2}|[1-9]?[0-9])(\.(?!$)|$)){4}$/);
55
56 /** Variables to hold regexp pattern for Port Number */
57 // tslint:disable-next-line: max-line-length
58 public REGX_PORT_PATTERN: RegExp = new RegExp(/^((6553[0-5])|(655[0-2][0-9])|(65[0-4][0-9]{2})|(6[0-4][0-9]{3})|([1-5][0-9]{4})|([0-5]{0,5})|([0-9]{1,4}))$/);
59
60 /** Variables to hold regexp pattern for DPID */
61 public REGX_DPID_PATTERN: RegExp = new RegExp(/^[0-9a-fA-F]{2}(:[0-9a-fA-F]{2}){7}$/);
62
63 /** Variable to hold regexp pattern for password */
64 // tslint:disable-next-line: max-line-length
65 public REGX_PASSWORD_PATTERN: RegExp = new RegExp(/^.*(?=.{8,})((?=.*[!@#$%^&*()\-_=+{};:,<.>]){1})(?=.*\d)((?=.*[a-z]){1})((?=.*[A-Z]){1}).*$/);
66
Barath Kumar R403234e2020-07-07 15:48:58 +053067 /** Variables to hold maxlength for the description @public */
68 public MAX_LENGTH_DESCRIPTION: number = 500;
69
70 /** Variables to hold maxlength for the name @public */
71 public MAX_LENGTH_NAME: number = 50;
72
kumaran.m3b4814a2020-05-01 19:48:54 +053073 /** FormGroup instance added to the form @ html @public */
74 public formGroup: FormGroup;
75
76 /** Controls the go to top button on scroll @public */
77 public showGotoTop: boolean;
78
79 /** Holds OSM Version value @public */
80 public osmVersion: string;
81
82 /** express number for time manupulation -2 */
83 private epochTimeMinus2: number = -2;
84
85 /** express number for time manupulation 1000 */
86 private epochTime1000: number = 1000;
87
88 /** Random string generator length */
89 private randomStringLength: number = 4;
90
91 /** Instance of the rest service @private */
92 private restService: RestService;
93
94 /** Service holds the router information @private */
95 private router: Router;
96
Barath Kumar R208bef22020-07-07 12:28:04 +053097 /** Random color string generator length @private */
98 private colorStringLength: number = 256;
99
kumaran.m3b4814a2020-05-01 19:48:54 +0530100 /** Check for the root directory @private */
101 private directoryCount: number = 2;
102
103 constructor(restService: RestService, router: Router) {
104 this.restService = restService;
105 this.router = router;
106 }
107
108 /** convert epoch time function @public */
109 public convertEpochTime(unixtimestamp: number): string {
110 const monthsArr: string[] = ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun',
111 'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec'];
112 const date: Date = new Date(unixtimestamp * this.epochTime1000);
113 const year: number = date.getFullYear();
114 const month: string = monthsArr[date.getMonth()];
115 const day: number = date.getDate();
116 const hours: number = date.getHours();
117 const minutes: string = '0' + date.getMinutes();
118 const seconds: string = '0' + date.getSeconds();
119 return month + '-' + day + '-' + year + ' ' + hours + ':' + minutes.substr(this.epochTimeMinus2) + ':'
120 + seconds.substr(this.epochTimeMinus2);
121 }
122
123 /** Download Files function @public */
124 public downloadFiles(shortName: string, binaryData: Blob[], filetype: string): void {
125 const downloadLink: HTMLAnchorElement = document.createElement('a');
126 downloadLink.href = window.URL.createObjectURL(new Blob(binaryData, { type: filetype }));
127 if (shortName !== undefined) {
128 if (window.navigator.msSaveOrOpenBlob) {
129 window.navigator.msSaveBlob(new Blob(binaryData, { type: filetype }), 'OSM_Export_' + shortName + '.tar.gz');
130 } else {
131 downloadLink.setAttribute('download', 'OSM_Export_' + shortName + '.tar.gz');
132 document.body.appendChild(downloadLink);
133 downloadLink.click();
134 }
135 }
136 }
137
138 /** Call this method after delete perform action is completed in the ng-smart-table data @public */
139 public callData(): void {
140 this.dataEvent.emit();
141 }
142
143 /** Generate random string @public */
144 public randomString(): string {
145 const chars: string = '0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ';
146 let result: string = '';
147 // tslint:disable-next-line:no-increment-decrement
148 for (let randomStringRef: number = this.randomStringLength; randomStringRef > 0; --randomStringRef) {
149 result += chars[Math.floor(Math.random() * chars.length)];
150 }
151 return result;
152 }
153 /** Function to read uploaded file String @public */
154 public async getFileString(files: FileList, fileType: string): Promise<string | ArrayBuffer> {
155 const reader: FileReader = new FileReader();
156 return new Promise<string | ArrayBuffer>((resolve: Function, reject: Function): void => {
157 if (this.vaildataFileInfo(files[0], fileType)) {
158 this.readFileContent(reader, files[0], fileType);
159 } else {
160 reject('typeError');
161 }
162 reader.onload = (): void => {
163 if (reader.result === null) {
164 reject('contentError');
165 }
166 resolve(reader.result);
167 };
168 reader.onerror = (event: Event): void => {
169 reject('contentError');
170 };
171 });
172 }
173 /** Method to handle tar and tar.gz file for shared YAML file content @public */
174 public async targzFile(packageInfo: PACKAGEINFO): Promise<string | ArrayBuffer> {
175 return new Promise<string | ArrayBuffer>((resolve: Function, reject: Function): void => {
176 const httpOptions: GETAPIURLHEADER = this.getHttpOptions();
177 let apiUrl: string = '';
178 apiUrl = packageInfo.packageType === 'nsd' ? environment.NSDESCRIPTORS_URL + '/' + packageInfo.id + '/nsd_content' :
179 environment.VNFPACKAGES_URL + '/' + packageInfo.id + '/package_content';
180 this.restService.getResource(apiUrl, httpOptions).subscribe((response: ArrayBuffer) => {
181 try {
182 // tslint:disable-next-line: no-any
183 const tar: any = new Tar();
184 const originalInput: Uint8Array = pako.inflate(response, { to: 'Uint8Array' });
185 untar(originalInput.buffer).then((extractedFiles: TARSETTINGS[]) => {
186 const getFoldersFiles: {}[] = extractedFiles;
187 const folderNameStr: string = extractedFiles[0].name;
188 getFoldersFiles.forEach((value: TARSETTINGS) => {
189 const getRootFolder: string[] = value.name.split('/');
190 if (value.name.startsWith(folderNameStr) &&
191 (value.name.endsWith('.yaml') || value.name.endsWith('.yml')) &&
192 getRootFolder.length === this.directoryCount) {
193 tar.append(value.name, packageInfo.descriptor, { type: value.type });
194 } else {
195 if (value.type !== 'L') {
196 tar.append(value.name, new Uint8Array(value.buffer), { type: value.type });
197 }
198 }
199 });
200 const out: Uint8Array = tar.out;
201 const originalOutput: Uint8Array = pako.gzip(out);
202 resolve(originalOutput.buffer);
203 }, (err: string) => {
204 reject('');
205 });
206 } catch (e) {
207 reject('');
208 }
209 }, (error: HttpErrorResponse) => {
210 if (error.status === HttpStatus.NOT_FOUND || error.status === HttpStatus.UNAUTHORIZED) {
211 this.router.navigateByUrl('404', { skipLocationChange: true }).catch();
212 } else {
213 this.restService.handleError(error, 'get');
214 reject('');
215 }
216 });
217 });
218 }
219 /** Method to check given string is JSON or not @public */
220 public checkJson(jsonString: string): boolean {
221 jsonString = jsonString.replace(/'/g, '"');
222 try {
223 JSON.parse(jsonString);
224 } catch (e) {
225 return false;
226 }
227 return true;
228 }
229 /** Clean the form before submit @public */
Barath Kumar Rd477b852020-07-07 15:24:05 +0530230 public cleanForm(formGroup: FormGroup, formName?: String): void {
kumaran.m3b4814a2020-05-01 19:48:54 +0530231 Object.keys(formGroup.controls).forEach((key: string) => {
Barath Kumar Rd477b852020-07-07 15:24:05 +0530232 if ((!isNullOrUndefined((formGroup.get(key) as FormArray | FormGroup).controls)) && key !== 'config') {
kumaran.m3b4814a2020-05-01 19:48:54 +0530233 // tslint:disable-next-line: no-shadowed-variable
234 for (const { item, index } of (formGroup.get(key).value).map((item: {}, index: number) => ({ item, index }))) {
235 const newFormGroup: FormGroup = (formGroup.get(key) as FormArray).controls[index] as FormGroup;
236 this.cleanForm(newFormGroup);
237 }
Barath Kumar Rd477b852020-07-07 15:24:05 +0530238 } else if (formGroup.get(key).value !== undefined && formGroup.get(key).value !== null && key !== 'config') {
kumaran.m3b4814a2020-05-01 19:48:54 +0530239 if (!Array.isArray(formGroup.get(key).value)) {
240 if (typeof formGroup.get(key).value === 'string') {
241 formGroup.get(key).setValue(formGroup.get(key).value.trim());
242 }
243 }
Barath Kumar Rd477b852020-07-07 15:24:05 +0530244 } else if (key === 'config' && formName === 'vim') {
kumaran.m3b4814a2020-05-01 19:48:54 +0530245 const newFormGroup: FormGroup = formGroup.get(key) as FormGroup;
246 this.cleanForm(newFormGroup);
247 }
248 });
249 }
250 /** Method to return the config of pager value for ngSmarttable @public */
251 public paginationPagerConfig(): PAGERSMARTTABLE {
252 return {
253 display: true,
254 perPage: environment.paginationNumber
255 };
256 }
257 /** Method to return the class for the table for ngSmarttable @public */
258 public tableClassConfig(): SMARTTABLECLASS {
259 return {
260 class: 'table list-data'
261 };
262 }
263 /** Method to return all languages name and its code @public */
264 public languageCodeList(): {}[] {
265 return [
266 { code: 'en', language: 'English' },
267 { code: 'es', language: 'Spanish' },
268 { code: 'pt', language: 'Portuguese' },
269 { code: 'de', language: 'German' }
270 ];
271 }
272 /** Fetch OSM Version @public */
273 public fetchOSMVersion(): void {
274 this.restService.getResource(environment.OSM_VERSION_URL).subscribe((res: { version: string }) => {
275 const version: string[] = res.version.split('+');
276 if (!isNullOrUndefined(version[0])) {
277 this.osmVersion = version[0];
278 } else {
279 this.osmVersion = null;
280 }
281 }, (error: ERRORDATA) => {
282 this.osmVersion = null;
283 this.restService.handleError(error, 'get');
284 });
285 }
Barath Kumar R208bef22020-07-07 12:28:04 +0530286 /** Random RGB color code generator @public */
287 public generateColor(): string {
288 const x: number = Math.floor(Math.random() * this.colorStringLength);
289 const y: number = Math.floor(Math.random() * this.colorStringLength);
290 const z: number = Math.floor(Math.random() * this.colorStringLength);
291 return 'rgb(' + x + ',' + y + ',' + z + ')';
292 }
Barath Kumar Rd477b852020-07-07 15:24:05 +0530293
294 /** Add custom name/tag to the dropdown @public */
295 public addCustomTag(tag: string): string {
296 return tag;
297 }
298
kumaran.m3b4814a2020-05-01 19:48:54 +0530299 /** Method to validate file extension and size @private */
300 private vaildataFileInfo(fileInfo: File, fileType: string): boolean {
301 const extension: string = fileInfo.name.substring(fileInfo.name.lastIndexOf('.') + 1);
302 const packageSize: number = CONSTANTNUMBER.oneMB * environment.packageSize;
Barath Kumar Rd477b852020-07-07 15:24:05 +0530303 if (fileType === 'yaml' && (extension.toLowerCase() === 'yaml' || extension.toLowerCase() === 'yml')
304 && fileInfo.size <= packageSize) {
305 return true;
306 } else if (extension.toLowerCase() === fileType && fileInfo.size <= packageSize) {
kumaran.m3b4814a2020-05-01 19:48:54 +0530307 return true;
308 }
309 return false;
310 }
311 /** Method to read file content based on type @private */
312 private readFileContent(reader: FileReader, fileInfo: File, fileType: string): void {
313 if (fileType === 'gz') {
314 reader.readAsArrayBuffer(fileInfo);
315 } else {
316 reader.readAsText(fileInfo);
317 }
318 }
319 /** Method to handle http options @public */
320 private getHttpOptions(): GETAPIURLHEADER {
321 return {
322 headers: new HttpHeaders({
323 Accept: 'application/gzip, application/json',
324 'Cache-Control': 'no-cache, no-store, must-revalidate, max-age=0'
325 }),
326 responseType: 'arraybuffer'
327 };
328 }
329}