Merge "feat: Support domain actions"
This commit is contained in:
commit
633fcdec63
@ -528,19 +528,6 @@ const renderMenu = (t) => {
|
|||||||
key: 'domainAdmin',
|
key: 'domainAdmin',
|
||||||
level: 1,
|
level: 1,
|
||||||
children: [
|
children: [
|
||||||
{
|
|
||||||
path: '/identity/domain-admin/create',
|
|
||||||
name: t('Create Domain'),
|
|
||||||
key: 'domainCreateAdmin',
|
|
||||||
level: 2,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
path: /^\/identity\/domain-admin\/edit\/.[^/]+$/,
|
|
||||||
name: t('Domain Edit'),
|
|
||||||
key: 'domainEditAdmin',
|
|
||||||
level: 2,
|
|
||||||
routePath: '/identity/domain-admin/edit/:id',
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
path: /^\/identity\/domain-admin\/detail\/.[^/]+$/,
|
path: /^\/identity\/domain-admin\/detail\/.[^/]+$/,
|
||||||
name: t('Domain Detail'),
|
name: t('Domain Detail'),
|
||||||
|
@ -732,7 +732,6 @@
|
|||||||
"Docker Volume Size (GiB)": "Docker Volume Size (GiB)",
|
"Docker Volume Size (GiB)": "Docker Volume Size (GiB)",
|
||||||
"Domain": "Domain",
|
"Domain": "Domain",
|
||||||
"Domain Detail": "Domain Detail",
|
"Domain Detail": "Domain Detail",
|
||||||
"Domain Edit": "Domain Edit",
|
|
||||||
"Domain ID/Name": "Domain ID/Name",
|
"Domain ID/Name": "Domain ID/Name",
|
||||||
"Domain Manager": "Domain Manager",
|
"Domain Manager": "Domain Manager",
|
||||||
"Domain Name": "Domain Name",
|
"Domain Name": "Domain Name",
|
||||||
@ -2401,7 +2400,6 @@
|
|||||||
"User Groups": "User Groups",
|
"User Groups": "User Groups",
|
||||||
"User ID": "User ID",
|
"User ID": "User ID",
|
||||||
"User ID/Name": "User ID/Name",
|
"User ID/Name": "User ID/Name",
|
||||||
"User List": "User List",
|
|
||||||
"User Name": "User Name",
|
"User Name": "User Name",
|
||||||
"User Num": "User Num",
|
"User Num": "User Num",
|
||||||
"User Num: ": "User Num: ",
|
"User Num: ": "User Num: ",
|
||||||
@ -2622,7 +2620,6 @@
|
|||||||
"edit": "edit",
|
"edit": "edit",
|
||||||
"edit baremetal node": "edit baremetal node",
|
"edit baremetal node": "edit baremetal node",
|
||||||
"edit default pool": "edit default pool",
|
"edit default pool": "edit default pool",
|
||||||
"edit domain": "edit domain",
|
|
||||||
"edit health monitor": "edit health monitor",
|
"edit health monitor": "edit health monitor",
|
||||||
"edit image": "edit image",
|
"edit image": "edit image",
|
||||||
"edit member": "edit member",
|
"edit member": "edit member",
|
||||||
|
@ -732,7 +732,6 @@
|
|||||||
"Docker Volume Size (GiB)": "Docker硬盘大小(GiB)",
|
"Docker Volume Size (GiB)": "Docker硬盘大小(GiB)",
|
||||||
"Domain": "域",
|
"Domain": "域",
|
||||||
"Domain Detail": "域详情",
|
"Domain Detail": "域详情",
|
||||||
"Domain Edit": "编辑域",
|
|
||||||
"Domain ID/Name": "域ID/名称",
|
"Domain ID/Name": "域ID/名称",
|
||||||
"Domain Manager": "域管理员",
|
"Domain Manager": "域管理员",
|
||||||
"Domain Name": "域名",
|
"Domain Name": "域名",
|
||||||
@ -2401,7 +2400,6 @@
|
|||||||
"User Groups": "用户组",
|
"User Groups": "用户组",
|
||||||
"User ID": "用户ID",
|
"User ID": "用户ID",
|
||||||
"User ID/Name": "用户ID/名称",
|
"User ID/Name": "用户ID/名称",
|
||||||
"User List": "用户列表",
|
|
||||||
"User Name": "用户名称",
|
"User Name": "用户名称",
|
||||||
"User Num": "用户数",
|
"User Num": "用户数",
|
||||||
"User Num: ": "用户数: ",
|
"User Num: ": "用户数: ",
|
||||||
@ -2622,7 +2620,6 @@
|
|||||||
"edit": "编辑",
|
"edit": "编辑",
|
||||||
"edit baremetal node": "编辑裸机节点",
|
"edit baremetal node": "编辑裸机节点",
|
||||||
"edit default pool": "编辑资源池",
|
"edit default pool": "编辑资源池",
|
||||||
"edit domain": "编辑域",
|
|
||||||
"edit health monitor": "编辑健康检查器",
|
"edit health monitor": "编辑健康检查器",
|
||||||
"edit image": "编辑镜像",
|
"edit image": "编辑镜像",
|
||||||
"edit member": "编辑成员",
|
"edit member": "编辑成员",
|
||||||
|
@ -40,10 +40,6 @@ export class Instance extends Base {
|
|||||||
this.downloadStore = new ServerStore();
|
this.downloadStore = new ServerStore();
|
||||||
}
|
}
|
||||||
|
|
||||||
get tabs() {
|
|
||||||
return [];
|
|
||||||
}
|
|
||||||
|
|
||||||
get policy() {
|
get policy() {
|
||||||
if (this.isAdminPage) {
|
if (this.isAdminPage) {
|
||||||
return 'os_compute_api:servers:index:get_all_tenants';
|
return 'os_compute_api:servers:index:get_all_tenants';
|
||||||
|
@ -12,12 +12,13 @@
|
|||||||
// See the License for the specific language governing permissions and
|
// See the License for the specific language governing permissions and
|
||||||
// limitations under the License.
|
// limitations under the License.
|
||||||
|
|
||||||
import React from 'react';
|
|
||||||
import { inject, observer } from 'mobx-react';
|
import { inject, observer } from 'mobx-react';
|
||||||
import { Badge } from 'antd';
|
|
||||||
import { DomainStore } from 'stores/keystone/domain';
|
import { DomainStore } from 'stores/keystone/domain';
|
||||||
import Base from 'containers/TabDetail';
|
import Base from 'containers/TabDetail';
|
||||||
|
import { enabledColumn } from 'resources/keystone/domain';
|
||||||
import User from '../../User';
|
import User from '../../User';
|
||||||
|
import Project from '../../Project';
|
||||||
|
import actionConfigs from '../actions';
|
||||||
|
|
||||||
export class DomainDetail extends Base {
|
export class DomainDetail extends Base {
|
||||||
get name() {
|
get name() {
|
||||||
@ -32,26 +33,24 @@ export class DomainDetail extends Base {
|
|||||||
return this.getRoutePath('domain');
|
return this.getRoutePath('domain');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
get actionConfigs() {
|
||||||
|
return actionConfigs;
|
||||||
|
}
|
||||||
|
|
||||||
get detailInfos() {
|
get detailInfos() {
|
||||||
return [
|
return [
|
||||||
{
|
{
|
||||||
title: t('Domain Name'),
|
title: t('Domain Name'),
|
||||||
dataIndex: 'name',
|
dataIndex: 'name',
|
||||||
},
|
},
|
||||||
{
|
enabledColumn,
|
||||||
title: t('Enabled'),
|
|
||||||
dataIndex: 'enabled',
|
|
||||||
isHideable: true,
|
|
||||||
render: (val) => {
|
|
||||||
if (val === true) {
|
|
||||||
return <Badge color="green" text={t('Yes')} />;
|
|
||||||
}
|
|
||||||
return <Badge color="red" text={t('No')} />;
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
title: t('User Num'),
|
title: t('User Num'),
|
||||||
dataIndex: 'user_num',
|
dataIndex: 'userCount',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: t('Project Num'),
|
||||||
|
dataIndex: 'projectCount',
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: t('Description'),
|
title: t('Description'),
|
||||||
@ -63,21 +62,19 @@ export class DomainDetail extends Base {
|
|||||||
get tabs() {
|
get tabs() {
|
||||||
const tabs = [
|
const tabs = [
|
||||||
{
|
{
|
||||||
title: t('User List'),
|
title: t('Users'),
|
||||||
key: 'user',
|
key: 'user',
|
||||||
component: User,
|
component: User,
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
title: t('Projects'),
|
||||||
|
key: 'project',
|
||||||
|
component: Project,
|
||||||
|
},
|
||||||
];
|
];
|
||||||
return tabs;
|
return tabs;
|
||||||
}
|
}
|
||||||
|
|
||||||
goEdit = () => {
|
|
||||||
const {
|
|
||||||
params: { id },
|
|
||||||
} = this.props.match;
|
|
||||||
this.routing.push(`${this.listUrl}/edit/${id}`);
|
|
||||||
};
|
|
||||||
|
|
||||||
init() {
|
init() {
|
||||||
this.store = new DomainStore();
|
this.store = new DomainStore();
|
||||||
}
|
}
|
||||||
|
@ -14,10 +14,10 @@
|
|||||||
|
|
||||||
import { inject, observer } from 'mobx-react';
|
import { inject, observer } from 'mobx-react';
|
||||||
import globalDomainStore from 'stores/keystone/domain';
|
import globalDomainStore from 'stores/keystone/domain';
|
||||||
import { FormAction } from 'containers/Action';
|
import { ModalAction } from 'containers/Action';
|
||||||
import { statusTypes } from 'utils/constants';
|
import { statusTypes } from 'resources/keystone/domain';
|
||||||
|
|
||||||
export class CreateForm extends FormAction {
|
export class Create extends ModalAction {
|
||||||
init() {
|
init() {
|
||||||
this.store = globalDomainStore;
|
this.store = globalDomainStore;
|
||||||
}
|
}
|
||||||
@ -26,29 +26,16 @@ export class CreateForm extends FormAction {
|
|||||||
|
|
||||||
static title = t('Create Domain');
|
static title = t('Create Domain');
|
||||||
|
|
||||||
static path = '/identity/domain-admin/create';
|
|
||||||
|
|
||||||
static policy = 'identity:create_domain';
|
static policy = 'identity:create_domain';
|
||||||
|
|
||||||
static allowed() {
|
static allowed() {
|
||||||
return Promise.resolve(true);
|
return Promise.resolve(true);
|
||||||
}
|
}
|
||||||
|
|
||||||
get listUrl() {
|
|
||||||
return this.getRoutePath('domain');
|
|
||||||
}
|
|
||||||
|
|
||||||
get name() {
|
get name() {
|
||||||
return t('Create Domain');
|
return t('Create Domain');
|
||||||
}
|
}
|
||||||
|
|
||||||
get labelCol() {
|
|
||||||
return {
|
|
||||||
xs: { span: 6 },
|
|
||||||
sm: { span: 5 },
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
get defaultValue() {
|
get defaultValue() {
|
||||||
const data = {
|
const data = {
|
||||||
enabled: statusTypes[0],
|
enabled: statusTypes[0],
|
||||||
@ -100,4 +87,4 @@ export class CreateForm extends FormAction {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
export default inject('rootStore')(observer(CreateForm));
|
export default inject('rootStore')(observer(Create));
|
||||||
|
@ -38,6 +38,8 @@ export default class DeleteAction extends ConfirmAction {
|
|||||||
|
|
||||||
policy = 'identity:delete_domain';
|
policy = 'identity:delete_domain';
|
||||||
|
|
||||||
|
allowedCheckFunc = (data) => !data.enabled;
|
||||||
|
|
||||||
onSubmit = (data) => {
|
onSubmit = (data) => {
|
||||||
const { id } = data;
|
const { id } = data;
|
||||||
return globalDomainStore.delete({ id });
|
return globalDomainStore.delete({ id });
|
||||||
|
@ -13,29 +13,19 @@
|
|||||||
// limitations under the License.
|
// limitations under the License.
|
||||||
|
|
||||||
import { inject, observer } from 'mobx-react';
|
import { inject, observer } from 'mobx-react';
|
||||||
import { FormAction } from 'containers/Action';
|
import { ModalAction } from 'containers/Action';
|
||||||
import globalDomainStore from 'stores/keystone/domain';
|
import globalDomainStore from 'stores/keystone/domain';
|
||||||
|
|
||||||
export class EditForm extends FormAction {
|
export class Edit extends ModalAction {
|
||||||
init() {
|
init() {
|
||||||
this.store = globalDomainStore;
|
this.store = globalDomainStore;
|
||||||
}
|
}
|
||||||
|
|
||||||
componentDidMount() {
|
|
||||||
const { item } = this.props;
|
|
||||||
const {
|
|
||||||
params: { id },
|
|
||||||
} = this.props.match;
|
|
||||||
this.store.fetchDetail({ ...item, id });
|
|
||||||
}
|
|
||||||
|
|
||||||
static id = 'domain-edit';
|
static id = 'domain-edit';
|
||||||
|
|
||||||
static title = t('Edit Domain');
|
static title = t('Edit Domain');
|
||||||
|
|
||||||
static path(item) {
|
static buttonText = t('Edit');
|
||||||
return `/identity/domain-admin/edit/${item.id}`;
|
|
||||||
}
|
|
||||||
|
|
||||||
static policy = 'identity:update_domain';
|
static policy = 'identity:update_domain';
|
||||||
|
|
||||||
@ -43,45 +33,12 @@ export class EditForm extends FormAction {
|
|||||||
return Promise.resolve(true);
|
return Promise.resolve(true);
|
||||||
}
|
}
|
||||||
|
|
||||||
get listUrl() {
|
|
||||||
return this.getRoutePath('domain');
|
|
||||||
}
|
|
||||||
|
|
||||||
get data() {
|
|
||||||
return this.store.detail || [];
|
|
||||||
}
|
|
||||||
|
|
||||||
get name() {
|
|
||||||
const { name } = this.data;
|
|
||||||
return `${t('edit domain')} ${name}`;
|
|
||||||
}
|
|
||||||
|
|
||||||
get labelCol() {
|
|
||||||
return {
|
|
||||||
xs: { span: 6 },
|
|
||||||
sm: { span: 5 },
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
get domainUserList() {
|
|
||||||
return (this.store.domainUsers || []).map((it) => ({
|
|
||||||
label: it.name,
|
|
||||||
value: it.id,
|
|
||||||
}));
|
|
||||||
}
|
|
||||||
|
|
||||||
get defaultValue() {
|
get defaultValue() {
|
||||||
const { name, description, domain_administrator } = this.store.detail;
|
const { name, description } = this.item;
|
||||||
const userIds = [];
|
return {
|
||||||
(domain_administrator || []).map((it) => userIds.push(it.id));
|
name,
|
||||||
if (name && this.formRef.current) {
|
description,
|
||||||
this.formRef.current.setFieldsValue({
|
};
|
||||||
name,
|
|
||||||
description,
|
|
||||||
adminUsers: userIds,
|
|
||||||
});
|
|
||||||
}
|
|
||||||
return {};
|
|
||||||
}
|
}
|
||||||
|
|
||||||
get formItems() {
|
get formItems() {
|
||||||
@ -95,13 +52,6 @@ export class EditForm extends FormAction {
|
|||||||
help: t('The name cannot be modified after creation'),
|
help: t('The name cannot be modified after creation'),
|
||||||
disabled: true,
|
disabled: true,
|
||||||
},
|
},
|
||||||
{
|
|
||||||
name: 'adminUsers',
|
|
||||||
label: t('Domain Manager'),
|
|
||||||
type: 'select',
|
|
||||||
mode: 'multiple',
|
|
||||||
options: this.domainUserList,
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
name: 'description',
|
name: 'description',
|
||||||
label: t('Description'),
|
label: t('Description'),
|
||||||
@ -111,32 +61,9 @@ export class EditForm extends FormAction {
|
|||||||
}
|
}
|
||||||
|
|
||||||
onSubmit = async (values) => {
|
onSubmit = async (values) => {
|
||||||
const { description, adminUsers } = values;
|
const { id } = this.item;
|
||||||
const {
|
return this.store.edit({ id, ...values });
|
||||||
adminRoleId: role_id,
|
|
||||||
detail: { domain_administrator: oldUsers },
|
|
||||||
} = this.store;
|
|
||||||
const {
|
|
||||||
params: { id },
|
|
||||||
} = this.props.match;
|
|
||||||
const promiseList = [];
|
|
||||||
oldUsers.forEach((user) => {
|
|
||||||
const { id: user_id } = user;
|
|
||||||
if (adminUsers.indexOf(user_id) === -1) {
|
|
||||||
promiseList.push(
|
|
||||||
globalDomainStore.deleteDomainAdmin({ id, user_id, role_id })
|
|
||||||
);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
adminUsers.forEach((user_id) =>
|
|
||||||
promiseList.push(
|
|
||||||
globalDomainStore.setDomainAdmin({ id, user_id, role_id })
|
|
||||||
)
|
|
||||||
);
|
|
||||||
promiseList.push(globalDomainStore.edit({ id, description }));
|
|
||||||
const results = await Promise.all(promiseList);
|
|
||||||
return results;
|
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
export default inject('rootStore')(observer(EditForm));
|
export default inject('rootStore')(observer(Edit));
|
||||||
|
@ -33,6 +33,10 @@ export default class ForbiddenAction extends ConfirmAction {
|
|||||||
return t('Forbidden Domain');
|
return t('Forbidden Domain');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
get isDanger() {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
policy = 'identity:update_domain';
|
policy = 'identity:update_domain';
|
||||||
|
|
||||||
allowedCheckFunc = (item) => {
|
allowedCheckFunc = (item) => {
|
||||||
|
@ -12,29 +12,29 @@
|
|||||||
// See the License for the specific language governing permissions and
|
// See the License for the specific language governing permissions and
|
||||||
// limitations under the License.
|
// limitations under the License.
|
||||||
|
|
||||||
import createActionConfig from './Create';
|
import Create from './Create';
|
||||||
import deleteActionConfig from './Delete';
|
import Delete from './Delete';
|
||||||
import editActionConfig from './Edit';
|
import Edit from './Edit';
|
||||||
import enableActionConfig from './Enable';
|
import Enable from './Enable';
|
||||||
import forbiddenActionConfig from './Forbidden';
|
import Forbidden from './Forbidden';
|
||||||
|
|
||||||
const actionConfigs = {
|
const actionConfigs = {
|
||||||
rowActions: {
|
rowActions: {
|
||||||
firstAction: editActionConfig,
|
firstAction: Edit,
|
||||||
moreActions: [
|
moreActions: [
|
||||||
{
|
{
|
||||||
action: deleteActionConfig,
|
action: Delete,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
action: enableActionConfig,
|
action: Enable,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
action: forbiddenActionConfig,
|
action: Forbidden,
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
batchActions: [deleteActionConfig],
|
batchActions: [Delete],
|
||||||
primaryActions: [createActionConfig],
|
primaryActions: [Create],
|
||||||
};
|
};
|
||||||
|
|
||||||
export default actionConfigs;
|
export default actionConfigs;
|
||||||
|
@ -15,16 +15,14 @@
|
|||||||
import { observer, inject } from 'mobx-react';
|
import { observer, inject } from 'mobx-react';
|
||||||
import Base from 'containers/List';
|
import Base from 'containers/List';
|
||||||
import globalDomainStore from 'stores/keystone/domain';
|
import globalDomainStore from 'stores/keystone/domain';
|
||||||
|
import { enabledColumn } from 'resources/keystone/domain';
|
||||||
|
import actionConfigs from './actions';
|
||||||
|
|
||||||
export class Domains extends Base {
|
export class Domains extends Base {
|
||||||
init() {
|
init() {
|
||||||
this.store = globalDomainStore;
|
this.store = globalDomainStore;
|
||||||
}
|
}
|
||||||
|
|
||||||
get tabs() {
|
|
||||||
return [];
|
|
||||||
}
|
|
||||||
|
|
||||||
get policy() {
|
get policy() {
|
||||||
return 'identity:list_domains';
|
return 'identity:list_domains';
|
||||||
}
|
}
|
||||||
@ -37,6 +35,10 @@ export class Domains extends Base {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
get actionConfigs() {
|
||||||
|
return actionConfigs;
|
||||||
|
}
|
||||||
|
|
||||||
getColumns = () => [
|
getColumns = () => [
|
||||||
{
|
{
|
||||||
title: t('Domain ID/Name'),
|
title: t('Domain ID/Name'),
|
||||||
@ -44,11 +46,16 @@ export class Domains extends Base {
|
|||||||
routeName: 'domainDetailAdmin',
|
routeName: 'domainDetailAdmin',
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: t('Member Num'),
|
title: t('User Num'),
|
||||||
dataIndex: 'user_num',
|
dataIndex: 'userCount',
|
||||||
isHideable: true,
|
isHideable: true,
|
||||||
render: (user_num) => `${t('User Num: ')}${user_num}`,
|
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
title: t('Project Num'),
|
||||||
|
dataIndex: 'projectCount',
|
||||||
|
isHideable: true,
|
||||||
|
},
|
||||||
|
enabledColumn,
|
||||||
{
|
{
|
||||||
title: t('Description'),
|
title: t('Description'),
|
||||||
dataIndex: 'description',
|
dataIndex: 'description',
|
||||||
|
@ -12,11 +12,10 @@
|
|||||||
// See the License for the specific language governing permissions and
|
// See the License for the specific language governing permissions and
|
||||||
// limitations under the License.
|
// limitations under the License.
|
||||||
|
|
||||||
import React from 'react';
|
|
||||||
import { inject, observer } from 'mobx-react';
|
import { inject, observer } from 'mobx-react';
|
||||||
import { Badge } from 'antd';
|
|
||||||
import { ProjectStore } from 'stores/keystone/project';
|
import { ProjectStore } from 'stores/keystone/project';
|
||||||
import Base from 'containers/TabDetail';
|
import Base from 'containers/TabDetail';
|
||||||
|
import { enabledColumn } from 'resources/keystone/domain';
|
||||||
import UserGroup from '../../UserGroup';
|
import UserGroup from '../../UserGroup';
|
||||||
import User from '../../User';
|
import User from '../../User';
|
||||||
import Quota from './Quota';
|
import Quota from './Quota';
|
||||||
@ -53,17 +52,7 @@ export class Detail extends Base {
|
|||||||
title: t('Project Name'),
|
title: t('Project Name'),
|
||||||
dataIndex: 'name',
|
dataIndex: 'name',
|
||||||
},
|
},
|
||||||
{
|
enabledColumn,
|
||||||
title: t('Enabled'),
|
|
||||||
dataIndex: 'enabled',
|
|
||||||
isHideable: true,
|
|
||||||
render: (val) => {
|
|
||||||
if (val === true) {
|
|
||||||
return <Badge color="green" text={t('Yes')} />;
|
|
||||||
}
|
|
||||||
return <Badge color="red" text={t('No')} />;
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
title: t('User Num'),
|
title: t('User Num'),
|
||||||
dataIndex: 'user_num',
|
dataIndex: 'user_num',
|
||||||
|
@ -17,7 +17,7 @@ import { ModalAction } from 'containers/Action';
|
|||||||
import globalDomainStore from 'stores/keystone/domain';
|
import globalDomainStore from 'stores/keystone/domain';
|
||||||
import globalProjectStore from 'stores/keystone/project';
|
import globalProjectStore from 'stores/keystone/project';
|
||||||
import { regex } from 'utils/validate';
|
import { regex } from 'utils/validate';
|
||||||
import { statusTypes } from 'utils/constants';
|
import { statusTypes } from 'resources/keystone/domain';
|
||||||
|
|
||||||
export class CreateForm extends ModalAction {
|
export class CreateForm extends ModalAction {
|
||||||
constructor(props) {
|
constructor(props) {
|
||||||
|
@ -15,7 +15,7 @@
|
|||||||
import { inject, observer } from 'mobx-react';
|
import { inject, observer } from 'mobx-react';
|
||||||
import { ModalAction } from 'containers/Action';
|
import { ModalAction } from 'containers/Action';
|
||||||
import globalProjectStore from 'stores/keystone/project';
|
import globalProjectStore from 'stores/keystone/project';
|
||||||
import { statusTypes } from 'utils/constants';
|
import { statusTypes } from 'resources/keystone/domain';
|
||||||
|
|
||||||
export class EditForm extends ModalAction {
|
export class EditForm extends ModalAction {
|
||||||
init() {
|
init() {
|
||||||
|
@ -14,11 +14,12 @@
|
|||||||
|
|
||||||
import React from 'react';
|
import React from 'react';
|
||||||
import { observer, inject } from 'mobx-react';
|
import { observer, inject } from 'mobx-react';
|
||||||
import { Divider, Badge } from 'antd';
|
import { Divider } from 'antd';
|
||||||
import Base from 'containers/List';
|
import Base from 'containers/List';
|
||||||
import globalProjectStore, { ProjectStore } from 'stores/keystone/project';
|
import globalProjectStore, { ProjectStore } from 'stores/keystone/project';
|
||||||
import { yesNoOptions, emptyActionConfig } from 'utils/constants';
|
import { yesNoOptions, emptyActionConfig } from 'utils/constants';
|
||||||
import { SimpleTag } from 'resources/nova/instance';
|
import { SimpleTag } from 'resources/nova/instance';
|
||||||
|
import { enabledColumn } from 'resources/keystone/domain';
|
||||||
import actionConfigs from './actions';
|
import actionConfigs from './actions';
|
||||||
import styles from './index.less';
|
import styles from './index.less';
|
||||||
|
|
||||||
@ -106,18 +107,7 @@ export class Projects extends Base {
|
|||||||
)}${group_num}`;
|
)}${group_num}`;
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
{
|
enabledColumn,
|
||||||
title: t('Enabled'),
|
|
||||||
dataIndex: 'enabled',
|
|
||||||
isHideable: true,
|
|
||||||
render: (val) => {
|
|
||||||
if (val === true) {
|
|
||||||
return <Badge color="green" text={t('Yes')} />;
|
|
||||||
}
|
|
||||||
return <Badge color="red" text={t('No')} />;
|
|
||||||
},
|
|
||||||
stringify: (enabled) => (enabled ? t('Yes') : t('No')),
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
title: t('Tags'),
|
title: t('Tags'),
|
||||||
dataIndex: 'tags',
|
dataIndex: 'tags',
|
||||||
|
@ -12,13 +12,12 @@
|
|||||||
// See the License for the specific language governing permissions and
|
// See the License for the specific language governing permissions and
|
||||||
// limitations under the License.
|
// limitations under the License.
|
||||||
|
|
||||||
import React from 'react';
|
|
||||||
import { inject, observer } from 'mobx-react';
|
import { inject, observer } from 'mobx-react';
|
||||||
import { Badge } from 'antd';
|
|
||||||
import { UserStore } from 'stores/keystone/user';
|
import { UserStore } from 'stores/keystone/user';
|
||||||
import globalDomainStore from 'stores/keystone/domain';
|
import globalDomainStore from 'stores/keystone/domain';
|
||||||
import Base from 'containers/TabDetail';
|
import Base from 'containers/TabDetail';
|
||||||
import Credentials from 'src/pages/user-center/containers/Credentials';
|
import Credentials from 'src/pages/user-center/containers/Credentials';
|
||||||
|
import { enabledColumn } from 'resources/keystone/domain';
|
||||||
import UserGroup from '../../UserGroup';
|
import UserGroup from '../../UserGroup';
|
||||||
import Project from '../../Project';
|
import Project from '../../Project';
|
||||||
import actionConfigs from '../actions';
|
import actionConfigs from '../actions';
|
||||||
@ -70,17 +69,7 @@ export class UserDetail extends Base {
|
|||||||
title: t('User Name'),
|
title: t('User Name'),
|
||||||
dataIndex: 'name',
|
dataIndex: 'name',
|
||||||
},
|
},
|
||||||
{
|
enabledColumn,
|
||||||
title: t('Enabled'),
|
|
||||||
dataIndex: 'enabled',
|
|
||||||
isHideable: true,
|
|
||||||
render: (val) => {
|
|
||||||
if (val === true) {
|
|
||||||
return <Badge color="green" text={t('Yes')} />;
|
|
||||||
}
|
|
||||||
return <Badge color="red" text={t('No')} />;
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
title: t('Real Name'),
|
title: t('Real Name'),
|
||||||
dataIndex: 'real_name',
|
dataIndex: 'real_name',
|
||||||
|
@ -26,7 +26,7 @@ import {
|
|||||||
phoneNumberValidate,
|
phoneNumberValidate,
|
||||||
emailValidate,
|
emailValidate,
|
||||||
} from 'utils/validate';
|
} from 'utils/validate';
|
||||||
import { statusTypes } from 'utils/constants';
|
import { statusTypes } from 'resources/keystone/domain';
|
||||||
|
|
||||||
export class CreateForm extends FormAction {
|
export class CreateForm extends FormAction {
|
||||||
constructor(props) {
|
constructor(props) {
|
||||||
|
@ -20,7 +20,7 @@ import globalProjectStore from 'stores/keystone/project';
|
|||||||
import globalRoleStore from 'stores/keystone/role';
|
import globalRoleStore from 'stores/keystone/role';
|
||||||
import { getPasswordOtherRule, phoneNumberValidate } from 'utils/validate';
|
import { getPasswordOtherRule, phoneNumberValidate } from 'utils/validate';
|
||||||
import globalDomainStore from 'stores/keystone/domain';
|
import globalDomainStore from 'stores/keystone/domain';
|
||||||
import { statusTypes } from 'utils/constants';
|
import { statusTypes } from 'resources/keystone/domain';
|
||||||
|
|
||||||
export class CreateForm extends ModalAction {
|
export class CreateForm extends ModalAction {
|
||||||
init() {
|
init() {
|
||||||
|
@ -20,6 +20,7 @@ import globalUserStore, { UserStore } from 'stores/keystone/user';
|
|||||||
import { yesNoOptions, emptyActionConfig } from 'utils/constants';
|
import { yesNoOptions, emptyActionConfig } from 'utils/constants';
|
||||||
import { Link } from 'react-router-dom';
|
import { Link } from 'react-router-dom';
|
||||||
import { FileTextOutlined } from '@ant-design/icons';
|
import { FileTextOutlined } from '@ant-design/icons';
|
||||||
|
import { enabledColumn } from 'resources/keystone/domain';
|
||||||
import actionConfigs from './actions';
|
import actionConfigs from './actions';
|
||||||
import actionConfigsInDomain from './actionsInDomain';
|
import actionConfigsInDomain from './actionsInDomain';
|
||||||
|
|
||||||
@ -204,18 +205,7 @@ export class User extends Base {
|
|||||||
dataIndex: 'phone',
|
dataIndex: 'phone',
|
||||||
isHideable: true,
|
isHideable: true,
|
||||||
},
|
},
|
||||||
{
|
enabledColumn,
|
||||||
title: t('Enabled'),
|
|
||||||
dataIndex: 'enabled',
|
|
||||||
isHideable: true,
|
|
||||||
render: (val) => {
|
|
||||||
if (val === true) {
|
|
||||||
return <Badge color="green" text={t('Yes')} />;
|
|
||||||
}
|
|
||||||
return <Badge color="red" text={t('No')} />;
|
|
||||||
},
|
|
||||||
stringify: (val) => (val ? t('Yes') : t('No')),
|
|
||||||
},
|
|
||||||
];
|
];
|
||||||
if (!this.inDetailPage) {
|
if (!this.inDetailPage) {
|
||||||
return columns.filter(
|
return columns.filter(
|
||||||
|
@ -15,8 +15,6 @@
|
|||||||
import BaseLayout from 'layouts/Basic';
|
import BaseLayout from 'layouts/Basic';
|
||||||
import E404 from 'pages/base/containers/404';
|
import E404 from 'pages/base/containers/404';
|
||||||
import Domain from '../containers/Domain';
|
import Domain from '../containers/Domain';
|
||||||
import DomainCreate from '../containers/Domain/actions/Create';
|
|
||||||
import DomainEdit from '../containers/Domain/actions/Edit';
|
|
||||||
import DomainDetail from '../containers/Domain/Detail';
|
import DomainDetail from '../containers/Domain/Detail';
|
||||||
import Project from '../containers/Project';
|
import Project from '../containers/Project';
|
||||||
import ProjectCreate from '../containers/Project/actions/Create';
|
import ProjectCreate from '../containers/Project/actions/Create';
|
||||||
@ -45,16 +43,6 @@ export default [
|
|||||||
component: DomainDetail,
|
component: DomainDetail,
|
||||||
exact: true,
|
exact: true,
|
||||||
},
|
},
|
||||||
{
|
|
||||||
path: `${PATH}/domain-admin/create`,
|
|
||||||
component: DomainCreate,
|
|
||||||
exact: true,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
path: `${PATH}/domain-admin/edit/:id`,
|
|
||||||
component: DomainEdit,
|
|
||||||
exact: true,
|
|
||||||
},
|
|
||||||
{ path: `${PATH}/project`, component: Project, exact: true },
|
{ path: `${PATH}/project`, component: Project, exact: true },
|
||||||
{ path: `${PATH}/project-admin`, component: Project, exact: true },
|
{ path: `${PATH}/project-admin`, component: Project, exact: true },
|
||||||
{ path: `${PATH}/project/create`, component: ProjectCreate, exact: true },
|
{ path: `${PATH}/project/create`, component: ProjectCreate, exact: true },
|
||||||
|
26
src/resources/keystone/domain.jsx
Normal file
26
src/resources/keystone/domain.jsx
Normal file
@ -0,0 +1,26 @@
|
|||||||
|
import React from 'react';
|
||||||
|
import { Badge } from 'antd';
|
||||||
|
|
||||||
|
export const statusTypes = [
|
||||||
|
{
|
||||||
|
label: t('Enable'),
|
||||||
|
value: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
label: t('Forbidden'),
|
||||||
|
value: false,
|
||||||
|
},
|
||||||
|
];
|
||||||
|
|
||||||
|
export const enabledColumn = {
|
||||||
|
title: t('Enabled'),
|
||||||
|
dataIndex: 'enabled',
|
||||||
|
isHideable: true,
|
||||||
|
render: (val) => {
|
||||||
|
if (val === true) {
|
||||||
|
return <Badge color="green" text={t('Yes')} />;
|
||||||
|
}
|
||||||
|
return <Badge color="red" text={t('No')} />;
|
||||||
|
},
|
||||||
|
stringify: (val) => (val ? t('Yes') : t('No')),
|
||||||
|
};
|
@ -13,7 +13,6 @@
|
|||||||
// limitations under the License.
|
// limitations under the License.
|
||||||
|
|
||||||
import { action, observable } from 'mobx';
|
import { action, observable } from 'mobx';
|
||||||
import { get } from 'lodash';
|
|
||||||
import client from 'client';
|
import client from 'client';
|
||||||
import Base from 'stores/base';
|
import Base from 'stores/base';
|
||||||
|
|
||||||
@ -21,12 +20,6 @@ export class DomainStore extends Base {
|
|||||||
@observable
|
@observable
|
||||||
domains = [];
|
domains = [];
|
||||||
|
|
||||||
@observable
|
|
||||||
domainUsers = [];
|
|
||||||
|
|
||||||
@observable
|
|
||||||
adminRoleId = '';
|
|
||||||
|
|
||||||
get client() {
|
get client() {
|
||||||
return client.keystone.domains;
|
return client.keystone.domains;
|
||||||
}
|
}
|
||||||
@ -35,66 +28,50 @@ export class DomainStore extends Base {
|
|||||||
return client.keystone.users;
|
return client.keystone.users;
|
||||||
}
|
}
|
||||||
|
|
||||||
@action
|
get projectClient() {
|
||||||
async fetchList({
|
return client.keystone.projects;
|
||||||
limit,
|
|
||||||
page,
|
|
||||||
sortKey,
|
|
||||||
sortOrder,
|
|
||||||
conditions,
|
|
||||||
...filters
|
|
||||||
} = {}) {
|
|
||||||
this.list.isLoading = true;
|
|
||||||
// todo: no page, no limit, fetch all
|
|
||||||
// const params = { ...filters };
|
|
||||||
|
|
||||||
await Promise.all([this.client.list(), this.userClient.list()]).then(
|
|
||||||
([domainsResult, usersResult]) => {
|
|
||||||
const { domains } = domainsResult;
|
|
||||||
// eslint-disable-next-line array-callback-return
|
|
||||||
domains.map((domain) => {
|
|
||||||
const domainUsers = usersResult.users.filter(
|
|
||||||
(it) => it.domain_id === domain.id
|
|
||||||
);
|
|
||||||
domain.user_num = domainUsers.length;
|
|
||||||
});
|
|
||||||
|
|
||||||
// const { domains: items } = domainsResult;
|
|
||||||
this.list.update({
|
|
||||||
data: domains,
|
|
||||||
total: domains.length || 0,
|
|
||||||
limit: Number(limit) || 10,
|
|
||||||
page: Number(page) || 1,
|
|
||||||
sortKey,
|
|
||||||
sortOrder,
|
|
||||||
filters,
|
|
||||||
isLoading: false,
|
|
||||||
...(this.list.silent ? {} : { selectedRowKeys: [] }),
|
|
||||||
});
|
|
||||||
return domains;
|
|
||||||
}
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@action
|
async listDidFetch(items) {
|
||||||
async fetchDetail({ id, silent }) {
|
if (!items.length) {
|
||||||
if (!silent) {
|
return items;
|
||||||
this.isLoading = true;
|
|
||||||
}
|
}
|
||||||
await Promise.all([this.client.show(id), this.userClient.list()]).then(
|
const [userResult, projectResult] = await Promise.all([
|
||||||
([result, usersResult]) => {
|
this.userClient.list(),
|
||||||
const domain = this.mapper(get(result, this.responseKey) || result);
|
this.projectClient.list(),
|
||||||
domain.domain_administrator = [];
|
]);
|
||||||
const domainUsers = usersResult.users.filter(
|
return items.map((it) => {
|
||||||
(it) => it.domain_id === domain.id
|
const users = (userResult.users || []).filter(
|
||||||
);
|
(user) => user.domain_id === it.id
|
||||||
domain.user_num = domainUsers.length;
|
);
|
||||||
this.domainUsers = domainUsers;
|
const projects = (projectResult.projects || []).filter(
|
||||||
this.detail = domain;
|
(project) => project.domain_id === it.id
|
||||||
this.isLoading = false;
|
);
|
||||||
return domain;
|
return {
|
||||||
}
|
...it,
|
||||||
);
|
users,
|
||||||
|
userCount: users.length,
|
||||||
|
projects,
|
||||||
|
projectCount: projects.length,
|
||||||
|
};
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
async detailDidFetch(item) {
|
||||||
|
const { id } = item;
|
||||||
|
const [userResult, projectResult] = await Promise.all([
|
||||||
|
this.userClient.list({ domain_id: id }),
|
||||||
|
this.projectClient.list({ domain_id: id }),
|
||||||
|
]);
|
||||||
|
const { users = [] } = userResult || {};
|
||||||
|
const { projects = [] } = projectResult || {};
|
||||||
|
return {
|
||||||
|
...item,
|
||||||
|
users,
|
||||||
|
userCount: users.length,
|
||||||
|
projects,
|
||||||
|
projectCount: projects.length,
|
||||||
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
@action
|
@action
|
||||||
@ -103,14 +80,6 @@ export class DomainStore extends Base {
|
|||||||
this.domains = domainsResult.domains;
|
this.domains = domainsResult.domains;
|
||||||
}
|
}
|
||||||
|
|
||||||
@action
|
|
||||||
async update({ id, body }) {
|
|
||||||
this.isSubmitting = true;
|
|
||||||
const resData = await this.client.update(id, body);
|
|
||||||
this.isSubmitting = false;
|
|
||||||
return resData;
|
|
||||||
}
|
|
||||||
|
|
||||||
@action
|
@action
|
||||||
async edit({ id, description }) {
|
async edit({ id, description }) {
|
||||||
const reqBody = {
|
const reqBody = {
|
||||||
@ -119,15 +88,6 @@ export class DomainStore extends Base {
|
|||||||
return this.submitting(this.client.patch(id, reqBody));
|
return this.submitting(this.client.patch(id, reqBody));
|
||||||
}
|
}
|
||||||
|
|
||||||
async setDomainAdmin({ id, user_id, role_id }) {
|
|
||||||
return this.submitting(this.client.users.roles.put(id, user_id, role_id));
|
|
||||||
}
|
|
||||||
|
|
||||||
async deleteDomainAdmin({ id, user_id, role_id }) {
|
|
||||||
const result = await this.client.users.roles.delete(id, user_id, role_id);
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
@action
|
@action
|
||||||
async forbidden({ id }) {
|
async forbidden({ id }) {
|
||||||
const reqBody = {
|
const reqBody = {
|
||||||
|
@ -140,14 +140,3 @@ export const projectTagsColors = shuffle([
|
|||||||
'geekblue',
|
'geekblue',
|
||||||
'purple',
|
'purple',
|
||||||
]);
|
]);
|
||||||
|
|
||||||
export const statusTypes = [
|
|
||||||
{
|
|
||||||
label: t('Enable'),
|
|
||||||
value: true,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
label: t('Forbidden'),
|
|
||||||
value: false,
|
|
||||||
},
|
|
||||||
];
|
|
||||||
|
@ -23,7 +23,7 @@ describe('The Domain Page', () => {
|
|||||||
});
|
});
|
||||||
|
|
||||||
it('successfully detail', () => {
|
it('successfully detail', () => {
|
||||||
cy.tableSearchText(name).goToDetail(0);
|
cy.tableSearchText(name).goToDetail();
|
||||||
cy.goBackToList(listUrl);
|
cy.goBackToList(listUrl);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
Loading…
Reference in New Issue
Block a user