mirror of
https://repository.entgra.net/community/device-mgt-core.git
synced 2025-10-06 02:01:45 +00:00
Merge branch 'application-mgt-new' into 'application-mgt-new'
Add UI improvements to APPM UI See merge request entgra/carbon-device-mgt!303
This commit is contained in:
commit
d3077da65b
@ -13,7 +13,7 @@
|
||||
"@ant-design/dark-theme": "^0.2.2",
|
||||
"@babel/polyfill": "^7.6.0",
|
||||
"acorn": "^6.2.0",
|
||||
"antd": "^3.22.2",
|
||||
"antd": "^3.23.6",
|
||||
"axios": "^0.19.0",
|
||||
"d3": "^5.9.7",
|
||||
"dagre": "^0.8.4",
|
||||
|
||||
@ -35,6 +35,10 @@ class ReleaseView extends React.Component {
|
||||
}
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
console.log("mounted: Release view");
|
||||
}
|
||||
|
||||
render() {
|
||||
const {app, release} = this.props;
|
||||
const config = this.props.context;
|
||||
|
||||
@ -61,6 +61,8 @@ class NewAppUploadForm extends React.Component {
|
||||
binaryFileHelperText: '',
|
||||
iconHelperText: '',
|
||||
screenshotHelperText: '',
|
||||
osVersionsHelperText: '',
|
||||
osVersionsValidateStatus: 'validating',
|
||||
metaData: []
|
||||
};
|
||||
this.lowerOsVersion = null;
|
||||
@ -95,10 +97,6 @@ class NewAppUploadForm extends React.Component {
|
||||
releaseType: releaseType
|
||||
};
|
||||
|
||||
if (formConfig.installationType !== "WEB_CLIP" && formConfig.installationType !== "CUSTOM") {
|
||||
release.supportedOsVersions = `${this.lowerOsVersion}-${this.upperOsVersion}`;
|
||||
}
|
||||
|
||||
if (specificElements.hasOwnProperty("version")) {
|
||||
release.version = values.version;
|
||||
}
|
||||
@ -110,20 +108,51 @@ class NewAppUploadForm extends React.Component {
|
||||
}
|
||||
|
||||
const data = new FormData();
|
||||
let isFormValid = true; // flag to check if this form is valid
|
||||
|
||||
if (formConfig.installationType !== "WEB_CLIP" && formConfig.installationType !== "CUSTOM") {
|
||||
if(this.lowerOsVersion==null || this.upperOsVersion==null){
|
||||
isFormValid = false;
|
||||
this.setState({
|
||||
osVersionsHelperText: 'Please select supported OS versions',
|
||||
osVersionsValidateStatus: 'error',
|
||||
});
|
||||
}else if(this.lowerOsVersion>=this.upperOsVersion){
|
||||
isFormValid = false;
|
||||
this.setState({
|
||||
osVersionsHelperText: 'Please select valid range',
|
||||
osVersionsValidateStatus: 'error',
|
||||
});
|
||||
}else{
|
||||
release.supportedOsVersions = `${this.lowerOsVersion}-${this.upperOsVersion}`;
|
||||
}
|
||||
}
|
||||
|
||||
if (specificElements.hasOwnProperty("binaryFile") && this.state.binaryFiles.length !== 1) {
|
||||
isFormValid = false;
|
||||
this.setState({
|
||||
binaryFileHelperText: 'Please select the application'
|
||||
});
|
||||
} else if (this.state.icons.length !== 1) {
|
||||
}
|
||||
if (this.state.icons.length !== 1) {
|
||||
isFormValid = false;
|
||||
this.setState({
|
||||
iconHelperText: 'Please select an icon'
|
||||
});
|
||||
} else if (this.state.screenshots.length !== 3) {
|
||||
}
|
||||
if (this.state.screenshots.length !== 3) {
|
||||
isFormValid = false;
|
||||
this.setState({
|
||||
screenshotHelperText: 'Please select 3 screenshots'
|
||||
});
|
||||
} else {
|
||||
}
|
||||
if (this.state.screenshots.length !== 3) {
|
||||
isFormValid = false;
|
||||
this.setState({
|
||||
screenshotHelperText: 'Please select 3 screenshots'
|
||||
});
|
||||
}
|
||||
if(isFormValid) {
|
||||
data.append('icon', icon[0].originFileObj);
|
||||
data.append('screenshot1', screenshots[0].originFileObj);
|
||||
data.append('screenshot2', screenshots[1].originFileObj);
|
||||
@ -193,10 +222,18 @@ class NewAppUploadForm extends React.Component {
|
||||
|
||||
handleLowerOsVersionChange = (lowerOsVersion) => {
|
||||
this.lowerOsVersion = lowerOsVersion;
|
||||
this.setState({
|
||||
osVersionsValidateStatus: 'validating',
|
||||
osVersionsHelperText: ''
|
||||
});
|
||||
};
|
||||
|
||||
handleUpperOsVersionChange = (upperOsVersion) => {
|
||||
this.upperOsVersion = upperOsVersion;
|
||||
this.setState({
|
||||
osVersionsValidateStatus: 'validating',
|
||||
osVersionsHelperText: ''
|
||||
});
|
||||
};
|
||||
|
||||
render() {
|
||||
@ -212,7 +249,9 @@ class NewAppUploadForm extends React.Component {
|
||||
binaryFileHelperText,
|
||||
iconHelperText,
|
||||
screenshotHelperText,
|
||||
metaData
|
||||
metaData,
|
||||
osVersionsHelperText,
|
||||
osVersionsValidateStatus
|
||||
} = this.state;
|
||||
const uploadButton = (
|
||||
<div>
|
||||
@ -361,7 +400,11 @@ class NewAppUploadForm extends React.Component {
|
||||
</Form.Item>
|
||||
|
||||
{(formConfig.installationType !== "WEB_CLIP" && formConfig.installationType !== "CUSTOM") && (
|
||||
<Form.Item {...formItemLayout} label="Supported OS Versions">
|
||||
<Form.Item
|
||||
{...formItemLayout}
|
||||
label="Supported OS Versions"
|
||||
validateStatus={osVersionsValidateStatus}
|
||||
help={osVersionsHelperText}>
|
||||
{getFieldDecorator('supportedOS')(
|
||||
<div>
|
||||
<InputGroup>
|
||||
@ -436,7 +479,6 @@ class NewAppUploadForm extends React.Component {
|
||||
required: true,
|
||||
message: 'Please select'
|
||||
}],
|
||||
initialValue: false
|
||||
})(
|
||||
<Switch checkedChildren={<Icon type="check"/>}
|
||||
unCheckedChildren={<Icon type="close"/>}
|
||||
@ -444,13 +486,7 @@ class NewAppUploadForm extends React.Component {
|
||||
)}
|
||||
</Form.Item>
|
||||
<Form.Item {...formItemLayout} label="Meta Data">
|
||||
{getFieldDecorator('meta', {
|
||||
rules: [{
|
||||
required: true,
|
||||
message: 'Please fill empty fields'
|
||||
}],
|
||||
initialValue: false
|
||||
})(
|
||||
{getFieldDecorator('meta', {})(
|
||||
<div>
|
||||
{
|
||||
metaData.map((data, index) => {
|
||||
|
||||
@ -17,7 +17,7 @@
|
||||
*/
|
||||
|
||||
import React from "react";
|
||||
import {Divider, Row, Col, Typography, Button, Rate, notification} from "antd";
|
||||
import {Divider, Row, Col, Typography, Button, Dropdown, notification, Menu, Icon} from "antd";
|
||||
import "../../../App.css";
|
||||
import ImgViewer from "../../apps/release/images/ImgViewer";
|
||||
import StarRatings from "react-star-ratings";
|
||||
@ -42,7 +42,7 @@ class ReleaseView extends React.Component {
|
||||
}
|
||||
}
|
||||
|
||||
appOperation = (type, payload, operation, timestamp=null) => {
|
||||
appOperation = (type, payload, operation, timestamp = null) => {
|
||||
const config = this.props.context;
|
||||
const release = this.props.app.applicationReleases[0];
|
||||
const {uuid} = release;
|
||||
@ -50,9 +50,9 @@ class ReleaseView extends React.Component {
|
||||
this.setState({
|
||||
loading: true,
|
||||
});
|
||||
let url = window.location.origin+ config.serverConfig.invoker.uri +
|
||||
let url = window.location.origin + config.serverConfig.invoker.uri +
|
||||
config.serverConfig.invoker.store + "/subscription/" + uuid + "/" + type + "/" + operation;
|
||||
if(timestamp!= null){
|
||||
if (timestamp != null) {
|
||||
url += `?timestamp=${timestamp}`;
|
||||
}
|
||||
axios.post(
|
||||
@ -81,18 +81,11 @@ class ReleaseView extends React.Component {
|
||||
message: "There was a problem",
|
||||
duration: 0,
|
||||
description:
|
||||
"Error occurred while "+operation+"ing app",
|
||||
"Error occurred while " + operation + "ing app",
|
||||
});
|
||||
}
|
||||
}).catch((error) => {
|
||||
handleApiError(error,"Error occurred while "+operation+"ing the app.");
|
||||
});
|
||||
};
|
||||
|
||||
|
||||
showAppInstallModal = () => {
|
||||
this.setState({
|
||||
appInstallModalVisible: true
|
||||
handleApiError(error, "Error occurred while " + operation + "ing the app.");
|
||||
});
|
||||
};
|
||||
|
||||
@ -103,37 +96,50 @@ class ReleaseView extends React.Component {
|
||||
});
|
||||
};
|
||||
|
||||
showAppUninstallModal = () => {
|
||||
this.setState({
|
||||
appUninstallModalVisible: true
|
||||
});
|
||||
handleSubscribeClick = (e) => {
|
||||
if (e.key === "install") {
|
||||
this.setState({
|
||||
appInstallModalVisible: true // display app install modal
|
||||
})
|
||||
} else if (e.key === "uninstall") {
|
||||
this.setState({
|
||||
appUninstallModalVisible: true // display app uninstall modal
|
||||
})
|
||||
}
|
||||
};
|
||||
|
||||
render() {
|
||||
const {app,deviceType} = this.props;
|
||||
const {app, deviceType} = this.props;
|
||||
const release = app.applicationReleases[0];
|
||||
|
||||
let metaData = [];
|
||||
try{
|
||||
try {
|
||||
metaData = JSON.parse(release.metaData);
|
||||
}catch (e) {
|
||||
} catch (e) {
|
||||
|
||||
}
|
||||
const menu = (
|
||||
<Menu onClick={this.handleSubscribeClick}>
|
||||
<Menu.Item key="install">Install</Menu.Item>
|
||||
<Menu.Item key="uninstall">Uninstall</Menu.Item>
|
||||
</Menu>
|
||||
);
|
||||
|
||||
|
||||
return (
|
||||
<div>
|
||||
<AppInstallModal
|
||||
uuid={release.uuid}
|
||||
visible={this.state.appInstallModalVisible}
|
||||
deviceType = {deviceType}
|
||||
deviceType={deviceType}
|
||||
onClose={this.closeAppOperationModal}
|
||||
onInstall={this.appOperation}/>
|
||||
<AppUninstallModal
|
||||
uuid={release.uuid}
|
||||
visible={this.state.appUninstallModalVisible}
|
||||
deviceType = {deviceType}
|
||||
onClose={this.closeAppOperationModal}
|
||||
onUninstall={this.appOperation}/>
|
||||
uuid={release.uuid}
|
||||
visible={this.state.appUninstallModalVisible}
|
||||
deviceType={deviceType}
|
||||
onClose={this.closeAppOperationModal}
|
||||
onUninstall={this.appOperation}/>
|
||||
<div className="release">
|
||||
<Row>
|
||||
<Col xl={4} sm={6} xs={8} className="release-icon">
|
||||
@ -152,17 +158,14 @@ class ReleaseView extends React.Component {
|
||||
/>
|
||||
</Col>
|
||||
<Col xl={8} md={10} sm={24} xs={24} style={{float: "right"}}>
|
||||
<div>
|
||||
<Button.Group style={{float: "right"}}>
|
||||
<Button onClick={this.showAppInstallModal} loading={this.state.loading}
|
||||
htmlType="button" type="primary" icon="download">Install</Button>
|
||||
</Button.Group>
|
||||
</div>
|
||||
<div>
|
||||
<Button.Group style={{float: "right",marginRight:'3%'}}>
|
||||
<Button onClick={this.showAppUninstallModal} loading={this.state.loading}
|
||||
htmlType="button" type="primary" icon="delete">UnInstall</Button>
|
||||
</Button.Group>
|
||||
<div style={{
|
||||
textAlign: "right"
|
||||
}}>
|
||||
<Dropdown overlay={menu}>
|
||||
<Button type="primary">
|
||||
Subscribe <Icon type="down"/>
|
||||
</Button>
|
||||
</Dropdown>
|
||||
</div>
|
||||
</Col>
|
||||
</Row>
|
||||
@ -178,16 +181,16 @@ class ReleaseView extends React.Component {
|
||||
<Text>META DATA</Text>
|
||||
<Row>
|
||||
{
|
||||
metaData.map((data, index)=>{
|
||||
metaData.map((data, index) => {
|
||||
return (
|
||||
<Col key={index} lg={8} md={6} xs={24} style={{marginTop:15}}>
|
||||
<Col key={index} lg={8} md={6} xs={24} style={{marginTop: 15}}>
|
||||
<Text>{data.key}</Text><br/>
|
||||
<Text type="secondary">{data.value}</Text>
|
||||
</Col>
|
||||
)
|
||||
})
|
||||
}
|
||||
{(metaData.length===0) && (<Text type="secondary">No meta data available.</Text>)}
|
||||
{(metaData.length === 0) && (<Text type="secondary">No meta data available.</Text>)}
|
||||
</Row>
|
||||
<Divider/>
|
||||
<CurrentUsersReview uuid={release.uuid}/>
|
||||
|
||||
@ -17,12 +17,12 @@
|
||||
*/
|
||||
|
||||
import React from "react";
|
||||
import {Button, DatePicker} from "antd";
|
||||
import {Button, DatePicker, Checkbox} from "antd";
|
||||
|
||||
class InstallModalFooter extends React.Component{
|
||||
class InstallModalFooter extends React.Component {
|
||||
constructor(props) {
|
||||
super(props);
|
||||
this.state={
|
||||
this.state = {
|
||||
scheduledTime: null,
|
||||
isScheduledInstallVisible: false
|
||||
}
|
||||
@ -34,65 +34,52 @@ class InstallModalFooter extends React.Component{
|
||||
});
|
||||
};
|
||||
|
||||
showScheduledInstall = ()=>{
|
||||
toggleScheduledInstall = () => {
|
||||
this.setState({
|
||||
isScheduledInstallVisible: true
|
||||
isScheduledInstallVisible: !this.state.isScheduledInstallVisible
|
||||
})
|
||||
};
|
||||
|
||||
hideScheduledInstall = ()=>{
|
||||
this.setState({
|
||||
isScheduledInstallVisible: false
|
||||
})
|
||||
};
|
||||
|
||||
triggerInstallOperation = () =>{
|
||||
this.props.operation();
|
||||
};
|
||||
triggerScheduledInstallOperation = () =>{
|
||||
const {scheduledTime} =this.state;
|
||||
this.props.operation(scheduledTime);
|
||||
triggerInstallOperation = () => {
|
||||
const {scheduledTime, isScheduledInstallVisible} = this.state;
|
||||
if (isScheduledInstallVisible && scheduledTime != null) {
|
||||
this.props.operation(scheduledTime);
|
||||
} else {
|
||||
this.props.operation();
|
||||
}
|
||||
};
|
||||
|
||||
render() {
|
||||
const {scheduledTime,isScheduledInstallVisible} =this.state;
|
||||
const {scheduledTime, isScheduledInstallVisible} = this.state;
|
||||
const {disabled, type} = this.props;
|
||||
return (
|
||||
<div>
|
||||
<div style={{
|
||||
textAlign: "right",
|
||||
display: (!isScheduledInstallVisible)?'block':'none'
|
||||
}}>
|
||||
<Button style={{margin: 5}} disabled={disabled} htmlType="button" type="primary"
|
||||
onClick={this.triggerInstallOperation}>
|
||||
{type}
|
||||
</Button>
|
||||
<Button style={{margin: 5}} disabled={disabled} htmlType="button"
|
||||
onClick={this.showScheduledInstall}>
|
||||
Scheduled {type}
|
||||
</Button>
|
||||
</div>
|
||||
<div style={{
|
||||
textAlign: "right",
|
||||
display: (isScheduledInstallVisible)?'block':'none'
|
||||
}}>
|
||||
<DatePicker showTime
|
||||
placeholder="Select Time"
|
||||
format="YYYY-MM-DDTHH:mm"
|
||||
onChange={this.onDateTimeChange}/>
|
||||
<Button disabled={scheduledTime == null}
|
||||
style={{margin: 5}}
|
||||
htmlType="button"
|
||||
type="primary"
|
||||
onClick={this.triggerScheduledInstallOperation}>
|
||||
Schedule
|
||||
</Button>
|
||||
<Button style={{margin: 5}} htmlType="button"
|
||||
onClick={this.hideScheduledInstall}>
|
||||
Cancel
|
||||
</Button>
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<div style={{
|
||||
textAlign: "right"
|
||||
}}>
|
||||
<div style={{margin: 8}}>
|
||||
<Checkbox checked={this.state.isScheduledInstallVisible} onChange={this.toggleScheduledInstall}>
|
||||
Schedule {type}
|
||||
</Checkbox>
|
||||
</div>
|
||||
<span style={{
|
||||
display: (isScheduledInstallVisible) ? 'inline' : 'none'
|
||||
}}>
|
||||
<DatePicker showTime
|
||||
placeholder="Select Time"
|
||||
format="YYYY-MM-DDTHH:mm"
|
||||
onChange={this.onDateTimeChange}/>
|
||||
</span>
|
||||
<Button style={{margin: 5}}
|
||||
disabled={disabled || (isScheduledInstallVisible && scheduledTime == null)}
|
||||
htmlType="button"
|
||||
type="primary"
|
||||
onClick={this.triggerInstallOperation}>
|
||||
{type}
|
||||
</Button>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@ -98,13 +98,18 @@ class NormalLoginForm extends React.Component {
|
||||
|
||||
const request = Object.keys(parameters).map(key => key + '=' + parameters[key]).join('&');
|
||||
|
||||
axios.post(window.location.origin+ config.serverConfig.loginUri, request
|
||||
axios.post(window.location.origin + config.serverConfig.loginUri, request
|
||||
).then(res => {
|
||||
if (res.status === 200) {
|
||||
window.location = window.location.origin+ "/store";
|
||||
let redirectUrl = window.location.origin + "/store";
|
||||
const searchParams = new URLSearchParams(window.location.search);
|
||||
if (searchParams.has("redirect")) {
|
||||
redirectUrl = searchParams.get("redirect");
|
||||
}
|
||||
window.location = redirectUrl;
|
||||
}
|
||||
}).catch(function (error) {
|
||||
handleApiError(error,"Error occurred while trying to load groups.");
|
||||
handleApiError(error, "Error occurred while trying to load groups.");
|
||||
if (error.hasOwnProperty("response") && error.response.status === 400) {
|
||||
thisForm.setState({
|
||||
inValid: true,
|
||||
@ -158,7 +163,8 @@ class NormalLoginForm extends React.Component {
|
||||
)}
|
||||
<br/>
|
||||
<a className="login-form-forgot" href="">Forgot password</a>
|
||||
<Button loading={this.state.loading} block type="primary" htmlType="submit" className="login-form-button">
|
||||
<Button loading={this.state.loading} block type="primary" htmlType="submit"
|
||||
className="login-form-button">
|
||||
Log in
|
||||
</Button>
|
||||
</Form.Item>
|
||||
|
||||
Loading…
Reference in New Issue
Block a user