Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit7410765

Browse files
committed
Add seperate workspace and usergroups tab
1 parentdffc683 commit7410765

File tree

3 files changed

+447
-14
lines changed

3 files changed

+447
-14
lines changed

‎client/packages/lowcoder/src/pages/setting/environments/EnvironmentDetail.tsx‎

Lines changed: 8 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,8 @@ import DeployableItemsTab from "./components/DeployableItemsTab";
2525
importEditEnvironmentModalfrom"./components/EditEnvironmentModal";
2626
import{Environment}from"./types/environment.types";
2727
importhistoryfrom"@lowcoder-ee/util/history";
28-
28+
importWorkspacesTabfrom"./components/WorkspacesTab";
29+
importUserGroupsTabfrom"./components/UserGroupsTab";
2930
const{ Title, Text}=Typography;
3031
const{ TabPane}=Tabs;
3132

@@ -227,13 +228,10 @@ const EnvironmentDetail: React.FC = () => {
227228
{/* Tabs for Workspaces and User Groups */}
228229
<TabsdefaultActiveKey="workspaces">
229230
<TabPanetab="Workspaces"key="workspaces">
230-
{/* Using our new generic component with the workspace config */}
231-
<DeployableItemsTab
232-
environment={environment}
233-
config={workspaceConfig}
234-
title="Workspaces in this Environment"
235-
/>
231+
{/* Using our new standalone WorkspacesTab component */}
232+
<WorkspacesTabenvironment={environment}/>
236233
</TabPane>
234+
237235
<TabPane
238236
tab={
239237
<span>
@@ -242,15 +240,11 @@ const EnvironmentDetail: React.FC = () => {
242240
}
243241
key="userGroups"
244242
>
245-
{/* Using our new generic component with the user group config */}
246-
<DeployableItemsTab
247-
environment={environment}
248-
config={userGroupsConfig}
249-
title="User Groups in this Environment"
250-
/>
243+
{/* Now using our standalone UserGroupsTab component */}
244+
<UserGroupsTabenvironment={environment}/>
251245
</TabPane>
252246
</Tabs>
253-
247+
254248
{/* Edit Environment Modal */}
255249
{environment&&(
256250
<EditEnvironmentModal
Lines changed: 222 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,222 @@
1+
importReact,{useState,useEffect}from'react';
2+
import{Card,Button,Divider,Alert,message,Table,Tag,Input,Space}from'antd';
3+
import{SyncOutlined,TeamOutlined}from'@ant-design/icons';
4+
importTitlefrom'antd/lib/typography/Title';
5+
import{Environment}from'../types/environment.types';
6+
import{UserGroup}from'../types/userGroup.types';
7+
import{getEnvironmentUserGroups}from'../services/environments.service';
8+
import{Spin,Empty}from'antd';
9+
10+
const{ Search}=Input;
11+
12+
interfaceUserGroupsTabProps{
13+
environment:Environment;
14+
}
15+
16+
constUserGroupsTab:React.FC<UserGroupsTabProps>=({ environment})=>{
17+
const[userGroups,setUserGroups]=useState<UserGroup[]>([]);
18+
const[stats,setStats]=useState({
19+
total:0,
20+
active:0,
21+
inactive:0
22+
});
23+
const[loading,setLoading]=useState(false);
24+
const[refreshing,setRefreshing]=useState(false);
25+
const[error,setError]=useState<string|null>(null);
26+
const[searchText,setSearchText]=useState('');
27+
28+
// Fetch user groups
29+
constfetchUserGroups=async()=>{
30+
if(!environment)return;
31+
32+
setLoading(true);
33+
setError(null);
34+
35+
try{
36+
// Check for required environment properties
37+
if(!environment.environmentApikey||!environment.environmentApiServiceUrl){
38+
setError('Missing required configuration: API key or API service URL');
39+
setLoading(false);
40+
return;
41+
}
42+
43+
constgroups=awaitgetEnvironmentUserGroups(
44+
environment.environmentId,
45+
environment.environmentApikey,
46+
environment.environmentApiServiceUrl
47+
);
48+
49+
setUserGroups(groups);
50+
51+
// Calculate stats
52+
consttotal=groups.length;
53+
constactive=groups.filter(group=>group.state==='ACTIVE').length;
54+
55+
setStats({
56+
total,
57+
active,
58+
inactive:total-active
59+
});
60+
}catch(err){
61+
setError(errinstanceofError ?err.message :"Failed to fetch user groups");
62+
}finally{
63+
setLoading(false);
64+
setRefreshing(false);
65+
}
66+
};
67+
68+
useEffect(()=>{
69+
fetchUserGroups();
70+
},[environment]);
71+
72+
// Handle refresh
73+
consthandleRefresh=()=>{
74+
setRefreshing(true);
75+
fetchUserGroups();
76+
};
77+
78+
// Filter user groups based on search
79+
constfilteredUserGroups=searchText
80+
?userGroups.filter(group=>
81+
group.name.toLowerCase().includes(searchText.toLowerCase())||
82+
group.id.toLowerCase().includes(searchText.toLowerCase()))
83+
:userGroups;
84+
85+
// Table columns
86+
constcolumns=[
87+
{
88+
title:'Name',
89+
dataIndex:'name',
90+
key:'name',
91+
render:(text:string)=><spanclassName="group-name">{text}</span>
92+
},
93+
{
94+
title:'ID',
95+
dataIndex:'id',
96+
key:'id',
97+
ellipsis:true,
98+
},
99+
{
100+
title:'Type',
101+
dataIndex:'type',
102+
key:'type',
103+
render:(type:string)=>(
104+
<Tagcolor={type==='USER' ?'blue' :'purple'}>
105+
{type}
106+
</Tag>
107+
),
108+
},
109+
{
110+
title:'Status',
111+
dataIndex:'state',
112+
key:'state',
113+
render:(state:string)=>(
114+
<Tagcolor={state==='ACTIVE' ?'green' :'red'}>
115+
{state}
116+
</Tag>
117+
),
118+
},
119+
{
120+
title:'Member Count',
121+
dataIndex:'memberCount',
122+
key:'memberCount',
123+
}
124+
];
125+
126+
return(
127+
<Card>
128+
{/* Header with refresh button */}
129+
<divstyle={{display:"flex",justifyContent:"space-between",alignItems:"center",marginBottom:"16px"}}>
130+
<Titlelevel={5}>User Groups in this Environment</Title>
131+
<Button
132+
icon={<SyncOutlinedspin={refreshing}/>}
133+
onClick={handleRefresh}
134+
loading={loading}
135+
>
136+
Refresh
137+
</Button>
138+
</div>
139+
140+
{/* Stats display */}
141+
<divstyle={{display:'flex',flexWrap:'wrap',gap:'24px',marginBottom:'16px'}}>
142+
<div>
143+
<divstyle={{fontSize:'14px',color:'#8c8c8c'}}>Total Groups</div>
144+
<divstyle={{fontSize:'24px',fontWeight:600}}>{stats.total}</div>
145+
</div>
146+
<div>
147+
<divstyle={{fontSize:'14px',color:'#8c8c8c'}}>Active</div>
148+
<divstyle={{fontSize:'24px',fontWeight:600}}>{stats.active}</div>
149+
</div>
150+
<div>
151+
<divstyle={{fontSize:'14px',color:'#8c8c8c'}}>Inactive</div>
152+
<divstyle={{fontSize:'24px',fontWeight:600}}>{stats.inactive}</div>
153+
</div>
154+
</div>
155+
156+
<Dividerstyle={{margin:"16px 0"}}/>
157+
158+
{/* Error display */}
159+
{error&&(
160+
<Alert
161+
message="Error loading user groups"
162+
description={error}
163+
type="error"
164+
showIcon
165+
style={{marginBottom:"16px"}}
166+
/>
167+
)}
168+
169+
{/* Configuration warnings */}
170+
{(!environment.environmentApikey||!environment.environmentApiServiceUrl)&&!error&&(
171+
<Alert
172+
message="Configuration Issue"
173+
description="Missing required configuration: API key or API service URL"
174+
type="warning"
175+
showIcon
176+
style={{marginBottom:"16px"}}
177+
/>
178+
)}
179+
180+
{/* Content */}
181+
{loading ?(
182+
<divstyle={{display:'flex',justifyContent:'center',padding:'20px'}}>
183+
<Spintip="Loading user groups..."/>
184+
</div>
185+
) :userGroups.length===0 ?(
186+
<Empty
187+
description={error||"No user groups found in this environment"}
188+
image={Empty.PRESENTED_IMAGE_SIMPLE}
189+
/>
190+
) :(
191+
<>
192+
{/* Search Bar */}
193+
<divstyle={{marginBottom:16}}>
194+
<Search
195+
placeholder="Search user groups by name or ID"
196+
allowClear
197+
onSearch={value=>setSearchText(value)}
198+
onChange={e=>setSearchText(e.target.value)}
199+
style={{width:300}}
200+
/>
201+
{searchText&&filteredUserGroups.length!==userGroups.length&&(
202+
<divstyle={{marginTop:8}}>
203+
Showing{filteredUserGroups.length} of{userGroups.length} user groups
204+
</div>
205+
)}
206+
</div>
207+
208+
<Table
209+
columns={columns}
210+
dataSource={filteredUserGroups}
211+
rowKey="id"
212+
pagination={{pageSize:10}}
213+
size="middle"
214+
scroll={{x:'max-content'}}
215+
/>
216+
</>
217+
)}
218+
</Card>
219+
);
220+
};
221+
222+
exportdefaultUserGroupsTab;

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp