/* Copyright (C) 2017 Cloudbase Solutions SRL This program is free software: you can redistribute it and/or modify it under the terms of the GNU Affero General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for more details. You should have received a copy of the GNU Affero General Public License along with this program. If not, see . */ import React, { PropTypes } from 'react'; import withStyles from 'isomorphic-style-loader/lib/withStyles'; import s from './AddCloudConnection.scss'; import Reflux from 'reflux'; import ConnectionsStore from '../../stores/ConnectionsStore'; import ConnectionsActions from '../../actions/ConnectionsActions'; import NotificationActions from '../../actions/NotificationActions'; import Dropdown from '../NewDropdown'; import LoadingIcon from "../LoadingIcon/LoadingIcon"; import ValidateEndpoint from '../ValidateEndpoint'; const title = 'Add Cloud Endpoint'; class AddCloudConnection extends Reflux.Component { static contextTypes = { onSetTitle: PropTypes.func.isRequired, }; static defaultProps = { cloud: null, connection: null, type: "new" } constructor(props) { super(props) this.store = ConnectionsStore this.state = { type: props.type, connection: props.connection, connectionName: "", description: null, currentCloud: this.props.cloud, currentCloudData: null, validateEndpoint: false, isConnecting: false, requiredFields: [], cloudFormsSubmitted: false } } componentWillMount() { super.componentWillMount.call(this) this.context.onSetTitle(title); } componentDidMount() { if (this.state.connection) { this.state.allClouds.forEach(item => { if (item.name === this.state.connection.type) { let credentials = this.state.connection.credentials for (let i in credentials) { credentials[i] = credentials[i] + "" } this.setState({ currentCloudData: credentials, connectionName: this.state.connection.name, description: this.state.connection.description }, () => { this.chooseCloud(item) }) } }) } else if (this.props.cloud) { this.chooseCloud(this.props.cloud) } } handleChangeName(e) { this.setState({ connectionName: e.target.value }) } handleChangeDescription(e) { this.setState({ description: e.target.value }) } handleSave() { let valid = true for (let i in this.state.currentCloudData) { if (this.state.requiredFields.indexOf(i) > -1 && !this.state.currentCloudData[i]) { valid = false } } if (this.state.connectionName.trim().length == 0) { valid = false } if (!valid) { NotificationActions.notify("Please fill all required fields", "error") this.setState({ cloudFormsSubmitted: true }) } else { let credentials = Object.assign({}, this.state.currentCloudData) for (let key in credentials) { if (credentials[key].label) { credentials[key] = credentials[key].value } } if (this.state.type == "new") { ConnectionsActions.newEndpoint({ name: this.state.connectionName, description: this.state.description, type: this.state.currentCloud.name, connection_info: credentials }, (response) => { this.setState({ validateEndpoint: response.data.endpoint, type: "edit", connection: response.data.endpoint }) }) this.props.addHandle(this.state.connectionName); } else { ConnectionsActions.editEndpoint(this.state.connection, { name: this.state.connectionName, description: this.state.description, connection_info: credentials }, () => { this.props.updateHandle({ name: this.state.connectionName, description: this.state.description }) }) this.props.closeHandle() } } } chooseCloud(cloud) { let currentCloudData = {} if (this.state.currentCloudData !== null) { currentCloudData = this.state.currentCloudData } let requiredFields = [] cloud.endpoint.fields.forEach(field => { if (typeof currentCloudData[field.name] == "undefined") { if (field.type == "dropdown") { currentCloudData[field.name] = field.options[0] } else { currentCloudData[field.name] = "" } } if (field.required) { requiredFields.push(field.name) } }) this.setState({ currentCloud: cloud, currentCloudData: currentCloudData, requiredFields: requiredFields }, this.setDefaultValues) } backToEdit() { this.setState({ validateEndpoint: null }) } handleBack() { this.setState({ currentCloudData: null, currentCloud: null, requiredFields: null, connectionName: "", description: null }) } setDefaultValues() { this.state.currentCloud.endpoint.fields.forEach(field => { let currentCloudData = this.state.currentCloudData switch (field.type) { case 'dropdown': field.options.forEach(option => { if (option.default === true && typeof currentCloudData[field.name] == "undefined") { currentCloudData[field.name] = option this.setState({ currentCloudData: currentCloudData }) } }, this) break case 'switch-radio': field.options.forEach(option => { if (option.default && typeof currentCloudData[field.name] == "undefined") { currentCloudData[field.name] = option.value this.setState({ currentCloudData: currentCloudData }) } }, this) break; case 'text': if (field.default && typeof currentCloudData[field.name] == "undefined") { currentCloudData[field.name] = field.default this.setState({ currentCloudData: currentCloudData }) } break default: break; } }, this) } isValid(field) { if (field.required && this.state.cloudFormsSubmitted) { if (this.state.currentCloudData[field.name].length == 0) { return false } else { return true } } else { return true } } handleCancel() { this.props.closeHandle(); } renderCloudList() { let clouds = this.state.allClouds.map((cloud, index) => { let colorType = "" if (cloud.credentials != null && cloud.credentials.length != 0) { colorType = "" } return (
this.chooseCloud(cloud)} >
) }, this) return (
{clouds}
) } renderField(field) { let returnValue switch (field.type) { case "text": returnValue = (
this.handleCloudFieldChange(e, field)} value={this.state.currentCloudData[field.name]} />
) break; case "password": returnValue = (
this.handleCloudFieldChange(e, field)} value={this.state.currentCloudData[field.name]} />
) break; case "dropdown": returnValue = (
this.handleCloudFieldChange(e, field)} placeholder={field.label + (field.required ? " *" : "")} value={this.state.currentCloudData[field.name]} />
) break; case "switch-radio": let fields = "" field.options.forEach((option) => { if (option.value == this.state.currentCloudData[field.name]) { fields = option.fields.map((optionField) => this.renderField(optionField)) } }) let radioOptions = field.options.map((option, key) => (
this.handleCloudFieldChange(e, field)} />
) ) returnValue = (
{ radioOptions }
{fields}
) break; default: break } return returnValue } handleCloudFieldChange(e, field) { let currentCloudData = this.state.currentCloudData if (field.type == 'dropdown') { currentCloudData[field.name] = e } else { currentCloudData[field.name] = e.target.value } this.setState({ currentCloudData: currentCloudData }) } renderCloudFields(cloud) { if (this.state.currentCloudData == null) { this.setState({ currentCloudData: {} }) } if (!this.state.isConnecting) { let fields = cloud.endpoint.fields.map(field => this.renderField(field), this) return (
this.handleChangeName(e)} value={this.state.connectionName} />
6 ? " " + s.larger : "")}> {fields}
{this.state.type == "new" ? ( ) : ( )}
) } else { return (
Connecting ...
) } } renderSaveConnection() { return (
this.handleChangeName(e)} value={this.state.connectionName} />
) } render() { let modalBody if (this.state.validateEndpoint) { modalBody = ( this.backToEdit(e)} /> ) } else if (this.state.currentCloud == null) { if (this.state.allClouds) { modalBody = this.renderCloudList() } else { modalBody = } } else { modalBody = this.renderCloudFields(this.state.currentCloud) } return (

{title}

{modalBody}
); } } export default withStyles(AddCloudConnection, s);