/* * ============LICENSE_START======================================================= * org.onap.aai * ================================================================================ * Copyright © 2017-2021 AT&T Intellectual Property. All rights reserved. * ================================================================================ * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. * ============LICENSE_END========================================================= */ import React, { Component } from 'react'; import Grid from 'react-bootstrap/lib/Grid'; import Row from 'react-bootstrap/lib/Row'; import Col from 'react-bootstrap/lib/Col'; import ModelCard from './ModelCard.jsx'; import Modal from 'react-bootstrap/lib/Modal'; import Button from 'react-bootstrap/lib/Button'; import BootstrapTable from 'react-bootstrap-table-next'; import {ExportExcel} from 'utils/ExportExcel.js'; import filterFactory, { textFilter, customFilter } from 'react-bootstrap-table2-filter'; //import overlayFactory from 'react-bootstrap-table2-overlay'; import OutputVisualization from 'generic-components/OutputVisualization.jsx'; import RelationshipList from './ModelTabularView.jsx'; import PropTypes from 'prop-types'; import Tabs from 'react-bootstrap/lib/Tabs'; import Tab from 'react-bootstrap/lib/Tab'; import commonApi from 'utils/CommonAPIService.js'; import {GlobalExtConstants} from 'utils/GlobalExtConstants.js'; import {GeneralCommonFunctions} from 'utils/GeneralCommonFunctions.js'; import Spinner from 'utils/SpinnerContainer.jsx'; let INVLIST = GlobalExtConstants.INVLIST; let ENVIRONMENT = GlobalExtConstants.ENVIRONMENT; /** * This function will take all of the node objects and turn them into * a ui grid of ModelCard components. This function is essentially a container * for the ModelCards * @param props * @returns {*} */ class AttributeFilter extends Component { constructor(props) { super(props); this.filter = this.filter.bind(this); this.getValue = this.getValue.bind(this); this.props = props; this.state = { filterText: '', isPageChange: this.props.isPageChange, columnValue : '' }; } getValue = () => { return this.input.value; } setPlaceHolder = () => { let filterText = ''; if(filterText === ''){ filterText = 'Enter ' + this.props.column.text; } return filterText; } setFilterValue = () =>{ let filterText = ''; var columnFilter = this.props.columnFilterList[this.props.nodeType][0]; for(var i=0;i { let txt=this.props.column.text; let obj = {}; obj[txt] = this.getValue(); var columnFilterList = this.props.columnFilterList; var columnFilter = columnFilterList[this.props.nodeType][0]; for(var i=0;i this.input = node } type="text" placeholder={this.setPlaceHolder()} // value={this.setFilterValue} onChange={this.filter} /> ) } } class ModelGallery extends Component { constructor(props){ super(props); this.props = props; this.state = { rerender: false, expanded: [], columnFilterList : {}, columnsList: {}, aliasColumnList: {}, nodeType: '', disableFilter: true, showEditNodeModal: false, focusedNode: null, isEditSuccess: false, isWriteAllowed: sessionStorage.getItem(ENVIRONMENT + 'roles') && sessionStorage.getItem(ENVIRONMENT + 'roles').indexOf('ui_write') > -1, editInputFields: [] } } componentWillMount() { console.log('Model gallery component will mount****'); } componentWillUnmount() { console.log('Model Gallery component will unmount****'); } handleOnExpand = (row, isExpand, rowIndex, e) => { console.log('handleOnExpand single Row...',row.id); if (isExpand) { this.setState(() => ({ expanded: [...this.state.expanded,row.id] })); } else { this.setState(() => ({ expanded: this.state.expanded.filter(x => x !== row.id) }),function () { this.forceUpdate(); }.bind(this)); } } handleOnExpandAll = (isExpand, rows, e) => { console.log('handleOnExpandAll to expand all rows'); var expandArr = []; if (isExpand) { for(var r=0; r < rows.length; r++){ expandArr.push(rows[r].id); } } this.setState(() => ({ expanded: expandArr }),function () { this.forceUpdate(); }.bind(this)); } handleOnFilter = (colFilterList,nodeType,columns,value,aliasColumnList) =>{ console.log('handleOnFilter to Re-render',colFilterList); var applyState = true; if(value === ''){ Object.keys(colFilterList).forEach(function(pkey){ var filterList = colFilterList[pkey][0]; for(var j in filterList){ Object.keys(filterList[j]).forEach(function(key){ if(filterList[j][key] !== ''){ applyState = false; } }); } }); }else{ applyState = false; } this.setState({columnFilterList : colFilterList,rerender:true,columnsList : columns,nodeType: nodeType, disableFilter: applyState,aliasColumnList: aliasColumnList}); } generateRegexForDsl= (nodeType) =>{ var nodePatternwithProp = nodeType+"\\*\\{.*?\\}\\(.*?\\)[\\,|\\>|\\]|\\)]|"+nodeType+"\\*\\(.*?\\)\\{.*?\\}[\\,|\\>|\\]|\\)]|"+nodeType+"\\{.*?\\}\\(.*?\\)[\\,|\\>|\\]|\\)]|"+nodeType+"\\(.*?\\)\\{.*?\\}[\\,|\\>|\\]|\\)]|"+nodeType+"\\{.*?\\}[\\,|\\>|\\]|\\)]|"+nodeType+"\\*\\{.*?\\}[\\,|\\>|\\]|\\)]"; return nodePatternwithProp; } /* Start Edit Node Modal Functions */ closeEditNodeModal = () =>{ this.setState({editErrMsg: null, editInfoMsg: null, showEditNodeModal:false}); } submitEditNodeModal = () =>{ var payload = {"operations": []}; const settings = { 'NODESERVER': INVLIST.NODESERVER, 'PROXY': INVLIST.PROXY, 'PREFIX': INVLIST.PREFIX, 'VERSION': INVLIST.VERSION, 'USESTUBS': INVLIST.useStubs, 'APERTURE': INVLIST.APERTURE, 'APERTURE_SERVICENAME':INVLIST.APERTURE_SERVICENAME }; let delimiter = '\/'; let start = 3; if((this.state.focusedNode.url).indexOf("/aperture/v") > -1){ start = 4; } let tokens = (this.state.focusedNode.url).split(delimiter).slice(start); let patchURL = tokens.join(delimiter); var entry = { "action": "patch", "uri": patchURL, "body": {} }; let path = "bulk/single-transaction"; this.setState({editErrMsg: null, isPatchLoading: true}); for(var key in this.state.editInputFields){ if(this.state.editInputFields[key].isEdited){ if(this.state.editInputFields[key].newValue !== ""){ entry.body[key] = encodeURI(this.state.editInputFields[key].newValue); }else{ entry.body[key] = null; } } } payload.operations.push(entry); console.log('ModelGallery: settings:' + JSON.stringify(settings)); console.log('ModelGallery: path:' + path); console.log('ModelGallery: payload:' + JSON.stringify(payload)); commonApi(settings, path, 'POST', payload, 'SingleTransactionEdit', null, null, null, true) .then(res => { console.log('ModelGallery: Response', Object.keys(res.data)); if(res.status === 201 || res.status === 200){ if(res.data["operation-responses"] && res.data["operation-responses"][0] && res.data["operation-responses"][0]["response-status-code"] === 200 ){ this.setState({isEditSuccess: true, isPatchLoading: false, showEditNodeModal:false}); GeneralCommonFunctions.scrollTo("editSuccessMessage"); }else{ this.triggerError(res.data); } }else{ this.triggerError(res.data); } }, error=>{ this.triggerError(error); }).catch(error => { this.triggerError(error); }); } triggerError = (error) => { console.error('[ModelGallery.jsx] error : ', JSON.stringify(error)); let errMsg = this.renderErrorMsg(error); this.setState({ isPatchLoading: false, isEditSuccess: false, editErrMsg: errMsg }); }; renderErrorMsg = (error) =>{ let errMsg=''; if (error.response) { // The request was made and the server responded with a status code // that falls out of the range of 2xx console.log('[ModeGallery.jsx] error :', error.response); if(error.response.status){ errMsg += " Code: " + error.response.status; } if(error.response.data){ errMsg += " - " + JSON.stringify(error.response.data); } } else if (error["requestError"]){ errMsg += JSON.stringify(error["requestError"]); } else if (error.request) { // The request was made but no response was received // `error.request` is an instance of XMLHttpRequest in the browser and an instance of // http.ClientRequest in node.js console.log(error.request); errMsg += " - Request was made but no response received"; } else { // Something happened in setting up the request that triggered an Error console.log('Error', error.message); errMsg += " - Unknown error occurred " + error.message; } return errMsg; } openEditNodeModal = (nodeKey) => { console.log("ModelGallery :: openEditNodeModal called with " + nodeKey); var focusedNode = null; for (var i = 0; i < this.props.nodes.length && !focusedNode; i++){ if(nodeKey === this.props.nodes[i].url){ focusedNode = this.props.nodes[i]; break; } } var editInputFields = []; if(focusedNode){ var nodeType = focusedNode['node-type']; focusedNode.allowedEditProps = []; //call to check what props can be modified in oxm here; focusedNode.allowedEditProps = GeneralCommonFunctions.getEditableAttributes(nodeType); if(focusedNode.allowedEditProps.length > 0){ for (var key in focusedNode.allowedEditProps){ var attr = focusedNode.allowedEditProps[key]; editInputFields[attr] = {}; editInputFields[attr].isEdited = false; if(focusedNode.properties[attr]){ editInputFields[attr].oldValue = focusedNode.properties[attr]; editInputFields[attr].newValue = focusedNode.properties[attr]; }else{ editInputFields[attr].oldValue = ""; editInputFields[attr].newValue = ""; } } }else{ this.setState({editInfoMsg: "This element cannot be edited, please contact an administrator if you need the ability to edit the attributes on this element."}); } }else{ //could not find the node, this shouldn't happen console.log("ModelGallery :: openEditNodeModal could not find " + nodeKey + " in this.props.nodes. This shouldn't happen."); } this.setState({showEditNodeModal:true, isEditSuccess: false, focusedNode: focusedNode, editInputFields: editInputFields}); } handleInputChange(event) { const target = event.target; const value = target.type === 'checkbox' ? target.checked : target.value; const name = target.name; var editInputFields = this.state.editInputFields; if(target.type === 'text'){ editInputFields[name].newValue = value; }else if(target.type === 'checkbox'){ if(!value){ editInputFields[name].newValue = editInputFields[name].oldValue, editInputFields[name].isEdited = value }else{ editInputFields[name].isEdited = value } } this.setState({ editInputFields: editInputFields }); } /* End Edit Node Modal Functions */ render(){ let cards = null; let tableColumns = []; let tableValues = []; let rowIndexValue = 0; let svgWidth = window.outerWidth * 0.8; let nodesList=[]; let tableColumnsList={}; let tableDataList={}; let columnFilter = []; let columnFilterList = (this.state.rerender) ? this.state.columnFilterList : {}; let aliasColumnList=(this.state.rerender) ? this.state.aliasColumnList: {}; let aliasRegex=/\'(\s)as(\s)\'|\'as\'/ig; console.log('Model gallery this.props>>>',this.props); console.log('columnFilterList while rendering:',columnFilterList); this.onTableFilterClick = (nodeType) => { this.setState({rerender:false},function(){this.props.isTableFilterApply(this.state.columnFilterList,nodeType,this.state.columnsList,this.state.aliasColumnList);}.bind(this)) } const expandRows = { parentClassName: 'parent-expand-bar', onlyOneExpanding: true, renderer: (row, rowIndex) => (
), showExpandColumn: true, expandByColumnOnly: true, onExpandAll: this.handleOnExpandAll, expanded: this.state.expanded, onExpand: this.handleOnExpand }; const rowEvents = { onClick: (e, row, rowIndex) => { //row index is usefull when single node type exist, for multiple node type use row id rowIndexValue = parseInt(row.id.split('_')[0]); }, onMouseEnter: (e, row, rowIndex) => { //row index is usefull when single node type exist, for multiple node type use row id rowIndexValue = parseInt(row.id.split('_')[0]); } }; let aliasColumns=[] if(this.props.nodes && this.props.nodes[0] && this.props.nodes[0]['node-type'] && this.props.viewName === "CellLayout" ){ for(var n=0; n>>>>*',plainNodes); if(plainNodes){ let propertiesPattern ="\\{.*?\\}"; var propRegularExp = new RegExp(propertiesPattern, 'g'); let nodeTypeProp = plainNodes[0].match(propRegularExp); nodeTypeProp = nodeTypeProp[0].slice(1,-1).split(',');//.replace(/\'/g,'').toLowerCase().split(','); for(var s=0;s>>>',tableColumns); tableColumns.push({value:'id'}); if(!columnFilterList[nodeType]){ columnFilterList[nodeType] = []; columnFilter = []; for(var j = 0; j < tableColumns.length; j++){ let txt = tableColumns[j].value; //if(!this.state.reRender && (!columnFilter[j] || (columnFilter[j] && columnFilter[j][txt] === undefined))){ let obj = {}; obj[txt] = ''; obj['description'] = tableColumns[j].description; columnFilter.push(obj); //} } columnFilterList[nodeType].push(columnFilter); } if(!aliasColumnList[nodeType]){ aliasColumnList[nodeType]=[]; aliasColumnList[nodeType].push(aliasColumns); } for(var j = 0; j < tableColumns.length; j++){ if(j === tableColumns.length-1){ tableColumns[j].dataField = 'id'; tableColumns[j].hidden = true; tableColumns[j].text = tableColumns[j].value; }else{ tableColumns[j].dataField = tableColumns[j].value; tableColumns[j].text = tableColumns[j].value; tableColumns[j].headerAttrs= { title:tableColumns[j].description}; tableColumns[j].ref=tableColumns[j].value; tableColumns[j].filter = customFilter(); tableColumns[j].filterRenderer = (onFilter, column) => ; } } tableColumnsList[nodeType] = tableColumns; tableDataList[nodeType] = []; for(var m=0; m { return ( ); }); } let tabs=nodesList.map((nodeType,index) => { return( ) }); return (
Edit Element
{this.state.focusedNode && Object.keys(this.state.editInputFields).length > 0 && (this.state.focusedNode.allowedEditProps).sort().map((attr) => { return
; }) }
{(() => { if (this.props.viewName === "CellLayout" && tableValues.length > 0) { if(nodesList.length > 1){ if(this.props.isTableFilterApply){ return (
{tabs}
) }else{ return (
{tabs}
) } }else{ if(this.props.isTableFilterApply){ return(
) }else{ return (
) } } } else if (this.props.viewName === "CardLayout") { return ( {cards} ) } })()}
); } }; export default ModelGallery;