jenkinsci/hpe-application-automation-tools-plugin

View on GitHub
src/main/webapp/js/dropdown.jsx

Summary

Maintainability
A
0 mins
Test Coverage

/*
 * Certain versions of software accessible here may contain branding from Hewlett-Packard Company (now HP Inc.) and Hewlett Packard Enterprise Company.
 * This software was acquired by Micro Focus on September 1, 2017, and is now offered by OpenText.
 * Any reference to the HP and Hewlett Packard Enterprise/HPE marks is historical in nature, and the HP and Hewlett Packard Enterprise/HPE marks are the property of their respective owners.
 * __________________________________________________________________
 * MIT License
 *
 * Copyright 2012-2024 Open Text
 *
 * The only warranties for products and services of Open Text and
 * its affiliates and licensors ("Open Text") are as may be set forth
 * in the express warranty statements accompanying such products and services.
 * Nothing herein should be construed as constituting an additional warranty.
 * Open Text shall not be liable for technical or editorial errors or
 * omissions contained herein. The information contained herein is subject
 * to change without notice.
 *
 * Except as specifically indicated otherwise, this document contains
 * confidential information and a valid license is required for possession,
 * use or copying. If this work is provided to the U.S. Government,
 * consistent with FAR 12.211 and 12.212, Commercial Computer Software,
 * Computer Software Documentation, and Technical Data for Commercial Items are
 * licensed to the U.S. Government under vendor's standard commercial license.
 *
 * 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.
 * ___________________________________________________________________
 */

class Chart extends React.Component{

    componentDidMount() {
        this.updateChart(this.props.chartData);
    };

    updateChart() {
        let chartName = this.props.chartName;
        let options = this.optionsSetter();
        let newChart = new Chartist.Line('#' + chartName, this.props.chartData, options);
        // newChart.on('draw', function(data) {
        //     if(data.type === 'grid' && data.index !== 0) {
        //         data.element.remove();
        //     }});

        return newChart;
    };

    shouldComponentUpdate() {
        return true;
    };

    componentDidUpdate(){
        this.updateChart(this.props.chartData);
    }

    optionsSetter() {
        let options = new Object();
        options.fullWidth = true;
        options.width = "100%";
        options.height = "85%";
        options.stretch = true;
        options.chartPadding = {left: 40, right: 20,bottom: 10};
        options.plugins = [];
        options.plugins.push(Chartist.plugins.tooltip({
            anchorToPoint: true,
            appendToBody: false,
            tooltipOffset: {
                x: 0,
                y: 40
            },
            transformTooltipTextFnc: function(value)
            {
                return Chartist.roundWithPrecision(value, 3);
            }
        }));
        options.plugins.push(Chartist.plugins.ctAxisTitle({
            axisX: {
                axisTitle: this.props.chartData.x_axis_title,
                axisClass: 'ct-axis-title',
                offset: {
                    x: 0,
                    y: 40
                },
                textAnchor: 'middle'
            },
            axisY: {
                axisTitle: this.props.chartData.y_axis_title,
                axisClass: 'ct-axis-title-y',
                offset: {
                    x: 0,
                    y: 0
                },
                textAnchor: 'middle',
                flipTitle: false
            }
        }));
        if ((this.props.multiSeriesChart === true)) {
            options.plugins.push(Chartist.plugins.legend({
                position: 'bottom'
            }));
        }
        options.lineSmooth = Chartist.Interpolation.step();
        options.axisY = {
            labelInterpolationFnc: function(value)
            {
                return Chartist.roundWithPrecision(value, 6);
            }
        }
        return options;
    };

    componentWillReceiveProps(newProps) {
        this.updateChart(newProps);
    }

    componentWillUnmount() {
        if (this.chartist) {
            try {
                this.chartist.detach();
            } catch (err) {
                throw new Error('Internal chartist error', err);
            }
        }
    }

    render() {
        return (
               <div id={this.props.chartName} className='ct-chart'>
               </div>
       );
    }
};

class Charts extends React.Component
{
    render() {
        let graphsData = this.props.graphsData;
        let charts = Object.keys(graphsData).map((chartName, index)=>
        {
            let chartData = graphsData[chartName];
            let multiSeriesChart = false;
            if(chartData.series.length > 1)
            {
                multiSeriesChart = true;
            }
            let chartBoxKey = chartName + "box";
            let chartAreaKey = chartName + "Area";
            return (

                <div key = {chartAreaKey} className="ct-chartBox">
                <div>
                    <span className="ct-chart-title">{chartData.title}</span>
                    <br className="ct-chart-seprator"/>
                    <span className="ct-chart-desc-title">Description: </span>
                    <span className="ct-chart-desc">{chartData.description}</span>
                </div>
                    <Chart key = {chartName} chartName = {chartName} chartData = {chartData}
                           multiSeriesChart = {multiSeriesChart} {...this.props}/>

                </div>

            );
        });
        let returnValue = <div id="charts"> </div>;
        if(charts.length > 0)
        {
            returnValue = <div id="charts">{charts}</div>;
        }
        return returnValue;
    }
};



class ChartDashboard extends React.Component{
    static propTypes: {
        globalOptions: React.PropTypes.array,
        graphsData: React.PropTypes.object.isRequired,
        dataProcessFunc: React.PropTypes.func,
        multiSeries: React.PropTypes.boolean,
    };

    static defaultProps : {
        globalOptions: [],
        graphsData: {},
        multiSeries: false,
    };

    render() {
        return (<Charts {...this.props}/> );
    }
};

/**
 * Checks if the given graphs is of SLA rule type that has multiple transaction and therefore
 * requires legend and multiple series support
 * @param graphKey - the graph name (as defined in the data object given.
 * @returns boolean iff it's of multiple transaction type.
 */
function isMultipleTransactionGraph(graphKey) {
    if(graphKey == 'averageTransactionResponseTime' || graphKey == 'percentileTransaction')
    {
        return true;
    }

    return false;
};

/**
 * Updates the graph view per scenario key
 * @param scenarioKey - the selected scenario
 */
function updateGraphs(scenarioKey)
{
    instance.getGraphData(function(t)
    {
        let graphsData = (t.responseObject())[scenarioKey];
        ReactDOM.render(<ChartDashboard graphsData = {graphsData.scenarioData} dataProcessFunc = {isMultipleTransactionGraph}/>
            ,document.querySelector('.graphCon'));
        // ReactDOM.render(<ScenarioTable scenName = {scenarioKey} scenData = {graphsData.scenarioStats}/>,
        //     document.querySelector('.scenarioSummary'));
    });
};

var Dropdown = React.createClass({

    propTypes: {
        id: React.PropTypes.string.isRequired,
        options: React.PropTypes.array.isRequired,
        value: React.PropTypes.oneOfType(
            [
                React.PropTypes.object,
                React.PropTypes.string
            ]
        ),
        valueField: React.PropTypes.string,
        labelField: React.PropTypes.string,
        onChange: React.PropTypes.func
    },

    getDefaultProps: function() {
        return {
            value: null,
            valueField: 'value',
            labelField: 'label',
            onChange: null
        };
    },

    getInitialState: function() {
        var selected = this.getSelectedFromProps(this.props);
        // console.log(JSON.stringify(selected));
        updateGraphs(selected);
        return {
            selected: selected
        }
    },

    componentWillReceiveProps: function(nextProps) {
        var selected = this.getSelectedFromProps(nextProps);
        this.setState({
            selected: selected
        });
    },

    getSelectedFromProps(props) {
        var selected;
        if (props.value === null && props.options.length !== 0) {
            selected = props.options[0][props.valueField];
        } else {
            selected = props.value;
        }
        return selected;
    },

    render: function() {
        var self = this;
        var options = self.props.options.map(function(option) {
            return (
                <option key={option[self.props.valueField]} value={option[self.props.valueField]}>
                    Scenario name: {option[self.props.labelField]}
                </option>
            )
        });
        return (
            <select id={this.props.id}
                    className='st-dropdown'
                    value={this.state.selected}
                    onChange={this.handleChange}>
                {options}
            </select>
        );
    },

    handleChange: function(e) {
        if (this.props.onChange) {
            var change = {
                oldValue: this.state.selected,
                newValue: e.target.value
            };
            this.props.onChange(change);
        }
        this.setState({selected: e.target.value});
    }

});

var dropDownOnChange = function(change) {
    updateGraphs(change.newValue);
};

instance.getScenarioList(function(t)
{
    let tData = t.responseObject();
    ReactDOM.render(<div>
            {/*<span>*/}
                {/*Scenario name:*/}
            {/*</span>*/}
            <Dropdown id='myDropdown' options= {tData} labelField='ScenarioName' valueField='ScenarioName' onChange={dropDownOnChange}/>
        </div>, document.getElementById('scenarioDropDown'));
});

class ScenarioTable extends React.Component{
    static propTypes: {
        scenName: React.PropTypes.string.isRequired,
        scenData: React.PropTypes.array.isRequired,
    };

    render() {
        const tableId = this.props.scenarioKey + '_table'
        const time = this.props.scenData.AvgScenarioDuration.AvgDuration;

        const days = Math.floor(time / 86400);
        const hours = Math.floor((time - (86400 * days)) / 3600);
        const minutes = Math.floor((time - (3600 * hours)) / 60);
        const seconds = Math.floor(time - (60 * minutes));

        return (<div id={this.props.scenarioKey} className='scenario-stats'>
            <table className="st-table">
                <thead className="st-table-head">
                    <tr className="st-table-row">
                        <th className="st-table-header">
                            Average duration
                            (Days:Hours:Min:Sec)
                        </th>
                        <th className="st-table-header">
                            Average total transaction state
                        </th>
                        <th className="st-table-header">
                            Average maximum connections
                        </th>
                        <th className="st-table-header">
                            Average maximum VUsers
                        </th>
                    </tr>
                </thead>
                <tbody className="st-table-body">
                    <tr className="st-table-row">
                        <td className="st-table-cell">
                            {days}:{hours}:{minutes}:{seconds}
                        </td>
                        <td className = "st-table-cell">
                            <td className = "st-table-inner-cell">
                                <img src="/plugin/hp-application-automation-tools-plugin/icons/16x16/passed.png" alt="Passed:"/>
                                {this.props.scenData.TransactionSummary.Pass} Passed
                            </td>
                            <td className = "st-table-inner-cell">
                                <img src="/plugin/hp-application-automation-tools-plugin/icons/16x16/stop.png" alt="Stopped:"/>
                                {this.props.scenData.TransactionSummary.Stop} Stopped
                            </td>
                            <td className = "st-table-inner-cell">
                                <img src="/plugin/hp-application-automation-tools-plugin/icons/16x16/failed.png" alt="Failed:"/>
                                {this.props.scenData.TransactionSummary.Fail} Failed
                            </td>
                        </td>
                        <td className="st-table-cell">
                            {this.props.scenData.AvgMaxConnections.AvgMaxConnection}
                        </td>
                        <td className="st-table-cell">
                            {this.props.scenData.VUserSummary.AvgMaxVuser}
                        </td>
                    </tr>
                </tbody>
            </table>
        </div>);
    }
};