[Feature] Add Workspace Support (#284)
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/common/Constants.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/common/Constants.java
index 22c0183..7dcb105 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/common/Constants.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/common/Constants.java
@@ -495,7 +495,7 @@
public static final String WORKFLOW_RELATION_LIST = "workFlowRelationList";
/** session user */
- public static final String SESSION_USER = "session.user";
+ public static final String SESSION_USER_CONTEXT = "session.user.context";
public static final String SESSION_ID = "sessionId";
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/config/AsyncConfig.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/config/AsyncConfig.java
index 8a66521..3652142 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/config/AsyncConfig.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/config/AsyncConfig.java
@@ -16,8 +16,8 @@
*/
package org.apache.seatunnel.app.config;
-import org.apache.seatunnel.app.dal.entity.User;
import org.apache.seatunnel.app.security.UserContext;
+import org.apache.seatunnel.app.security.UserContextHolder;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
@@ -59,13 +59,13 @@
@Override
public Runnable decorate(Runnable runnable) {
try {
- User user = UserContext.getUser();
+ UserContext userContext = UserContextHolder.getUserContext();
return () -> {
try {
- UserContext.setUser(user);
+ UserContextHolder.setUserContext(userContext);
runnable.run();
} finally {
- UserContext.clear();
+ UserContextHolder.clear();
}
};
} catch (Exception e) {
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/controller/SeatunnelDatasourceController.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/controller/SeatunnelDatasourceController.java
index 6dfe70c..85da2ac 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/controller/SeatunnelDatasourceController.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/controller/SeatunnelDatasourceController.java
@@ -48,7 +48,6 @@
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
-import org.springframework.web.bind.annotation.RequestAttribute;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
@@ -57,7 +56,6 @@
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
-import springfox.documentation.annotations.ApiIgnore;
import javax.annotation.Resource;
@@ -67,8 +65,6 @@
import java.util.Optional;
import java.util.stream.Collectors;
-import static org.apache.seatunnel.app.common.Constants.SESSION_USER;
-
@RestController
@RequestMapping("/seatunnel/api/v1/datasource")
public class SeatunnelDatasourceController extends BaseController {
@@ -278,7 +274,6 @@
})
@GetMapping("/support-datasources")
Result<Map<Integer, List<DataSourcePluginInfo>>> getSupportDatasources(
- @ApiIgnore @RequestAttribute(value = SESSION_USER) User loginUser,
@RequestParam("showVirtualDataSource") Boolean showVirtualDataSource,
@RequestParam(value = "source", required = false) String source) {
Map<Integer, List<DataSourcePluginInfo>> allDatasources =
@@ -301,22 +296,17 @@
}
@GetMapping("/dynamic-form")
- Result<String> getDynamicForm(
- @ApiIgnore @RequestAttribute(value = SESSION_USER) User loginUser,
- @RequestParam("pluginName") String pluginName) {
+ Result<String> getDynamicForm(@RequestParam("pluginName") String pluginName) {
return Result.success(datasourceService.getDynamicForm(pluginName));
}
@GetMapping("/databases")
- Result<List<String>> getDatabases(
- @ApiIgnore @RequestAttribute(value = SESSION_USER) User loginUser,
- @RequestParam("datasourceName") String datasourceName) {
+ Result<List<String>> getDatabases(@RequestParam("datasourceName") String datasourceName) {
return Result.success(datasourceService.queryDatabaseByDatasourceName(datasourceName));
}
@GetMapping("/tables")
Result<List<String>> getTableNames(
- @ApiIgnore @RequestAttribute(value = SESSION_USER) User loginUser,
@RequestParam("datasourceName") String datasourceName,
@RequestParam("databaseName") String databaseName,
@RequestParam("filterName") String filterName,
@@ -327,7 +317,6 @@
@GetMapping("/schema")
Result<List<TableField>> getTableFields(
- @ApiIgnore @RequestAttribute(value = SESSION_USER) User loginUser,
@RequestParam("datasourceId") String datasourceId,
@RequestParam(value = "databaseName", required = false) String databaseName,
@RequestParam("tableName") String tableName) {
@@ -367,9 +356,7 @@
}
@GetMapping("/all-tables")
- Result<List<DatabaseTables>> getTables(
- @ApiIgnore @RequestAttribute(value = SESSION_USER) User loginUser,
- @RequestParam("datasourceId") String datasourceId) {
+ Result<List<DatabaseTables>> getTables(@RequestParam("datasourceId") String datasourceId) {
DatasourceDetailRes res = datasourceService.queryDatasourceDetailById(datasourceId);
List<DatabaseTables> tables = new ArrayList<>();
List<String> databases =
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/controller/VirtualTableController.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/controller/VirtualTableController.java
index 2870e57..09d8667 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/controller/VirtualTableController.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/controller/VirtualTableController.java
@@ -34,7 +34,6 @@
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
-import org.springframework.web.bind.annotation.RequestAttribute;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
@@ -43,7 +42,6 @@
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
-import springfox.documentation.annotations.ApiIgnore;
import javax.annotation.Resource;
@@ -51,8 +49,6 @@
import java.util.Map;
import java.util.stream.Collectors;
-import static org.apache.seatunnel.app.common.Constants.SESSION_USER;
-
@RestController
@RequestMapping("/seatunnel/api/v1/virtual_table")
public class VirtualTableController extends BaseController {
@@ -103,9 +99,7 @@
dataType = "VirtualTableReq")
})
@GetMapping("/check/valid")
- Result<Boolean> checkVirtualTableValid(
- @ApiIgnore @RequestAttribute(value = SESSION_USER) User loginUser,
- @RequestBody VirtualTableReq virtualTableReq) {
+ Result<Boolean> checkVirtualTableValid(@RequestBody VirtualTableReq virtualTableReq) {
return Result.success(virtualTableService.checkVirtualTableValid(virtualTableReq));
}
@@ -139,9 +133,7 @@
dataType = "String")
})
@GetMapping("/{id}")
- Result<VirtualTableDetailRes> queryVirtualTable(
- @ApiIgnore @RequestAttribute(value = SESSION_USER) User loginUser,
- @PathVariable("id") String id) {
+ Result<VirtualTableDetailRes> queryVirtualTable(@PathVariable("id") String id) {
// rsp add plugin name
return Result.success(virtualTableService.queryVirtualTable(id));
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/controller/WorkspaceController.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/controller/WorkspaceController.java
new file mode 100644
index 0000000..6eb4e93
--- /dev/null
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/controller/WorkspaceController.java
@@ -0,0 +1,69 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+
+package org.apache.seatunnel.app.controller;
+
+import org.apache.seatunnel.app.common.Result;
+import org.apache.seatunnel.app.dal.entity.Workspace;
+import org.apache.seatunnel.app.domain.request.workspace.WorkspaceReq;
+import org.apache.seatunnel.app.service.WorkspaceService;
+
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.DeleteMapping;
+import org.springframework.web.bind.annotation.GetMapping;
+import org.springframework.web.bind.annotation.PathVariable;
+import org.springframework.web.bind.annotation.PostMapping;
+import org.springframework.web.bind.annotation.PutMapping;
+import org.springframework.web.bind.annotation.RequestBody;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RestController;
+
+import java.util.List;
+
+@RestController
+@RequestMapping("/seatunnel/api/v1/workspace")
+public class WorkspaceController {
+
+ @Autowired private WorkspaceService workspaceService;
+
+ @PostMapping("/create")
+ public Result<Long> createWorkspace(@RequestBody WorkspaceReq workspaceReq) {
+ return Result.success(workspaceService.createWorkspace(workspaceReq));
+ }
+
+ @PutMapping("/update/{id}")
+ public Result<Boolean> updateWorkspace(
+ @PathVariable Long id, @RequestBody WorkspaceReq workspaceReq) {
+ return Result.success(workspaceService.updateWorkspace(id, workspaceReq));
+ }
+
+ @DeleteMapping("/delete/{id}")
+ public Result<Boolean> deleteWorkspace(@PathVariable Long id) {
+ return Result.success(workspaceService.deleteWorkspace(id));
+ }
+
+ @GetMapping("/list")
+ public Result<List<Workspace>> getAllWorkspaces() {
+ return Result.success(workspaceService.getAllWorkspaces());
+ }
+
+ @GetMapping("/list/{id}")
+ public Result<Workspace> getWorkspace(@PathVariable Long id) {
+ Workspace workspaceById = workspaceService.getWorkspace(id);
+ return Result.success(workspaceById);
+ }
+}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/IUserDao.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/IUserDao.java
index be5dd16..a8dafe7 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/IUserDao.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/IUserDao.java
@@ -51,7 +51,7 @@
void disableToken(int userId);
- UserLoginLog getLastLoginLog(Integer userId);
+ UserLoginLog getLastLoginLog(Integer userId, Long workspaceId);
/**
* query enabled users
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/IWorkspaceDao.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/IWorkspaceDao.java
new file mode 100644
index 0000000..5458ea3
--- /dev/null
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/IWorkspaceDao.java
@@ -0,0 +1,36 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+
+package org.apache.seatunnel.app.dal.dao;
+
+import org.apache.seatunnel.app.dal.entity.Workspace;
+
+import java.util.List;
+
+public interface IWorkspaceDao {
+ void insertWorkspace(Workspace workspace);
+
+ Workspace selectWorkspaceById(Long id);
+
+ Workspace selectWorkspaceByName(String workspaceName);
+
+ boolean updateWorkspaceById(Workspace workspace);
+
+ boolean deleteWorkspaceById(Long id);
+
+ List<Workspace> selectAllWorkspaces();
+}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/DatasourceDaoImpl.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/DatasourceDaoImpl.java
index fc5c760..e6c4180 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/DatasourceDaoImpl.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/DatasourceDaoImpl.java
@@ -31,6 +31,8 @@
import java.util.List;
+import static org.apache.seatunnel.app.utils.ServletUtils.getCurrentWorkspaceId;
+
@Repository
public class DatasourceDaoImpl implements IDatasourceDao {
@@ -43,23 +45,37 @@
@Override
public Datasource selectDatasourceById(Long id) {
- return datasourceMapper.selectById(id);
+ return datasourceMapper.selectOne(
+ new QueryWrapper<Datasource>()
+ .eq("id", id)
+ .eq("workspace_id", getCurrentWorkspaceId()));
}
@Override
public boolean deleteDatasourceById(Long id) {
- return datasourceMapper.deleteById(id) > 0;
+ return datasourceMapper.delete(
+ new QueryWrapper<Datasource>()
+ .eq("id", id)
+ .eq("workspace_id", getCurrentWorkspaceId()))
+ > 0;
}
@Override
public Datasource queryDatasourceByName(String name) {
return datasourceMapper.selectOne(
- new QueryWrapper<Datasource>().eq("datasource_name", name));
+ new QueryWrapper<Datasource>()
+ .eq("datasource_name", name)
+ .eq("workspace_id", getCurrentWorkspaceId()));
}
@Override
public boolean updateDatasourceById(Datasource datasource) {
- return datasourceMapper.updateById(datasource) > 0;
+ return datasourceMapper.update(
+ datasource,
+ new QueryWrapper<Datasource>()
+ .eq("id", datasource.getId())
+ .eq("workspace_id", getCurrentWorkspaceId()))
+ > 0;
}
@Override
@@ -67,12 +83,14 @@
QueryWrapper<Datasource> queryWrapper = new QueryWrapper<>();
queryWrapper.eq("datasource_name", dataSourceName);
queryWrapper.ne("id", dataSourceId);
- return datasourceMapper.selectList(queryWrapper).size() <= 0;
+ queryWrapper.eq("workspace_id", getCurrentWorkspaceId());
+ return datasourceMapper.selectList(queryWrapper).isEmpty();
}
@Override
public IPage<Datasource> selectDatasourcePage(Page<Datasource> page) {
- return datasourceMapper.selectPage(page, new QueryWrapper<Datasource>());
+ return datasourceMapper.selectPage(
+ page, new QueryWrapper<Datasource>().eq("workspace_id", getCurrentWorkspaceId()));
}
@Override
@@ -83,7 +101,10 @@
String pluginName) {
QueryWrapper<Datasource> datasourceQueryWrapper = new QueryWrapper<>();
- datasourceQueryWrapper.in("id", availableDatasourceIds);
+ if (availableDatasourceIds != null) {
+ datasourceQueryWrapper.in("id", availableDatasourceIds);
+ }
+ datasourceQueryWrapper.eq("workspace_id", getCurrentWorkspaceId());
if (searchVal != null
&& !searchVal.isEmpty()
&& pluginName != null
@@ -107,7 +128,12 @@
@Override
public String queryDatasourceNameById(Long id) {
- return datasourceMapper.selectById(id).getDatasourceName();
+ return datasourceMapper
+ .selectOne(
+ new QueryWrapper<Datasource>()
+ .eq("id", id)
+ .eq("workspace_id", getCurrentWorkspaceId()))
+ .getDatasourceName();
}
@Override
@@ -115,28 +141,37 @@
return datasourceMapper.selectList(
new QueryWrapper<Datasource>()
.eq("plugin_name", pluginName)
- .eq("plugin_version", pluginVersion));
+ .eq("plugin_version", pluginVersion)
+ .eq("workspace_id", getCurrentWorkspaceId()));
}
@Override
public List<Datasource> selectDatasourceByIds(List<Long> ids) {
- return datasourceMapper.selectBatchIds(ids);
+ return datasourceMapper.selectList(
+ new QueryWrapper<Datasource>()
+ .in("id", ids)
+ .eq("workspace_id", getCurrentWorkspaceId()));
}
@Override
public List<Datasource> queryAll() {
- return datasourceMapper.selectList(new QueryWrapper<>());
+ return datasourceMapper.selectList(
+ new QueryWrapper<Datasource>().eq("workspace_id", getCurrentWorkspaceId()));
}
@Override
public List<Datasource> selectByIds(List<Long> ids) {
- return datasourceMapper.selectBatchIds(ids);
+ return datasourceMapper.selectList(
+ new QueryWrapper<Datasource>()
+ .in("id", ids)
+ .eq("workspace_id", getCurrentWorkspaceId()));
}
@Override
public List<Datasource> selectDatasourceByUserId(int userId) {
- QueryWrapper<Datasource> queryWrapper = new QueryWrapper<>();
- queryWrapper.eq("create_user_id", userId);
- return datasourceMapper.selectList(queryWrapper);
+ return datasourceMapper.selectList(
+ new QueryWrapper<Datasource>()
+ .eq("create_user_id", userId)
+ .eq("workspace_id", getCurrentWorkspaceId()));
}
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobDefinitionDaoImpl.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobDefinitionDaoImpl.java
index 1563b89..cad87ac 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobDefinitionDaoImpl.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobDefinitionDaoImpl.java
@@ -36,6 +36,8 @@
import java.util.List;
+import static org.apache.seatunnel.app.utils.ServletUtils.getCurrentWorkspaceId;
+
@Repository
public class JobDefinitionDaoImpl implements IJobDefinitionDao {
@@ -43,17 +45,25 @@
@Override
public void add(JobDefinition job) {
+ job.setWorkspaceId(getCurrentWorkspaceId());
jobMapper.insert(job);
}
@Override
public JobDefinition getJob(long id) {
- return jobMapper.selectById(id);
+ return jobMapper.selectOne(
+ Wrappers.<JobDefinition>lambdaQuery()
+ .eq(JobDefinition::getId, id)
+ .eq(JobDefinition::getWorkspaceId, getCurrentWorkspaceId()));
}
@Override
public void updateJob(JobDefinition jobDefinition) {
- jobMapper.updateById(jobDefinition);
+ jobMapper.update(
+ jobDefinition,
+ Wrappers.<JobDefinition>lambdaUpdate()
+ .eq(JobDefinition::getId, jobDefinition.getId())
+ .eq(JobDefinition::getWorkspaceId, getCurrentWorkspaceId()));
}
@Override
@@ -62,11 +72,15 @@
IPage<JobDefinitionRes> jobDefinitionIPage;
if (StringUtils.isEmpty(jobMode)) {
jobDefinitionIPage =
- jobMapper.queryJobListPaging(new Page<>(pageNo, pageSize), searchName);
+ jobMapper.queryJobListPaging(
+ new Page<>(pageNo, pageSize), searchName, getCurrentWorkspaceId());
} else {
jobDefinitionIPage =
jobMapper.queryJobListPagingWithJobMode(
- new Page<>(pageNo, pageSize), searchName, jobMode);
+ new Page<>(pageNo, pageSize),
+ searchName,
+ jobMode,
+ getCurrentWorkspaceId());
}
PageInfo<JobDefinitionRes> jobs = new PageInfo<>();
jobs.setData(jobDefinitionIPage.getRecords());
@@ -78,16 +92,19 @@
@Override
public List<JobDefinition> getJobList(@NonNull String name) {
- return jobMapper.queryJobList(name);
+ return jobMapper.queryJobList(name, getCurrentWorkspaceId());
}
@Override
public JobDefinition getJobByName(@NonNull String name) {
- return jobMapper.queryJob(name);
+ return jobMapper.queryJob(name, getCurrentWorkspaceId());
}
+ @Override
public void delete(long id) {
jobMapper.delete(
- Wrappers.lambdaQuery(new JobDefinition()).and(i -> i.eq(JobDefinition::getId, id)));
+ Wrappers.<JobDefinition>lambdaQuery()
+ .eq(JobDefinition::getId, id)
+ .eq(JobDefinition::getWorkspaceId, getCurrentWorkspaceId()));
}
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobInstanceDaoImpl.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobInstanceDaoImpl.java
index 5ece725..5e9d049 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobInstanceDaoImpl.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobInstanceDaoImpl.java
@@ -21,6 +21,7 @@
import org.apache.seatunnel.app.dal.entity.JobInstance;
import org.apache.seatunnel.app.dal.mapper.JobInstanceMapper;
import org.apache.seatunnel.app.domain.dto.job.SeaTunnelJobInstanceDto;
+import org.apache.seatunnel.app.utils.ServletUtils;
import org.apache.seatunnel.common.constants.JobMode;
import org.springframework.stereotype.Repository;
@@ -31,7 +32,6 @@
import javax.annotation.Resource;
-import java.util.ArrayList;
import java.util.Date;
import java.util.List;
@@ -39,25 +39,35 @@
public class JobInstanceDaoImpl implements IJobInstanceDao {
@Resource private JobInstanceMapper jobInstanceMapper;
+ private Long getWorkspaceId() {
+ return ServletUtils.getCurrentWorkspaceId();
+ }
+
@Override
public JobInstance getJobInstance(@NonNull Long jobInstanceId) {
- return jobInstanceMapper.selectById(jobInstanceId);
+ return jobInstanceMapper.selectOne(
+ new LambdaQueryWrapper<JobInstance>()
+ .eq(JobInstance::getId, jobInstanceId)
+ .eq(JobInstance::getWorkspaceId, getWorkspaceId()));
}
@Override
public JobInstance getJobInstanceByEngineId(@NonNull Long jobEngineId) {
return jobInstanceMapper.selectOne(
- new LambdaQueryWrapper<>(new JobInstance())
- .eq(JobInstance::getJobEngineId, jobEngineId));
+ new LambdaQueryWrapper<JobInstance>()
+ .eq(JobInstance::getJobEngineId, jobEngineId)
+ .eq(JobInstance::getWorkspaceId, getWorkspaceId()));
}
@Override
public void update(@NonNull JobInstance jobInstance) {
+ jobInstance.setWorkspaceId(getWorkspaceId());
jobInstanceMapper.updateById(jobInstance);
}
@Override
public void insert(@NonNull JobInstance jobInstance) {
+ jobInstance.setWorkspaceId(getWorkspaceId());
jobInstanceMapper.insert(jobInstance);
}
@@ -74,27 +84,30 @@
String jobDefineName,
JobMode jobMode) {
return jobInstanceMapper.queryJobInstanceListPaging(
- page, startTime, endTime, jobDefineName, jobMode);
+ page, startTime, endTime, jobDefineName, jobMode, getWorkspaceId());
}
@Override
public List<JobInstance> getAllJobInstance(@NonNull List<Long> jobInstanceIdList) {
- ArrayList<JobInstance> jobInstances = new ArrayList<>();
- for (long jobInstanceId : jobInstanceIdList) {
- JobInstance jobInstance = jobInstanceMapper.selectById(jobInstanceId);
- jobInstances.add(jobInstance);
- }
-
- return jobInstances;
+ return jobInstanceMapper.selectList(
+ new LambdaQueryWrapper<JobInstance>()
+ .in(JobInstance::getId, jobInstanceIdList)
+ .eq(JobInstance::getWorkspaceId, getWorkspaceId()));
}
@Override
public JobInstance getJobExecutionStatus(@NonNull Long jobInstanceId) {
- return jobInstanceMapper.getJobExecutionStatus(jobInstanceId);
+ return jobInstanceMapper.selectOne(
+ new LambdaQueryWrapper<JobInstance>()
+ .eq(JobInstance::getId, jobInstanceId)
+ .eq(JobInstance::getWorkspaceId, getWorkspaceId()));
}
@Override
public void deleteById(@NonNull Long jobInstanceId) {
- jobInstanceMapper.deleteById(jobInstanceId);
+ jobInstanceMapper.delete(
+ new LambdaQueryWrapper<JobInstance>()
+ .eq(JobInstance::getId, jobInstanceId)
+ .eq(JobInstance::getWorkspaceId, getWorkspaceId()));
}
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobInstanceHistoryDaoImpl.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobInstanceHistoryDaoImpl.java
index 1b440e2..5e5f8fd 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobInstanceHistoryDaoImpl.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobInstanceHistoryDaoImpl.java
@@ -27,6 +27,8 @@
import javax.annotation.Resource;
+import static org.apache.seatunnel.app.utils.ServletUtils.getCurrentWorkspaceId;
+
@Repository
public class JobInstanceHistoryDaoImpl implements IJobInstanceHistoryDao {
@@ -36,16 +38,19 @@
public JobInstanceHistory getByInstanceId(Long jobInstanceId) {
return jobInstanceHistoryMapper.selectOne(
Wrappers.lambdaQuery(new JobInstanceHistory())
- .eq(JobInstanceHistory::getId, jobInstanceId));
+ .eq(JobInstanceHistory::getId, jobInstanceId)
+ .eq(JobInstanceHistory::getWorkspaceId, getCurrentWorkspaceId()));
}
@Override
public void insert(JobInstanceHistory jobInstanceHistory) {
+ jobInstanceHistory.setWorkspaceId(getCurrentWorkspaceId());
jobInstanceHistoryMapper.insert(jobInstanceHistory);
}
@Override
public void updateJobInstanceHistory(JobInstanceHistory jobInstanceHistory) {
+ jobInstanceHistory.setWorkspaceId(getCurrentWorkspaceId());
jobInstanceHistoryMapper.updateById(jobInstanceHistory);
}
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobLineDaoImpl.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobLineDaoImpl.java
index 3be8e97..9b39703 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobLineDaoImpl.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobLineDaoImpl.java
@@ -29,6 +29,8 @@
import java.util.List;
+import static org.apache.seatunnel.app.utils.ServletUtils.getCurrentWorkspaceId;
+
@Service
public class JobLineDaoImpl implements IJobLineDao {
@@ -36,17 +38,24 @@
@Override
public void deleteLinesByVersionId(long jobVersionId) {
- jobLineMapper.deleteLinesByVersionId(jobVersionId);
+ jobLineMapper.delete(
+ Wrappers.lambdaQuery(new JobLine())
+ .eq(JobLine::getVersionId, jobVersionId)
+ .eq(JobLine::getWorkspaceId, getCurrentWorkspaceId()));
}
@Override
public void insertLines(List<JobLine> lines) {
+ Long workspaceId = getCurrentWorkspaceId();
+ lines.forEach(line -> line.setWorkspaceId(workspaceId));
jobLineMapper.insertBatchLines(lines);
}
@Override
public List<JobLine> getLinesByVersionId(long jobVersionId) {
return jobLineMapper.selectList(
- Wrappers.lambdaQuery(new JobLine()).eq(JobLine::getVersionId, jobVersionId));
+ Wrappers.lambdaQuery(new JobLine())
+ .eq(JobLine::getVersionId, jobVersionId)
+ .eq(JobLine::getWorkspaceId, getCurrentWorkspaceId()));
}
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobMetricsDaoImpl.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobMetricsDaoImpl.java
index 11cc40e..8f83789 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobMetricsDaoImpl.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobMetricsDaoImpl.java
@@ -28,6 +28,8 @@
import java.util.List;
+import static org.apache.seatunnel.app.utils.ServletUtils.getCurrentWorkspaceId;
+
@Repository
public class JobMetricsDaoImpl implements IJobMetricsDao {
@@ -35,7 +37,7 @@
@Override
public List<JobMetrics> getByInstanceId(@NonNull Long jobInstanceId) {
- return jobMetricsMapper.queryJobMetricsByInstanceId(jobInstanceId);
+ return jobMetricsMapper.queryJobMetricsByInstanceId(jobInstanceId, getCurrentWorkspaceId());
}
@Override
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobTaskDaoImpl.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobTaskDaoImpl.java
index 5ab86f5..028fb7b 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobTaskDaoImpl.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobTaskDaoImpl.java
@@ -29,6 +29,8 @@
import java.util.List;
+import static org.apache.seatunnel.app.utils.ServletUtils.getCurrentWorkspaceId;
+
@Repository
public class JobTaskDaoImpl implements IJobTaskDao {
@@ -37,12 +39,15 @@
@Override
public List<JobTask> getTasksByVersionId(long jobVersionId) {
return jobTaskMapper.selectList(
- Wrappers.lambdaQuery(new JobTask()).eq(JobTask::getVersionId, jobVersionId));
+ Wrappers.lambdaQuery(new JobTask())
+ .eq(JobTask::getVersionId, jobVersionId)
+ .eq(JobTask::getWorkspaceId, getCurrentWorkspaceId()));
}
@Override
public void insertTask(JobTask jobTask) {
if (jobTask != null) {
+ jobTask.setWorkspaceId(getCurrentWorkspaceId());
jobTaskMapper.insert(jobTask);
}
}
@@ -50,6 +55,7 @@
@Override
public void updateTask(JobTask jobTask) {
if (jobTask != null) {
+ jobTask.setWorkspaceId(getCurrentWorkspaceId());
jobTaskMapper.updateById(jobTask);
}
}
@@ -59,24 +65,35 @@
return jobTaskMapper.selectOne(
Wrappers.lambdaQuery(new JobTask())
.eq(JobTask::getVersionId, jobVersionId)
- .and(i -> i.eq(JobTask::getPluginId, pluginId)));
+ .eq(JobTask::getPluginId, pluginId)
+ .eq(JobTask::getWorkspaceId, getCurrentWorkspaceId()));
}
@Override
public List<JobTask> getJobTaskByDataSourceId(long datasourceId) {
return jobTaskMapper.selectList(
- Wrappers.lambdaQuery(new JobTask()).eq(JobTask::getDataSourceId, datasourceId));
+ Wrappers.lambdaQuery(new JobTask())
+ .eq(JobTask::getDataSourceId, datasourceId)
+ .eq(JobTask::getWorkspaceId, getCurrentWorkspaceId()));
}
@Override
public void updateTasks(List<JobTask> jobTasks) {
- jobTasks.forEach(jobTaskMapper::updateById);
+ Long workspaceId = getCurrentWorkspaceId();
+ jobTasks.forEach(
+ jobTask -> {
+ jobTask.setWorkspaceId(workspaceId);
+ jobTaskMapper.updateById(jobTask);
+ });
}
@Override
public void deleteTasks(List<Long> jobTaskIds) {
if (!jobTaskIds.isEmpty()) {
- jobTaskMapper.deleteBatchIds(jobTaskIds);
+ jobTaskMapper.delete(
+ Wrappers.lambdaQuery(new JobTask())
+ .in(JobTask::getId, jobTaskIds)
+ .eq(JobTask::getWorkspaceId, getCurrentWorkspaceId()));
}
}
@@ -85,11 +102,15 @@
jobTaskMapper.delete(
Wrappers.lambdaQuery(new JobTask())
.eq(JobTask::getVersionId, jobVersionId)
- .and(i -> i.eq(JobTask::getPluginId, pluginId)));
+ .eq(JobTask::getPluginId, pluginId)
+ .eq(JobTask::getWorkspaceId, getCurrentWorkspaceId()));
}
@Override
public void deleteTaskByVersionId(long id) {
- jobTaskMapper.delete(Wrappers.lambdaQuery(new JobTask()).eq(JobTask::getVersionId, id));
+ jobTaskMapper.delete(
+ Wrappers.lambdaQuery(new JobTask())
+ .eq(JobTask::getVersionId, id)
+ .eq(JobTask::getWorkspaceId, getCurrentWorkspaceId()));
}
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobVersionDaoImpl.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobVersionDaoImpl.java
index 4c1dc15..bc0c828 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobVersionDaoImpl.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/JobVersionDaoImpl.java
@@ -27,9 +27,9 @@
import javax.annotation.Resource;
-import java.util.HashMap;
import java.util.List;
-import java.util.Map;
+
+import static org.apache.seatunnel.app.utils.ServletUtils.getCurrentWorkspaceId;
@Repository
public class JobVersionDaoImpl implements IJobVersionDao {
@@ -38,35 +38,48 @@
@Override
public void createVersion(JobVersion jobVersion) {
+ jobVersion.setWorkspaceId(getCurrentWorkspaceId());
jobVersionMapper.insert(jobVersion);
}
@Override
public void updateVersion(JobVersion version) {
+ version.setWorkspaceId(getCurrentWorkspaceId());
jobVersionMapper.updateById(version);
}
@Override
public JobVersion getLatestVersion(long jobId) {
- Map<String, Object> queryMap = new HashMap<>();
- queryMap.put("job_id", jobId);
- return jobVersionMapper.selectByMap(queryMap).get(0);
+ return jobVersionMapper.selectOne(
+ new QueryWrapper<JobVersion>()
+ .eq("job_id", jobId)
+ .eq("workspace_id", getCurrentWorkspaceId())
+ .orderByDesc("create_time")
+ .last("LIMIT 1"));
}
@Override
public List<JobVersion> getLatestVersionByJobIds(List<Long> jobIds) {
- QueryWrapper<JobVersion> wrapper = new QueryWrapper<>();
- wrapper.in("job_id", jobIds);
- return jobVersionMapper.selectList(wrapper);
+ return jobVersionMapper.selectList(
+ new QueryWrapper<JobVersion>()
+ .in("job_id", jobIds)
+ .eq("workspace_id", getCurrentWorkspaceId())
+ .orderByDesc("create_time"));
}
@Override
public JobVersion getVersionById(long jobVersionId) {
- return jobVersionMapper.selectById(jobVersionId);
+ return jobVersionMapper.selectOne(
+ new QueryWrapper<JobVersion>()
+ .eq("id", jobVersionId)
+ .eq("workspace_id", getCurrentWorkspaceId()));
}
@Override
public List<JobVersion> getVersionsByIds(List<Long> jobVersionIds) {
- return jobVersionMapper.selectBatchIds(jobVersionIds);
+ return jobVersionMapper.selectList(
+ new QueryWrapper<JobVersion>()
+ .in("id", jobVersionIds)
+ .eq("workspace_id", getCurrentWorkspaceId()));
}
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/UserDaoImpl.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/UserDaoImpl.java
index 3d1afef..9ed4a45 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/UserDaoImpl.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/UserDaoImpl.java
@@ -37,6 +37,7 @@
import java.util.Objects;
import static com.google.common.base.Preconditions.checkState;
+import static org.apache.seatunnel.app.utils.ServletUtils.getCurrentWorkspaceId;
import static org.apache.seatunnel.server.common.SeatunnelErrorEnum.NO_SUCH_USER;
import static org.apache.seatunnel.server.common.SeatunnelErrorEnum.USER_ALREADY_EXISTS;
@@ -125,6 +126,7 @@
log.setToken(dto.getToken());
log.setTokenStatus(dto.getTokenStatus());
log.setUserId(dto.getUserId());
+ log.setWorkspaceId(dto.getWorkspaceId());
userLoginLogMapper.insert(log);
return log.getId();
@@ -132,12 +134,13 @@
@Override
public void disableToken(int userId) {
- userLoginLogMapper.updateStatus(userId, UserTokenStatusEnum.DISABLE.enable());
+ userLoginLogMapper.updateStatus(
+ userId, UserTokenStatusEnum.DISABLE.enable(), getCurrentWorkspaceId());
}
@Override
- public UserLoginLog getLastLoginLog(Integer userId) {
- return userLoginLogMapper.checkLastTokenEnable(userId);
+ public UserLoginLog getLastLoginLog(Integer userId, Long workspaceId) {
+ return userLoginLogMapper.checkLastTokenEnable(userId, workspaceId);
}
@Override
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/VirtualTableDaoImpl.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/VirtualTableDaoImpl.java
index 854d38e..80ba310 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/VirtualTableDaoImpl.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/VirtualTableDaoImpl.java
@@ -37,6 +37,8 @@
import java.util.List;
import java.util.stream.Collectors;
+import static org.apache.seatunnel.app.utils.ServletUtils.getCurrentWorkspaceId;
+
@Repository
@Slf4j
public class VirtualTableDaoImpl implements IVirtualTableDao {
@@ -45,35 +47,46 @@
@Override
public boolean insertVirtualTable(VirtualTable virtualTable) {
+ virtualTable.setWorkspaceId(getCurrentWorkspaceId());
return virtualTableMapper.insert(virtualTable) > 0;
}
@Override
public boolean updateVirtualTable(VirtualTable virtualTable) {
+ virtualTable.setWorkspaceId(getCurrentWorkspaceId());
return virtualTableMapper.updateById(virtualTable) > 0;
}
@Override
public boolean deleteVirtualTable(Long id) {
- return virtualTableMapper.deleteById(id) > 0;
+ return virtualTableMapper.delete(
+ new QueryWrapper<VirtualTable>()
+ .eq("id", id)
+ .eq("workspace_id", getCurrentWorkspaceId()))
+ > 0;
}
@Override
public VirtualTable selectVirtualTableById(Long id) {
- return virtualTableMapper.selectById(id);
+ return virtualTableMapper.selectOne(
+ new QueryWrapper<VirtualTable>()
+ .eq("id", id)
+ .eq("workspace_id", getCurrentWorkspaceId()));
}
@Override
public VirtualTable selectVirtualTableByTableName(String tableName) {
return virtualTableMapper.selectOne(
- new QueryWrapper<VirtualTable>().eq("virtual_table_name", tableName));
+ new QueryWrapper<VirtualTable>()
+ .eq("virtual_table_name", tableName)
+ .eq("workspace_id", getCurrentWorkspaceId()));
}
@Override
public boolean checkVirtualTableNameUnique(
String virtualTableName, String databaseName, Long tableId) {
return virtualTableMapper.checkVirtualTableNameUnique(
- tableId, databaseName, virtualTableName)
+ tableId, databaseName, virtualTableName, getCurrentWorkspaceId())
<= 0;
}
@@ -84,11 +97,17 @@
"======================pluginName:{}, datasourceName:{}",
pluginName,
datasourceName);
- if (StringUtils.isBlank(pluginName) && StringUtils.isBlank(datasourceName)) {
- return virtualTableMapper.selectPage(
- page, new QueryWrapper<VirtualTable>().orderByDesc("create_time"));
+ QueryWrapper<VirtualTable> queryWrapper =
+ new QueryWrapper<VirtualTable>()
+ .eq("workspace_id", getCurrentWorkspaceId())
+ .orderByDesc("create_time");
+ if (StringUtils.isNotBlank(pluginName)) {
+ queryWrapper.eq("plugin_name", pluginName);
}
- return virtualTableMapper.selectVirtualTablePageByParam(page, pluginName, datasourceName);
+ if (StringUtils.isNotBlank(datasourceName)) {
+ queryWrapper.eq("datasource_name", datasourceName);
+ }
+ return virtualTableMapper.selectPage(page, queryWrapper);
}
@Override
@@ -97,18 +116,19 @@
page,
new QueryWrapper<VirtualTable>()
.eq("datasource_id", datasourceId)
+ .eq("workspace_id", getCurrentWorkspaceId())
.orderByDesc("create_time"));
}
@Override
public List<String> getVirtualTableNames(String databaseName, Long datasourceId) {
-
List<VirtualTable> result =
virtualTableMapper.selectList(
new QueryWrapper<VirtualTable>()
.select("virtual_table_name")
.eq("datasource_id", datasourceId)
- .eq("virtual_database_name", databaseName));
+ .eq("virtual_database_name", databaseName)
+ .eq("workspace_id", getCurrentWorkspaceId()));
if (CollectionUtils.isEmpty(result)) {
return new ArrayList<>();
}
@@ -121,7 +141,8 @@
virtualTableMapper.selectList(
new QueryWrapper<VirtualTable>()
.select("virtual_database_name")
- .eq("datasource_id", datasourceId));
+ .eq("datasource_id", datasourceId)
+ .eq("workspace_id", getCurrentWorkspaceId()));
if (CollectionUtils.isEmpty(result)) {
return new ArrayList<>();
}
@@ -133,7 +154,9 @@
@Override
public boolean checkHasVirtualTable(Long datasourceId) {
return virtualTableMapper.selectCount(
- new QueryWrapper<VirtualTable>().eq("datasource_id", datasourceId))
+ new QueryWrapper<VirtualTable>()
+ .eq("datasource_id", datasourceId)
+ .eq("workspace_id", getCurrentWorkspaceId()))
> 0;
}
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/WorkspaceDaoImpl.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/WorkspaceDaoImpl.java
new file mode 100644
index 0000000..26c21da
--- /dev/null
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/dao/impl/WorkspaceDaoImpl.java
@@ -0,0 +1,65 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+
+package org.apache.seatunnel.app.dal.dao.impl;
+
+import org.apache.seatunnel.app.dal.dao.IWorkspaceDao;
+import org.apache.seatunnel.app.dal.entity.Workspace;
+import org.apache.seatunnel.app.dal.mapper.WorkspaceMapper;
+
+import org.springframework.stereotype.Repository;
+
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
+
+import javax.annotation.Resource;
+
+import java.util.List;
+
+@Repository
+public class WorkspaceDaoImpl implements IWorkspaceDao {
+ @Resource private WorkspaceMapper workspaceMapper;
+
+ @Override
+ public void insertWorkspace(Workspace workspace) {
+ workspaceMapper.insert(workspace);
+ }
+
+ @Override
+ public Workspace selectWorkspaceById(Long id) {
+ return workspaceMapper.selectById(id);
+ }
+
+ public Workspace selectWorkspaceByName(String workspaceName) {
+ return workspaceMapper.selectOne(
+ new QueryWrapper<Workspace>().eq("workspace_name", workspaceName));
+ }
+
+ @Override
+ public boolean updateWorkspaceById(Workspace workspace) {
+ return workspaceMapper.updateById(workspace) > 0;
+ }
+
+ @Override
+ public boolean deleteWorkspaceById(Long id) {
+ return workspaceMapper.deleteById(id) > 0;
+ }
+
+ @Override
+ public List<Workspace> selectAllWorkspaces() {
+ return workspaceMapper.selectList(new QueryWrapper<>());
+ }
+}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/Datasource.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/Datasource.java
index 3a526da..1a9fb45 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/Datasource.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/Datasource.java
@@ -64,4 +64,7 @@
@TableField("update_time")
private Date updateTime;
+
+ @TableField("workspace_id")
+ private Long workspaceId;
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobDefinition.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobDefinition.java
index 0809907..73f3521 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobDefinition.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobDefinition.java
@@ -57,4 +57,7 @@
@TableField("update_time")
private Date updateTime;
+
+ @TableField("workspace_id")
+ private Long workspaceId;
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobInstance.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobInstance.java
index 05419a8..cbb4f67 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobInstance.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobInstance.java
@@ -80,4 +80,7 @@
@TableField("error_message")
private String errorMessage;
+
+ @TableField("workspace_id")
+ private Long workspaceId;
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobInstanceHistory.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobInstanceHistory.java
index 761c96a..d5885d4 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobInstanceHistory.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobInstanceHistory.java
@@ -44,4 +44,7 @@
@TableField("update_time")
private Date updateTime;
+
+ @TableField("workspace_id")
+ private Long workspaceId;
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobLine.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobLine.java
index fb6c747..a107f42 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobLine.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobLine.java
@@ -53,4 +53,7 @@
@TableField("update_time")
private Date updateTime;
+
+ @TableField("workspace_id")
+ private Long workspaceId;
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobMetrics.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobMetrics.java
index 6706c59..933479c 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobMetrics.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobMetrics.java
@@ -80,4 +80,7 @@
@TableField("update_time")
private Date updateTime;
+
+ @TableField("workspace_id")
+ private Long workspaceId;
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobTask.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobTask.java
index 417a201..ec8c369 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobTask.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobTask.java
@@ -81,4 +81,7 @@
@TableField("update_time")
private Date updateTime;
+
+ @TableField("workspace_id")
+ private Long workspaceId;
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobVersion.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobVersion.java
index a60629c..3615735 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobVersion.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/JobVersion.java
@@ -69,4 +69,7 @@
@TableField("update_time")
private Date updateTime;
+
+ @TableField("workspace_id")
+ private Long workspaceId;
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/UserLoginLog.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/UserLoginLog.java
index 008d46d..4de1e96 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/UserLoginLog.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/UserLoginLog.java
@@ -34,4 +34,6 @@
private Date createTime;
private Date updateTime;
+
+ private Long workspaceId;
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/VirtualTable.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/VirtualTable.java
index 7afcf72..374c472 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/VirtualTable.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/VirtualTable.java
@@ -67,4 +67,7 @@
@TableField("update_time")
private Date updateTime;
+
+ @TableField("workspace_id")
+ private Long workspaceId;
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/Workspace.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/Workspace.java
new file mode 100644
index 0000000..4099660
--- /dev/null
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/entity/Workspace.java
@@ -0,0 +1,44 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+
+package org.apache.seatunnel.app.dal.entity;
+
+import com.baomidou.mybatisplus.annotation.TableField;
+import lombok.AllArgsConstructor;
+import lombok.Data;
+import lombok.NoArgsConstructor;
+
+import java.util.Date;
+
+@Data
+@AllArgsConstructor
+@NoArgsConstructor
+public class Workspace {
+ private Long id;
+
+ @TableField("workspace_name")
+ private String workspaceName;
+
+ @TableField("description")
+ private String description;
+
+ @TableField("create_time")
+ private Date createTime;
+
+ @TableField("update_time")
+ private Date updateTime;
+}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/JobInstanceMapper.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/JobInstanceMapper.java
index 2977715..fb013a4 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/JobInstanceMapper.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/JobInstanceMapper.java
@@ -37,7 +37,6 @@
@Param("startTime") Date startTime,
@Param("endTime") Date endTime,
@Param("jobDefineName") String jobDefineName,
- @Param("jobMode") JobMode jobMode);
-
- JobInstance getJobExecutionStatus(@Param("jobInstanceId") Long jobInstanceId);
+ @Param("jobMode") JobMode jobMode,
+ @Param("workspaceId") Long workspaceId);
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/JobMapper.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/JobMapper.java
index b84894a..af4c7fa 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/JobMapper.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/JobMapper.java
@@ -30,14 +30,19 @@
public interface JobMapper extends BaseMapper<JobDefinition> {
IPage<JobDefinitionRes> queryJobListPaging(
- IPage<JobDefinition> page, @Param("searchName") String searchName);
+ IPage<JobDefinition> page,
+ @Param("searchName") String searchName,
+ @Param("workspaceId") Long workspaceId);
IPage<JobDefinitionRes> queryJobListPagingWithJobMode(
IPage<JobDefinition> page,
@Param("searchName") String searchName,
- @Param("jobMode") String jobMode);
+ @Param("jobMode") String jobMode,
+ @Param("workspaceId") Long workspaceId);
- List<JobDefinition> queryJobList(@Param("searchName") String searchName);
+ List<JobDefinition> queryJobList(
+ @Param("searchName") String searchName, @Param("workspaceId") Long workspaceId);
- JobDefinition queryJob(@Param("searchName") String searchName);
+ JobDefinition queryJob(
+ @Param("searchName") String searchName, @Param("workspaceId") Long workspaceId);
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/JobMetricsMapper.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/JobMetricsMapper.java
index 1671c93..4b7bc72 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/JobMetricsMapper.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/JobMetricsMapper.java
@@ -25,7 +25,8 @@
import java.util.List;
public interface JobMetricsMapper extends BaseMapper<JobMetrics> {
- List<JobMetrics> queryJobMetricsByInstanceId(@Param("jobInstanceId") Long jobInstanceId);
+ List<JobMetrics> queryJobMetricsByInstanceId(
+ @Param("jobInstanceId") Long jobInstanceId, @Param("workspaceId") Long workspaceId);
void insertBatchMetrics(@Param("jobMetrics") List<JobMetrics> jobMetrics);
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/UserLoginLogMapper.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/UserLoginLogMapper.java
index 1641f3d..6b71984 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/UserLoginLogMapper.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/UserLoginLogMapper.java
@@ -26,7 +26,11 @@
public interface UserLoginLogMapper {
int insert(UserLoginLog userLoginLog);
- int updateStatus(@Param("userId") int userId, @Param("enable") boolean enable);
+ int updateStatus(
+ @Param("userId") int userId,
+ @Param("enable") boolean enable,
+ @Param("workspaceId") long workspaceId);
- UserLoginLog checkLastTokenEnable(@Param("userId") Integer userId);
+ UserLoginLog checkLastTokenEnable(
+ @Param("userId") Integer userId, @Param("workspaceId") long workspaceId);
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/VirtualTableMapper.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/VirtualTableMapper.java
index 5111bc3..bca31b7 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/VirtualTableMapper.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/VirtualTableMapper.java
@@ -22,19 +22,12 @@
import org.apache.ibatis.annotations.Param;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
-import com.baomidou.mybatisplus.core.metadata.IPage;
public interface VirtualTableMapper extends BaseMapper<VirtualTable> {
- IPage<VirtualTable> selectPage(IPage<VirtualTable> page);
-
- IPage<VirtualTable> selectVirtualTablePageByParam(
- IPage<VirtualTable> page,
- @Param("pluginName") String pluginName,
- @Param("datasourceName") String datasourceName);
-
int checkVirtualTableNameUnique(
@Param("tableId") Long tableId,
@Param("virtualDatabaseName") String databaseName,
- @Param("virtualTableName") String virtualTableName);
+ @Param("virtualTableName") String virtualTableName,
+ @Param("datasourceId") Long datasourceId);
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/WorkspaceMapper.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/WorkspaceMapper.java
new file mode 100644
index 0000000..552f166
--- /dev/null
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/dal/mapper/WorkspaceMapper.java
@@ -0,0 +1,32 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+
+package org.apache.seatunnel.app.dal.mapper;
+
+import org.apache.seatunnel.app.dal.entity.Workspace;
+
+import org.apache.ibatis.annotations.Param;
+
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+
+import java.util.List;
+
+public interface WorkspaceMapper extends BaseMapper<Workspace> {
+ List<Workspace> getWorkspaceByName(@Param("workspaceName") String workspaceName);
+
+ List<String> getWorkspaceNames(String searchName);
+}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/domain/dto/user/UserLoginLogDto.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/domain/dto/user/UserLoginLogDto.java
index 55af565..1763af3 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/domain/dto/user/UserLoginLogDto.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/domain/dto/user/UserLoginLogDto.java
@@ -30,4 +30,6 @@
private String token;
private Boolean tokenStatus;
+
+ private Long workspaceId;
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/domain/request/user/UserLoginReq.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/domain/request/user/UserLoginReq.java
index fdf2cd3..6c11b29 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/domain/request/user/UserLoginReq.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/domain/request/user/UserLoginReq.java
@@ -17,10 +17,15 @@
package org.apache.seatunnel.app.domain.request.user;
+import lombok.AllArgsConstructor;
import lombok.Data;
+import lombok.NoArgsConstructor;
@Data
+@NoArgsConstructor
+@AllArgsConstructor
public class UserLoginReq {
private String username;
private String password;
+ private String workspaceName;
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/domain/request/workspace/WorkspaceReq.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/domain/request/workspace/WorkspaceReq.java
new file mode 100644
index 0000000..334f016
--- /dev/null
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/domain/request/workspace/WorkspaceReq.java
@@ -0,0 +1,38 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+
+package org.apache.seatunnel.app.domain.request.workspace;
+
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.AllArgsConstructor;
+import lombok.Data;
+import lombok.NoArgsConstructor;
+
+import javax.validation.constraints.NotNull;
+
+@ApiModel(value = "WorkspaceReq", description = "workspace create request")
+@Data
+@AllArgsConstructor
+@NoArgsConstructor
+public class WorkspaceReq {
+ @ApiModelProperty(value = "workspace name", required = true, dataType = "String")
+ @NotNull private String workspaceName;
+
+ @ApiModelProperty(value = "workspace description", dataType = "String")
+ private String description;
+}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/interceptor/AuthenticationInterceptor.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/interceptor/AuthenticationInterceptor.java
index d542293..07ccf56 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/interceptor/AuthenticationInterceptor.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/interceptor/AuthenticationInterceptor.java
@@ -22,6 +22,7 @@
import org.apache.seatunnel.app.dal.entity.User;
import org.apache.seatunnel.app.dal.entity.UserLoginLog;
import org.apache.seatunnel.app.security.JwtUtils;
+import org.apache.seatunnel.app.security.UserContext;
import org.apache.commons.lang3.StringUtils;
@@ -78,7 +79,8 @@
response.setStatus(HttpStatus.UNAUTHORIZED_401);
return false;
}
- final UserLoginLog userLoginLog = userDaoImpl.getLastLoginLog(userId);
+ long workspaceIdFromToken = ((Number) map.get("workspaceId")).longValue();
+ final UserLoginLog userLoginLog = userDaoImpl.getLastLoginLog(userId, workspaceIdFromToken);
if (Objects.isNull(userLoginLog) || !userLoginLog.getTokenStatus()) {
log.info("userLoginLog does not exist");
response.setStatus(HttpStatus.UNAUTHORIZED_401);
@@ -100,7 +102,13 @@
"Setting user to request attributes: userId={}, username={}",
user.getId(),
user.getUsername());
- request.setAttribute(Constants.SESSION_USER, user);
+
+ UserContext userContext = new UserContext();
+ userContext.setUser(user);
+ userContext.setWorkspaceId(workspaceIdFromToken);
+ userContext.setWorkspaceName((String) map.get("workspaceName"));
+ request.setAttribute(Constants.SESSION_USER_CONTEXT, userContext);
+
request.setAttribute("userId", userId);
return true;
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/interceptor/UserContextInterceptor.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/interceptor/UserContextInterceptor.java
index e8477cc..be42dbb 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/interceptor/UserContextInterceptor.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/interceptor/UserContextInterceptor.java
@@ -16,8 +16,8 @@
*/
package org.apache.seatunnel.app.interceptor;
-import org.apache.seatunnel.app.dal.entity.User;
import org.apache.seatunnel.app.security.UserContext;
+import org.apache.seatunnel.app.security.UserContextHolder;
import org.springframework.web.servlet.HandlerInterceptor;
@@ -26,7 +26,7 @@
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
-import static org.apache.seatunnel.app.common.Constants.SESSION_USER;
+import static org.apache.seatunnel.app.common.Constants.SESSION_USER_CONTEXT;
/**
* Interceptor for managing user context in web requests. This interceptor sets up and cleans up the
@@ -48,12 +48,12 @@
@Override
public boolean preHandle(
HttpServletRequest request, HttpServletResponse response, Object handler) {
- User user = (User) request.getAttribute(SESSION_USER);
- if (user != null) {
- log.debug("Setting user context for user: {}", user.getUsername());
- UserContext.setUser(user);
+ UserContext userContext = (UserContext) request.getAttribute(SESSION_USER_CONTEXT);
+ if (userContext != null) {
+ log.debug("Setting user context for user: {}", userContext.getUser().getUsername());
+ UserContextHolder.setUserContext(userContext);
} else {
- log.warn("No user found in request attributes");
+ log.warn("No user context found in request attributes");
}
return true;
}
@@ -74,6 +74,6 @@
Object handler,
Exception ex) {
log.debug("Clearing user context");
- UserContext.clear();
+ UserContextHolder.clear();
}
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/security/UserContext.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/security/UserContext.java
index 7e42fab..8897779 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/security/UserContext.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/security/UserContext.java
@@ -18,22 +18,15 @@
import org.apache.seatunnel.app.dal.entity.User;
+import lombok.AllArgsConstructor;
+import lombok.Data;
+import lombok.NoArgsConstructor;
+
+@Data
+@AllArgsConstructor
+@NoArgsConstructor
public class UserContext {
- private static final ThreadLocal<User> userHolder = new ThreadLocal<>();
-
- public static void setUser(User user) {
- userHolder.set(user);
- }
-
- public static User getUser() {
- User user = userHolder.get();
- if (user == null) {
- throw new RuntimeException("User context not found");
- }
- return user;
- }
-
- public static void clear() {
- userHolder.remove();
- }
+ User user;
+ Long workspaceId;
+ String workspaceName;
}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/security/UserContextHolder.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/security/UserContextHolder.java
new file mode 100644
index 0000000..bd6eb5c
--- /dev/null
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/security/UserContextHolder.java
@@ -0,0 +1,44 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.seatunnel.app.security;
+
+import org.apache.seatunnel.app.dal.entity.User;
+
+public class UserContextHolder {
+ private static final ThreadLocal<UserContext> userContextHolder = new ThreadLocal<>();
+
+ public static void setUserContext(UserContext userContext) {
+ userContextHolder.set(userContext);
+ }
+
+ public static User getUser() {
+ UserContext userContext = getUserContext();
+ return userContext.getUser();
+ }
+
+ public static UserContext getUserContext() {
+ UserContext userContext = userContextHolder.get();
+ if (userContext == null) {
+ throw new RuntimeException("User context not found");
+ }
+ return userContext;
+ }
+
+ public static void clear() {
+ userContextHolder.remove();
+ }
+}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/service/WorkspaceService.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/service/WorkspaceService.java
new file mode 100644
index 0000000..7b413f1
--- /dev/null
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/service/WorkspaceService.java
@@ -0,0 +1,43 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+
+package org.apache.seatunnel.app.service;
+
+import org.apache.seatunnel.app.dal.entity.Workspace;
+import org.apache.seatunnel.app.domain.request.workspace.WorkspaceReq;
+
+import java.util.List;
+
+public interface WorkspaceService {
+ Long createWorkspace(WorkspaceReq workspaceCreateReq);
+
+ Workspace getWorkspace(String workspaceName);
+
+ Workspace getWorkspace(Long id);
+
+ boolean updateWorkspace(Long id, WorkspaceReq workspaceReq);
+
+ boolean deleteWorkspace(Long id);
+
+ List<Workspace> getAllWorkspaces();
+
+ Workspace getDefaultWorkspace();
+
+ Long getWorkspaceIdOrDefault(Long workspaceId);
+
+ Long getWorkspaceIdOrCurrent(String workspaceName);
+}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/service/impl/DatasourceServiceImpl.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/service/impl/DatasourceServiceImpl.java
index ce9cbc6..2a0d790 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/service/impl/DatasourceServiceImpl.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/service/impl/DatasourceServiceImpl.java
@@ -131,6 +131,7 @@
.datasourceConfig(datasourceConfigStr)
.createTime(new Date())
.updateTime(new Date())
+ .workspaceId(ServletUtils.getCurrentWorkspaceId())
.build();
boolean success = datasourceDao.insertDatasource(datasource);
if (success) {
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/service/impl/JobMetricsServiceImpl.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/service/impl/JobMetricsServiceImpl.java
index ade203b..0d9bad0 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/service/impl/JobMetricsServiceImpl.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/service/impl/JobMetricsServiceImpl.java
@@ -547,6 +547,7 @@
metrics.setJobInstanceId(jobInstance.getId());
metrics.setCreateUserId(userId);
metrics.setUpdateUserId(userId);
+ metrics.setWorkspaceId(jobInstance.getWorkspaceId());
});
if (!jobMetricsFromEngine.isEmpty()) {
@@ -674,6 +675,7 @@
jobMetrics.setJobInstanceId(jobInstance.getId());
jobMetrics.setCreateUserId(userId);
jobMetrics.setUpdateUserId(userId);
+ jobMetrics.setWorkspaceId(ServletUtils.getCurrentWorkspaceId());
list.add(jobMetrics);
}
if (!list.isEmpty()) {
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/service/impl/JobServiceImpl.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/service/impl/JobServiceImpl.java
index e99ff4d..8a2620f 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/service/impl/JobServiceImpl.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/service/impl/JobServiceImpl.java
@@ -52,7 +52,7 @@
import java.util.stream.Stream;
@Service
-public class JobServiceImpl implements IJobService {
+public class JobServiceImpl extends SeatunnelBaseServiceImpl implements IJobService {
@Resource private IJobDefinitionService jobService;
@Resource private IJobTaskService jobTaskService;
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/service/impl/UserServiceImpl.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/service/impl/UserServiceImpl.java
index fb39373..138ab4b 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/service/impl/UserServiceImpl.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/service/impl/UserServiceImpl.java
@@ -22,6 +22,7 @@
import org.apache.seatunnel.app.config.SeatunnelAuthenticationProvidersConfig;
import org.apache.seatunnel.app.dal.dao.IUserDao;
import org.apache.seatunnel.app.dal.entity.User;
+import org.apache.seatunnel.app.dal.entity.Workspace;
import org.apache.seatunnel.app.domain.dto.user.ListUserDto;
import org.apache.seatunnel.app.domain.dto.user.UpdateUserDto;
import org.apache.seatunnel.app.domain.dto.user.UserLoginLogDto;
@@ -38,6 +39,7 @@
import org.apache.seatunnel.app.security.authentication.strategy.impl.LDAPAuthenticationStrategy;
import org.apache.seatunnel.app.service.IRoleService;
import org.apache.seatunnel.app.service.IUserService;
+import org.apache.seatunnel.app.service.WorkspaceService;
import org.apache.seatunnel.app.utils.PasswordUtils;
import org.apache.seatunnel.app.utils.ServletUtils;
import org.apache.seatunnel.server.common.PageData;
@@ -60,11 +62,13 @@
import java.util.stream.Collectors;
@Component
-public class UserServiceImpl implements IUserService {
+public class UserServiceImpl extends SeatunnelBaseServiceImpl implements IUserService {
@Resource private IUserDao userDaoImpl;
@Resource private IRoleService roleServiceImpl;
+ @Resource private WorkspaceService workspaceService;
+
@Resource private JwtUtils jwtUtils;
@Value("${user.default.passwordSalt:seatunnel}")
@@ -184,7 +188,19 @@
IAuthenticationStrategy strategy = strategies.get(authType);
User user = strategy.authenticate(req);
UserSimpleInfoRes translate = translate(user);
- final String token = jwtUtils.genToken(translate.toMap());
+ Workspace workspace;
+ if (StringUtils.isNotEmpty(req.getWorkspaceName())
+ && !req.getWorkspaceName().equals("default")) {
+ workspace = workspaceService.getWorkspace(req.getWorkspaceName());
+ } else {
+ // get user default workspace
+ workspace = workspaceService.getDefaultWorkspace();
+ }
+
+ Map<String, Object> map = translate.toMap();
+ map.put("workspaceName", workspace.getWorkspaceName());
+ map.put("workspaceId", workspace.getId());
+ final String token = jwtUtils.genToken(map);
translate.setToken(token);
final UserLoginLogDto logDto =
@@ -192,6 +208,7 @@
.token(token)
.tokenStatus(UserTokenStatusEnum.ENABLE.enable())
.userId(user.getId())
+ .workspaceId(workspace.getId())
.build();
userDaoImpl.insertLoginLog(logDto);
return translate;
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/service/impl/WorkspaceServiceImpl.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/service/impl/WorkspaceServiceImpl.java
new file mode 100644
index 0000000..2700c7d
--- /dev/null
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/service/impl/WorkspaceServiceImpl.java
@@ -0,0 +1,157 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+
+package org.apache.seatunnel.app.service.impl;
+
+import org.apache.seatunnel.app.dal.dao.IWorkspaceDao;
+import org.apache.seatunnel.app.dal.entity.Workspace;
+import org.apache.seatunnel.app.domain.request.workspace.WorkspaceReq;
+import org.apache.seatunnel.app.service.WorkspaceService;
+import org.apache.seatunnel.app.utils.ServletUtils;
+import org.apache.seatunnel.server.common.CodeGenerateUtils;
+import org.apache.seatunnel.server.common.ParamValidationException;
+import org.apache.seatunnel.server.common.SeatunnelErrorEnum;
+import org.apache.seatunnel.server.common.SeatunnelException;
+
+import org.apache.commons.lang3.StringUtils;
+
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+
+import java.util.Date;
+import java.util.List;
+
+@Service
+public class WorkspaceServiceImpl extends SeatunnelBaseServiceImpl implements WorkspaceService {
+ @Autowired private IWorkspaceDao workspaceDao;
+
+ @Override
+ public Long createWorkspace(WorkspaceReq workspaceReq) {
+ validateWorkspaceParam(workspaceReq);
+ Workspace workspaceByName =
+ workspaceDao.selectWorkspaceByName(workspaceReq.getWorkspaceName());
+ if (workspaceByName != null) {
+ throw new SeatunnelException(
+ SeatunnelErrorEnum.RESOURCE_ALREADY_EXISTS,
+ "Workspace with name " + workspaceReq.getWorkspaceName() + " already exists.");
+ }
+ Workspace workspace = new Workspace();
+ long id = CodeGenerateUtils.getInstance().genCode();
+ workspace.setId(id);
+ workspace.setWorkspaceName(workspaceReq.getWorkspaceName());
+ workspace.setDescription(workspaceReq.getDescription());
+ workspaceDao.insertWorkspace(workspace);
+ return id;
+ }
+
+ private void validateWorkspaceParam(WorkspaceReq workspaceReq) {
+ if (StringUtils.isEmpty(workspaceReq.getWorkspaceName())) {
+ throw new ParamValidationException(
+ SeatunnelErrorEnum.PARAM_CAN_NOT_BE_NULL, "workspace");
+ }
+ }
+
+ @Override
+ public Workspace getWorkspace(Long id) {
+ Workspace workspace = workspaceDao.selectWorkspaceById(id);
+ if (null == workspace) {
+ throw new SeatunnelException(
+ SeatunnelErrorEnum.RESOURCE_NOT_FOUND,
+ "Workspace with id " + id + " not found.");
+ }
+ return workspace;
+ }
+
+ @Override
+ public Workspace getWorkspace(String workspaceName) {
+ Workspace workspace = workspaceDao.selectWorkspaceByName(workspaceName);
+ if (null == workspace) {
+ throw new SeatunnelException(
+ SeatunnelErrorEnum.RESOURCE_NOT_FOUND,
+ "Workspace with name " + workspaceName + " not found.");
+ }
+ return workspace;
+ }
+
+ @Override
+ public boolean updateWorkspace(Long id, WorkspaceReq workspaceReq) {
+ Workspace workspace = workspaceDao.selectWorkspaceById(id);
+ if (workspace == null) {
+ throw new SeatunnelException(
+ SeatunnelErrorEnum.RESOURCE_NOT_FOUND,
+ "Workspace with id " + id + " not found.");
+ }
+ validateWorkspaceParam(workspaceReq);
+
+ // Check if the workspace name is being changed and if it already exists in the database
+ if (!workspace.getWorkspaceName().equals(workspaceReq.getWorkspaceName())
+ && workspaceDao.selectWorkspaceByName(workspaceReq.getWorkspaceName()) != null) {
+ throw new SeatunnelException(
+ SeatunnelErrorEnum.RESOURCE_ALREADY_EXISTS,
+ "Workspace with name " + workspaceReq.getWorkspaceName() + " already exists.");
+ }
+
+ workspace.setWorkspaceName(workspaceReq.getWorkspaceName());
+ workspace.setDescription(workspaceReq.getDescription());
+ workspace.setUpdateTime(new Date());
+ return workspaceDao.updateWorkspaceById(workspace);
+ }
+
+ @Override
+ public boolean deleteWorkspace(Long id) {
+ Workspace workspace = workspaceDao.selectWorkspaceById(id);
+ if (null != workspace) {
+ return workspaceDao.deleteWorkspaceById(id);
+ }
+ return false;
+ }
+
+ @Override
+ public List<Workspace> getAllWorkspaces() {
+ return workspaceDao.selectAllWorkspaces();
+ }
+
+ @Override
+ public Workspace getDefaultWorkspace() {
+ return getWorkspace("default");
+ }
+
+ @Override
+ public Long getWorkspaceIdOrDefault(Long workspaceId) {
+ if (workspaceId == null || workspaceId == 0 || workspaceId == 1) {
+ return getDefaultWorkspace().getId();
+ } else {
+ // Check if the workspace exists
+ Workspace workspaceById = getWorkspace(workspaceId);
+ if (workspaceById == null) {
+ throw new SeatunnelException(
+ SeatunnelErrorEnum.RESOURCE_NOT_FOUND,
+ "Workspace with id " + workspaceId + " not found.");
+ }
+ return workspaceById.getId();
+ }
+ }
+
+ public Long getWorkspaceIdOrCurrent(String workspaceName) {
+ if (StringUtils.isEmpty(workspaceName)) {
+ // get names from current workspace
+ return ServletUtils.getCurrentWorkspaceId();
+ } else {
+ return getWorkspace(workspaceName).getId();
+ }
+ }
+}
diff --git a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/utils/ServletUtils.java b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/utils/ServletUtils.java
index 5fe0b7a..d696353 100644
--- a/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/utils/ServletUtils.java
+++ b/seatunnel-server/seatunnel-app/src/main/java/org/apache/seatunnel/app/utils/ServletUtils.java
@@ -18,15 +18,19 @@
package org.apache.seatunnel.app.utils;
import org.apache.seatunnel.app.dal.entity.User;
-import org.apache.seatunnel.app.security.UserContext;
+import org.apache.seatunnel.app.security.UserContextHolder;
public class ServletUtils {
public static User getCurrentUser() {
- return UserContext.getUser();
+ return UserContextHolder.getUser();
}
public static Integer getCurrentUserId() {
return getCurrentUser().getId();
}
+
+ public static Long getCurrentWorkspaceId() {
+ return UserContextHolder.getUserContext().getWorkspaceId();
+ }
}
diff --git a/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/JobInstanceMapper.xml b/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/JobInstanceMapper.xml
index 9e4d661..0978573 100644
--- a/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/JobInstanceMapper.xml
+++ b/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/JobInstanceMapper.xml
@@ -25,10 +25,11 @@
<result column="engine_version" jdbcType="VARCHAR" property="engineVersion"/>
<result column="job_engine_id" jdbcType="VARCHAR" property="jobEngineId"/>
<result column="error_message" jdbcType="VARCHAR" property="errorMessage"/>
+ <result column="workspace_id" jdbcType="BIGINT" property="workspaceId"/>
</resultMap>
<sql id="Base_Column_List">
id
- , `job_define_id`, `job_status`, `job_config`, `engine_name`, `engine_version`, `job_engine_id`,`error_message`
+ , `job_define_id`, `job_status`, `job_config`, `engine_name`, `engine_version`, `job_engine_id`,`error_message`, `workspace_id`
</sql>
<select id="queryJobInstanceListPaging" resultType="org.apache.seatunnel.app.domain.dto.job.SeaTunnelJobInstanceDto">
@@ -37,6 +38,7 @@
LEFT JOIN t_st_job_definition jd ON ji.job_define_id = jd.id
LEFT JOIN `user` cu ON ji.create_user_id = cu.id
<where>
+ ji.workspace_id = #{workspaceId}
<if test="startTime != null">
AND ji.create_time <![CDATA[ >=]]> #{startTime}
</if>
@@ -55,9 +57,4 @@
</where>
ORDER BY ji.create_time DESC
</select>
- <select id="getJobExecutionStatus" resultType="org.apache.seatunnel.app.dal.entity.JobInstance">
- SELECT `job_status`, `error_message`
- FROM t_st_job_instance t
- WHERE t.id = #{jobInstanceId}
- </select>
</mapper>
diff --git a/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/JobLineMapper.xml b/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/JobLineMapper.xml
index d6e99a5..a921aba 100644
--- a/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/JobLineMapper.xml
+++ b/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/JobLineMapper.xml
@@ -24,19 +24,17 @@
<result column="target_plugin_id" jdbcType="BIGINT" property="targetPluginId"/>
<result column="create_time" jdbcType="TIMESTAMP" property="createTime"/>
<result column="update_time" jdbcType="TIMESTAMP" property="updateTime"/>
+ <result column="workspace_id" jdbcType="BIGINT" property="workspaceId"/>
</resultMap>
- <delete id="deleteLinesByVersionId">
- delete from t_st_job_line where version_id = #{versionId}
- </delete>
-
<insert id="insertBatchLines">
- insert into t_st_job_line (id, version_id, input_plugin_id, target_plugin_id)
+ insert into t_st_job_line (id, version_id, input_plugin_id, target_plugin_id, workspace_id)
values
<foreach collection="lines" item="line" separator=",">
(#{line.id},
#{line.versionId},
#{line.inputPluginId},
- #{line.targetPluginId})
+ #{line.targetPluginId},
+ #{line.workspaceId})
</foreach>
</insert>
</mapper>
diff --git a/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/JobMapper.xml b/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/JobMapper.xml
index a8a2b06..3bd8ac9 100644
--- a/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/JobMapper.xml
+++ b/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/JobMapper.xml
@@ -24,18 +24,19 @@
<result column="update_user_id" jdbcType="INTEGER" property="updateUserId"/>
<result column="create_time" jdbcType="TIMESTAMP" property="createTime"/>
<result column="update_time" jdbcType="TIMESTAMP" property="updateTime"/>
+ <result column="workspace_id" jdbcType="BIGINT" property="workspaceId"/>
</resultMap>
<sql id="Base_Column_List">
- id, `name`, `description`,`job_type`, create_user_id, update_user_id
+ id, `name`, `description`,`job_type`, create_user_id, update_user_id, workspace_id
</sql>
<sql id="Query_Job_Column_List">
- t.id, t.`name`, t.`description`, t.`job_type`, t.create_user_id, t.update_user_id, t.create_time, t.update_time
+ t.id, t.`name`, t.`description`, t.`job_type`, t.create_user_id, t.update_user_id, t.create_time, t.update_time, t.workspace_id
</sql>
<insert id="insert" parameterType="org.apache.seatunnel.app.dal.entity.JobDefinition">
insert into `t_st_job_definition` (<include refid="Base_Column_List"/>)
values (#{id,jdbcType=BIGINT}, #{name,jdbcType=VARCHAR},
#{description,jdbcType=VARCHAR},#{jobType,jdbcType=VARCHAR},
- #{createUserId,jdbcType=BIGINT}, #{updateUserId,jdbcType=BIGINT})
+ #{createUserId,jdbcType=BIGINT}, #{updateUserId,jdbcType=BIGINT}, #{workspaceId,jdbcType=BIGINT})
</insert>
<select id="queryJobListPaging" resultType="org.apache.seatunnel.app.domain.response.job.JobDefinitionRes">
select
@@ -44,9 +45,10 @@
uu.username as update_username
from
t_st_job_definition t
- left join user cu on t.create_user_id = cu.id
- left join user uu on t.update_user_id = uu.id
+ left join `user` cu on t.create_user_id = cu.id
+ left join `user` uu on t.update_user_id = uu.id
<where>
+ t.workspace_id = #{workspaceId}
<if test="searchName!=null and searchName!= ''">
and t.name LIKE concat('%', #{searchName}, '%')
</if>
@@ -63,9 +65,10 @@
from
t_st_job_definition t
join (select * from t_st_job_version where job_mode = #{jobMode}) v on t.id = v.job_id
- left join user cu on t.create_user_id = cu.id
- left join user uu on t.update_user_id = uu.id
+ left join `user` cu on t.create_user_id = cu.id
+ left join `user` uu on t.update_user_id = uu.id
<where>
+ t.workspace_id = #{workspaceId}
<if test="searchName!=null and searchName != ''">
and t.name LIKE concat('%', #{searchName}, '%')
</if>
@@ -79,6 +82,7 @@
<include refid="Base_Column_List"/>, create_time, update_time
from t_st_job_definition
<where>
+ workspace_id = #{workspaceId}
<if test="searchName!=null and searchName != ''">
and name LIKE concat('%', #{searchName}, '%')
</if>
@@ -91,6 +95,7 @@
<include refid="Base_Column_List"/>, create_time, update_time
from t_st_job_definition
<where>
+ workspace_id = #{workspaceId}
<if test="searchName!=null and searchName != ''">
and name LIKE concat('%', #{searchName}, '%')
</if>
diff --git a/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/JobMetricsMapper.xml b/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/JobMetricsMapper.xml
index 7fdf024..94aaa4b 100644
--- a/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/JobMetricsMapper.xml
+++ b/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/JobMetricsMapper.xml
@@ -27,10 +27,11 @@
<result column="read_qps" jdbcType="BIGINT" property="readQps"/>
<result column="write_qps" jdbcType="BIGINT" property="writeQps"/>
<result column="status" jdbcType="VARCHAR" property="status"/>
+ <result column="workspace_id" jdbcType="BIGINT" property="workspaceId"/>
</resultMap>
<sql id="Base_Column_List">
id
- , `job_instance_id`, `pipeline_id`, read_row_count, write_row_count, source_table_names, sink_table_names, read_qps, write_qps, status
+ , `job_instance_id`, `pipeline_id`, read_row_count, write_row_count, source_table_names, sink_table_names, read_qps, write_qps, status, workspace_id
</sql>
<insert id="insert" parameterType="org.apache.seatunnel.app.dal.entity.JobMetrics">
insert into `t_st_job_metrics` (<include refid="Base_Column_List"/>, `create_user_id`, `update_user_id`)
@@ -44,6 +45,7 @@
#{read_qps,jdbcType=BIGINT},
#{write_qps,jdbcType=BIGINT},
#{status,jdbcType=VARCHAR},
+ #{workspaceId,jdbcType=BIGINT},
#{createUserId,jdbcType=BIGINT},
#{updateUserId,jdbcType=BIGINT})
</insert>
@@ -52,7 +54,7 @@
select
<include refid="Base_Column_List"/>
from t_st_job_metrics
- where 1=1
+ where workspace_id = #{workspaceId}
<if test="jobInstanceId != null and jobInstanceId > 0">
and job_instance_id = #{jobInstanceId}
</if>
@@ -72,6 +74,7 @@
#{metrics.readQps},
#{metrics.writeQps},
#{metrics.status},
+ #{metrics.workspaceId},
#{metrics.createUserId},
#{metrics.updateUserId})
</foreach>
diff --git a/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/UserLoginLogMapper.xml b/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/UserLoginLogMapper.xml
index f8f9444..e932035 100644
--- a/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/UserLoginLogMapper.xml
+++ b/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/UserLoginLogMapper.xml
@@ -25,6 +25,7 @@
<result property="tokenStatus" column="token_status" jdbcType="BOOLEAN"/>
<result property="createTime" column="create_time" jdbcType="TIMESTAMP"/>
<result property="updateTime" column="update_time" jdbcType="TIMESTAMP"/>
+ <result property="workspaceId" column="workspace_id" jdbcType="BIGINT" />
</resultMap>
<sql id="Base_Column_List">
@@ -33,25 +34,26 @@
token,
token_status,
create_time,
- update_time
+ update_time,
+ workspace_id
</sql>
<insert id="insert" keyColumn="id" keyProperty="id" parameterType="org.apache.seatunnel.app.dal.entity.UserLoginLog"
useGeneratedKeys="true">
- insert into `user_login_log` (user_id, token, `token_status`)
- VALUES (#{userId,jdbcType=INTEGER}, #{token,jdbcType=VARCHAR}, #{tokenStatus,jdbcType=BOOLEAN})
+ insert into `user_login_log` (user_id, token, `token_status`, `workspace_id`)
+ VALUES (#{userId,jdbcType=INTEGER}, #{token,jdbcType=VARCHAR}, #{tokenStatus,jdbcType=BOOLEAN}, #{workspaceId,jdbcType=BIGINT})
</insert>
<update id="updateStatus">
update user_login_log
set token_status = #{enable,jdbcType=BOOLEAN}
- where user_id = #{userId,jdbcType=INTEGER} and token_status != #{enable}
+ where workspace_id = #{workspaceId} and user_id = #{userId,jdbcType=INTEGER} and token_status != #{enable}
</update>
<select id="checkLastTokenEnable" resultMap="BaseResultMap">
select
<include refid="Base_Column_List"/>
from user_login_log
- where user_id = #{userId,jdbcType=INTEGER}
+ where workspace_id = #{workspaceId} and user_id = #{userId,jdbcType=INTEGER}
order by id desc
limit 1
</select>
diff --git a/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/VirtualTableMapper.xml b/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/VirtualTableMapper.xml
index 29baa8b..201feb1 100644
--- a/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/VirtualTableMapper.xml
+++ b/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/VirtualTableMapper.xml
@@ -26,36 +26,19 @@
<result column="update_user_id" jdbcType="INTEGER" property="updateUserId"/>
<result column="create_time" jdbcType="TIMESTAMP" property="createTime"/>
<result column="update_time" jdbcType="TIMESTAMP" property="updateTime"/>
+ <result column="workspace_id" jdbcType="BIGINT" property="workspaceId"/>
</resultMap>
<sql id="Base_Column_List">
id
- , datasource_id, virtual_database_name, virtual_table_name, table_fields, description, create_user_id, update_user_id, create_time, update_time
+ , datasource_id, virtual_database_name, virtual_table_name, table_fields, description, create_user_id, update_user_id, create_time, update_time, workspace_id
</sql>
<select id="checkVirtualTableNameUnique" resultType="java.lang.Integer">
SELECT COUNT(1)
FROM t_st_virtual_table
- WHERE id != #{tableId}
+ WHERE workspace_id = #{workspaceId} AND id != #{tableId}
AND virtual_database_name = #{virtualDatabaseName}
AND virtual_table_name = #{virtualTableName}
</select>
-
- <select id="selectVirtualTablePageByParam" resultType="org.apache.seatunnel.app.dal.entity.VirtualTable">
- SELECT
- a.id
- , a.datasource_id, a.virtual_database_name, a.virtual_table_name, a.table_fields, a.description, a.create_user_id, a.update_user_id, a.create_time, a.update_time
- FROM t_st_virtual_table a JOIN t_st_datasource b on a.datasource_id = b.id
- where
- a.datasource_id = b.id
- <if test="pluginName != null and pluginName != '' ">
- AND b.plugin_name = #{pluginName}
- </if>
- <if test="datasourceName != null and datasourceName != '' ">
- AND b.datasource_name like concat('%', #{datasourceName}, '%')
- </if>
- ORDER BY create_time DESC
- </select>
-
-
</mapper>
diff --git a/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/WorkspaceMapper.xml b/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/WorkspaceMapper.xml
new file mode 100644
index 0000000..6535652
--- /dev/null
+++ b/seatunnel-server/seatunnel-app/src/main/resources/org/apache/seatunnel/app/dal/mapper/WorkspaceMapper.xml
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+ Licensed to the Apache Software Foundation (ASF) under one or more
+ contributor license agreements. See the NOTICE file distributed with
+ this work for additional information regarding copyright ownership.
+ The ASF licenses this file to You under the Apache License, Version 2.0
+ (the "License"); you may not use this file except in compliance with
+ the License. You may obtain a copy of the License at
+ http://www.apache.org/licenses/LICENSE-2.0
+ 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.
+-->
+<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="org.apache.seatunnel.app.dal.mapper.WorkspaceMapper">
+ <select id="getWorkspaceByName" resultType="org.apache.seatunnel.app.dal.entity.Workspace">
+ select id, workspace_name, description, create_time, update_time
+ from workspace
+ where workspace_name = #{workspaceName}
+ order by update_time desc
+ </select>
+ <select id="getWorkspaceNames" resultType="java.lang.String">
+ select workspace_name
+ from workspace
+ where #{searchName} IS NULL OR workspace_name LIKE concat('%', #{searchName}, '%')
+ order by update_time desc
+ </select>
+</mapper>
diff --git a/seatunnel-server/seatunnel-app/src/main/resources/script/seatunnel_server_h2.sql b/seatunnel-server/seatunnel-app/src/main/resources/script/seatunnel_server_h2.sql
index b4231ce..f02bb23 100644
--- a/seatunnel-server/seatunnel-app/src/main/resources/script/seatunnel_server_h2.sql
+++ b/seatunnel-server/seatunnel-app/src/main/resources/script/seatunnel_server_h2.sql
@@ -70,8 +70,9 @@
update_user_id INT NOT NULL,
create_time TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
update_time TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
+ workspace_id BIGINT NOT NULL,
PRIMARY KEY (id),
- UNIQUE (datasource_name)
+ UNIQUE (datasource_name, workspace_id)
);
-- Table structure for t_st_job_definition
@@ -85,8 +86,9 @@
update_user_id INT NOT NULL,
create_time TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
update_time TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
+ workspace_id BIGINT NOT NULL,
PRIMARY KEY (id),
- UNIQUE (name)
+ UNIQUE (name, workspace_id)
);
-- Table structure for t_st_job_instance
@@ -106,6 +108,7 @@
end_time TIMESTAMP(3) DEFAULT NULL,
job_type VARCHAR(50) NOT NULL,
error_message VARCHAR(4096) DEFAULT NULL,
+ workspace_id BIGINT NOT NULL,
PRIMARY KEY (id)
);
@@ -116,6 +119,7 @@
dag CLOB NOT NULL,
create_time TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
update_time TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
+ workspace_id BIGINT NOT NULL,
PRIMARY KEY (id)
);
@@ -128,8 +132,9 @@
target_plugin_id VARCHAR(50) NOT NULL,
create_time TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
update_time TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
+ workspace_id BIGINT NOT NULL,
PRIMARY KEY (id),
- INDEX job_line_version_index (version_id)
+ INDEX job_line_version_index (version_id, workspace_id)
);
-- Table structure for t_st_job_metrics
@@ -150,6 +155,7 @@
update_user_id INT DEFAULT NULL,
create_time TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
update_time TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
+ workspace_id BIGINT NOT NULL,
PRIMARY KEY (id)
);
@@ -171,8 +177,9 @@
type VARCHAR(50) NOT NULL,
create_time TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
update_time TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
+ workspace_id BIGINT NOT NULL,
PRIMARY KEY (id),
- INDEX job_task_plugin_id_index (plugin_id)
+ INDEX job_task_plugin_id_index (plugin_id, workspace_id)
);
-- Table structure for t_st_job_version
@@ -189,6 +196,7 @@
update_user_id INT NOT NULL,
create_time TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
update_time TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
+ workspace_id BIGINT NOT NULL,
PRIMARY KEY (id)
);
@@ -206,6 +214,7 @@
update_user_id INT NOT NULL,
create_time TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
update_time TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
+ workspace_id BIGINT NOT NULL,
PRIMARY KEY (id)
);
@@ -226,6 +235,36 @@
-- Records of user
INSERT INTO "user" ("username", "password", "status", "type") VALUES ('admin', '7f97da8846fed829bb8d1fd9f8030f3b', 0, 0);
+-- ----------------------------
+-- Table structure for user_login_log
+-- ----------------------------
+DROP TABLE IF EXISTS user_login_log;
+CREATE TABLE user_login_log (
+ id BIGINT NOT NULL AUTO_INCREMENT,
+ user_id INT NOT NULL,
+ token CLOB NOT NULL,
+ token_status TINYINT NOT NULL,
+ create_time TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(),
+ update_time TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP() ON UPDATE CURRENT_TIMESTAMP(),
+ workspace_id BIGINT NOT NULL,
+ PRIMARY KEY (id)
+);
+
+-- ----------------------------
+-- Workspace related tables
+-- ----------------------------
+DROP TABLE IF EXISTS "workspace";
+CREATE TABLE workspace (
+ id BIGINT NOT NULL AUTO_INCREMENT,
+ workspace_name VARCHAR(255) NOT NULL,
+ description VARCHAR(255) DEFAULT NULL,
+ create_time TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(),
+ update_time TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP() ON UPDATE CURRENT_TIMESTAMP(),
+ PRIMARY KEY (id)
+);
+
+INSERT INTO workspace (workspace_name, description) VALUES ('default', 'default workspace');
+
-- Records of user_login_log
-- No equivalent records provided for the user_login_log table in the provided SQL script.
-- You can insert records into this table using similar INSERT INTO statements.
diff --git a/seatunnel-server/seatunnel-app/src/main/resources/script/seatunnel_server_mysql.sql b/seatunnel-server/seatunnel-app/src/main/resources/script/seatunnel_server_mysql.sql
index 2262caa..5dd91e4 100644
--- a/seatunnel-server/seatunnel-app/src/main/resources/script/seatunnel_server_mysql.sql
+++ b/seatunnel-server/seatunnel-app/src/main/resources/script/seatunnel_server_mysql.sql
@@ -68,8 +68,9 @@
`update_user_id` int(11) NOT NULL,
`create_time` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
`update_time` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3) ON UPDATE CURRENT_TIMESTAMP(3),
+ `workspace_id` bigint(20) NOT NULL,
PRIMARY KEY (`id`) USING BTREE,
- UNIQUE INDEX `t_st_datasource_datasource_name_uindex`(`datasource_name`) USING BTREE
+ UNIQUE INDEX `t_st_datasource_datasource_name_uindex`(`datasource_name`, `workspace_id`) USING BTREE
) ENGINE = InnoDB CHARACTER SET = utf8mb4 COLLATE = utf8mb4_bin ROW_FORMAT = Dynamic;
-- ----------------------------
@@ -85,8 +86,9 @@
`update_user_id` int(11) NOT NULL,
`create_time` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
`update_time` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3) ON UPDATE CURRENT_TIMESTAMP(3),
+ `workspace_id` bigint(20) NOT NULL,
PRIMARY KEY (`id`) USING BTREE,
- UNIQUE INDEX `name`(`name`) USING BTREE
+ UNIQUE INDEX `name`(`name`, `workspace_id`) USING BTREE
) ENGINE = InnoDB CHARACTER SET = utf8mb4 COLLATE = utf8mb4_bin ROW_FORMAT = Dynamic;
-- ----------------------------
@@ -108,6 +110,7 @@
`end_time` timestamp(3) NULL DEFAULT NULL,
`job_type` varchar(50) CHARACTER SET utf8mb4 COLLATE utf8mb4_bin NOT NULL,
`error_message` varchar(4096) CHARACTER SET utf8mb4 COLLATE utf8mb4_bin NULL DEFAULT NULL,
+ `workspace_id` bigint(20) NOT NULL,
PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB CHARACTER SET = utf8mb4 COLLATE = utf8mb4_bin ROW_FORMAT = Dynamic;
@@ -120,6 +123,7 @@
`dag` text CHARACTER SET utf8mb4 COLLATE utf8mb4_bin NOT NULL,
`create_time` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
`update_time` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3) ON UPDATE CURRENT_TIMESTAMP(3),
+ `workspace_id` bigint(20) NOT NULL,
PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB CHARACTER SET = utf8mb4 COLLATE = utf8mb4_bin ROW_FORMAT = Dynamic;
@@ -134,8 +138,9 @@
`target_plugin_id` varchar(50) CHARACTER SET utf8mb4 COLLATE utf8mb4_bin NOT NULL,
`create_time` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
`update_time` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3) ON UPDATE CURRENT_TIMESTAMP(3),
+ `workspace_id` bigint(20) NOT NULL,
PRIMARY KEY (`id`) USING BTREE,
- INDEX `job_line_version_index`(`version_id`) USING BTREE
+ INDEX `job_line_version_index`(`version_id`, `workspace_id`) USING BTREE
) ENGINE = InnoDB CHARACTER SET = utf8mb4 COLLATE = utf8mb4_bin ROW_FORMAT = Dynamic;
-- ----------------------------
@@ -158,6 +163,7 @@
`update_user_id` int(20) NULL DEFAULT NULL,
`create_time` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
`update_time` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3) ON UPDATE CURRENT_TIMESTAMP(3),
+ `workspace_id` bigint(20) NOT NULL,
PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB CHARACTER SET = utf8mb4 COLLATE = utf8mb4_bin ROW_FORMAT = Dynamic;
@@ -181,8 +187,9 @@
`type` varchar(50) CHARACTER SET utf8mb4 COLLATE utf8mb4_bin NOT NULL,
`create_time` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
`update_time` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3) ON UPDATE CURRENT_TIMESTAMP(3),
+ `workspace_id` bigint(20) NOT NULL,
PRIMARY KEY (`id`) USING BTREE,
- INDEX `job_task_plugin_id_index`(`plugin_id`) USING BTREE
+ INDEX `job_task_plugin_id_index`(`plugin_id`, `workspace_id` ) USING BTREE
) ENGINE = InnoDB CHARACTER SET = utf8mb4 COLLATE = utf8mb4_bin ROW_FORMAT = Dynamic;
-- ----------------------------
@@ -201,6 +208,7 @@
`update_user_id` int(11) NOT NULL,
`create_time` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
`update_time` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3) ON UPDATE CURRENT_TIMESTAMP(3),
+ `workspace_id` bigint(20) NOT NULL,
PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB CHARACTER SET = utf8mb4 COLLATE = utf8mb4_bin ROW_FORMAT = Dynamic;
@@ -220,6 +228,7 @@
`update_user_id` int(11) NOT NULL,
`create_time` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
`update_time` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3) ON UPDATE CURRENT_TIMESTAMP(3),
+ `workspace_id` bigint(20) NOT NULL,
PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB CHARACTER SET = utf8mb4 COLLATE = utf8mb4_bin ROW_FORMAT = Dynamic;
@@ -250,6 +259,7 @@
`token_status` tinyint(1) NOT NULL,
`create_time` datetime(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
`update_time` datetime(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3) ON UPDATE CURRENT_TIMESTAMP(3),
+ `workspace_id` bigint(20) NOT NULL,
PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 106 CHARACTER SET = utf8mb4 COLLATE = utf8mb4_general_ci ROW_FORMAT = Dynamic;
@@ -260,3 +270,17 @@
INSERT INTO `seatunnel`.`user`(`username`,`password`,`status`,`type`) values ('admin', '7f97da8846fed829bb8d1fd9f8030f3b', 0, 0);
SET FOREIGN_KEY_CHECKS = 1;
+
+-- ----------------------------
+-- Workspace related tables
+-- ----------------------------
+CREATE TABLE `workspace` (
+ `id` bigint(20) NOT NULL AUTO_INCREMENT,
+ `workspace_name` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NOT NULL,
+ `description` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NULL DEFAULT NULL,
+ `create_time` datetime(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
+ `update_time` datetime(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3) ON UPDATE CURRENT_TIMESTAMP(3),
+ PRIMARY KEY (`id`) USING BTREE
+) ENGINE = InnoDB AUTO_INCREMENT = 1 CHARACTER SET = utf8mb4 COLLATE = utf8mb4_general_ci ROW_FORMAT = Dynamic;
+
+INSERT INTO `seatunnel`.`workspace`(`workspace_name`,`description`) values ('default', 'default workspace');
diff --git a/seatunnel-server/seatunnel-app/src/test/java/org/apache/seatunnel/app/security/AsyncUserContextTest.java b/seatunnel-server/seatunnel-app/src/test/java/org/apache/seatunnel/app/security/AsyncUserContextTest.java
index 13ee42f..f5460d6 100644
--- a/seatunnel-server/seatunnel-app/src/test/java/org/apache/seatunnel/app/security/AsyncUserContextTest.java
+++ b/seatunnel-server/seatunnel-app/src/test/java/org/apache/seatunnel/app/security/AsyncUserContextTest.java
@@ -63,7 +63,7 @@
taskExecutor.shutdown();
}
// Clear any remaining user context
- UserContext.clear();
+ UserContextHolder.clear();
}
@Test
@@ -85,7 +85,7 @@
"Setting main thread user context: userId={}, username={}",
userId,
user.getUsername());
- UserContext.setUser(user);
+ UserContextHolder.setUserContext(getUserContext(user));
CompletableFuture<Void> future =
CompletableFuture.runAsync(
@@ -145,6 +145,12 @@
}
}
+ private UserContext getUserContext(User user) {
+ UserContext userContext = new UserContext();
+ userContext.setUser(user);
+ return userContext;
+ }
+
@Test
public void testNestedAsyncCalls() throws Exception {
log.info("Starting nested async calls test...");
@@ -157,7 +163,7 @@
"Setting main thread user context: userId={}, username={}",
user.getId(),
user.getUsername());
- UserContext.setUser(user);
+ UserContextHolder.setUserContext(getUserContext(user));
CompletableFuture<Void> future =
CompletableFuture.runAsync(
@@ -204,7 +210,7 @@
// First user
User user1 = new User();
user1.setId(1);
- UserContext.setUser(user1);
+ UserContextHolder.setUserContext(getUserContext(user1));
log.info("Setting first user context: userId={}", user1.getId());
// Capture current user to avoid context loss during thread switching
@@ -217,7 +223,7 @@
"First user's async task started: threadName={}",
Thread.currentThread().getName());
Thread.sleep(1000);
- UserContext.setUser(capturedUser1);
+ UserContextHolder.setUserContext(getUserContext(capturedUser1));
User currentUser = ServletUtils.getCurrentUser();
log.info(
"First user's async task got user: userId={}",
@@ -227,7 +233,7 @@
log.error("First user's async task failed", e);
throw new RuntimeException(e);
} finally {
- UserContext.clear();
+ UserContextHolder.clear();
latch.countDown();
}
},
@@ -236,7 +242,7 @@
// Second user
User user2 = new User();
user2.setId(2);
- UserContext.setUser(user2);
+ UserContextHolder.setUserContext(getUserContext(user2));
log.info("Setting second user context: userId={}", user2.getId());
// Capture current user to avoid context loss during thread switching
@@ -248,7 +254,7 @@
log.info(
"Second user's async task started: threadName={}",
Thread.currentThread().getName());
- UserContext.setUser(capturedUser2);
+ UserContextHolder.setUserContext(getUserContext(capturedUser2));
User currentUser = ServletUtils.getCurrentUser();
log.info(
"Second user's async task got user: userId={}",
@@ -258,7 +264,7 @@
log.error("Second user's async task failed", e);
throw new RuntimeException(e);
} finally {
- UserContext.clear();
+ UserContextHolder.clear();
latch.countDown();
}
},
@@ -274,6 +280,6 @@
assertEquals(2, result2);
log.info("User context isolation test completed");
- UserContext.clear();
+ UserContextHolder.clear();
}
}
diff --git a/seatunnel-server/seatunnel-server-common/src/main/java/org/apache/seatunnel/server/common/SeatunnelErrorEnum.java b/seatunnel-server/seatunnel-server-common/src/main/java/org/apache/seatunnel/server/common/SeatunnelErrorEnum.java
index 8a232b3..5318b55 100644
--- a/seatunnel-server/seatunnel-server-common/src/main/java/org/apache/seatunnel/server/common/SeatunnelErrorEnum.java
+++ b/seatunnel-server/seatunnel-server-common/src/main/java/org/apache/seatunnel/server/common/SeatunnelErrorEnum.java
@@ -140,7 +140,7 @@
INVALID_PARAM(60019, "", "param [%s] is invalid. %s"),
TASK_NAME_ALREADY_EXISTS(60020, "task name already exists", "task [%s] already exists"),
RESOURCE_NOT_FOUND(404, "", "%s"),
- ;
+ RESOURCE_ALREADY_EXISTS(60021, "resource already exists", "resource [%s] already exists");
private final int code;
private final String msg;
diff --git a/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/common/SeatunnelWebTestingBase.java b/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/common/SeatunnelWebTestingBase.java
index a006cd3..46df8f7 100644
--- a/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/common/SeatunnelWebTestingBase.java
+++ b/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/common/SeatunnelWebTestingBase.java
@@ -42,14 +42,25 @@
}
public Result<UserSimpleInfoRes> login(UserLoginReq userLoginReq, String authType) {
+ return login(userLoginReq, authType, false);
+ }
+
+ public Result<UserSimpleInfoRes> login(
+ UserLoginReq userLoginReq, String authType, Boolean setAsCurrentUser) {
String requestBody = JsonUtils.toJsonString(userLoginReq);
Map<String, String> headers =
authType != null
? Collections.singletonMap("X-Seatunnel-Auth-Type", authType)
: null;
String response = sendRequest(url("user/login"), requestBody, "POST", headers);
- return JSONTestUtils.parseObject(
- response, new TypeReference<Result<UserSimpleInfoRes>>() {});
+ Result<UserSimpleInfoRes> userSimpleInfoResResult =
+ JSONTestUtils.parseObject(
+ response, new TypeReference<Result<UserSimpleInfoRes>>() {});
+ if (setAsCurrentUser) {
+ assert userSimpleInfoResResult != null;
+ TokenProvider.setToken(userSimpleInfoResResult.getData().getToken());
+ }
+ return userSimpleInfoResResult;
}
protected String url(String path) {
diff --git a/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/common/TokenProvider.java b/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/common/TokenProvider.java
index 7f58495..7586ee2 100644
--- a/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/common/TokenProvider.java
+++ b/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/common/TokenProvider.java
@@ -35,6 +35,10 @@
userLoginReq.setUsername("admin");
userLoginReq.setPassword("admin");
Result<UserSimpleInfoRes> loginResponse = seatunnelWebTestingBase.login(userLoginReq);
- TokenProvider.token = loginResponse.getData().getToken();
+ setToken(loginResponse.getData().getToken());
+ }
+
+ public static void setToken(String token) {
+ TokenProvider.token = token;
}
}
diff --git a/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/controller/JobControllerWrapper.java b/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/controller/JobControllerWrapper.java
index 9a5b64b..04705a1 100644
--- a/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/controller/JobControllerWrapper.java
+++ b/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/controller/JobControllerWrapper.java
@@ -18,13 +18,19 @@
import org.apache.seatunnel.app.common.Result;
import org.apache.seatunnel.app.common.SeatunnelWebTestingBase;
+import org.apache.seatunnel.app.domain.request.job.JobConfig;
import org.apache.seatunnel.app.domain.request.job.JobCreateReq;
+import org.apache.seatunnel.app.domain.request.job.JobDAG;
+import org.apache.seatunnel.app.domain.request.job.PluginConfig;
+import org.apache.seatunnel.app.domain.response.job.JobConfigRes;
import org.apache.seatunnel.app.domain.response.job.JobRes;
import org.apache.seatunnel.app.utils.JSONTestUtils;
import org.apache.seatunnel.common.utils.JsonUtils;
import com.fasterxml.jackson.core.type.TypeReference;
+import java.util.List;
+
public class JobControllerWrapper extends SeatunnelWebTestingBase {
public Result<Long> createJob(JobCreateReq jobCreateRequest) {
@@ -44,4 +50,26 @@
String response = sendRequest(urlWithParam("job/get/" + jobVersionId + "?"), null, "GET");
return JSONTestUtils.parseObject(response, new TypeReference<Result<JobRes>>() {});
}
+
+ public JobCreateReq convertJobResToJobCreateReq(JobRes jobRes) {
+ JobCreateReq jobCreateReq = new JobCreateReq();
+
+ // Assuming JobRes contains JobConfigRes and List<PluginConfig> and JobDAG
+ JobConfigRes jobConfigRes = jobRes.getJobConfig();
+ List<PluginConfig> pluginConfigs = jobRes.getPluginConfigs();
+ JobDAG jobDAG = jobRes.getJobDAG();
+
+ // Populate JobCreateReq with data from JobRes
+ JobConfig jobConfig = new JobConfig();
+ jobConfig.setName(jobConfigRes.getName());
+ jobConfig.setDescription(jobConfigRes.getDescription());
+ jobConfig.setEnv(jobConfigRes.getEnv());
+ jobConfig.setEngine(jobConfigRes.getEngine());
+
+ jobCreateReq.setJobConfig(jobConfig);
+ jobCreateReq.setPluginConfigs(pluginConfigs);
+ jobCreateReq.setJobDAG(jobDAG);
+
+ return jobCreateReq;
+ }
}
diff --git a/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/controller/UserControllerWrapper.java b/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/controller/UserControllerWrapper.java
index 711ef67..57e8ded 100644
--- a/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/controller/UserControllerWrapper.java
+++ b/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/controller/UserControllerWrapper.java
@@ -18,14 +18,20 @@
import org.apache.seatunnel.app.common.Result;
import org.apache.seatunnel.app.common.SeatunnelWebTestingBase;
+import org.apache.seatunnel.app.common.TokenProvider;
import org.apache.seatunnel.app.domain.request.user.AddUserReq;
import org.apache.seatunnel.app.domain.request.user.UpdateUserReq;
+import org.apache.seatunnel.app.domain.request.user.UserLoginReq;
+import org.apache.seatunnel.app.domain.response.PageInfo;
import org.apache.seatunnel.app.domain.response.user.AddUserRes;
+import org.apache.seatunnel.app.domain.response.user.UserSimpleInfoRes;
import org.apache.seatunnel.app.utils.JSONTestUtils;
import org.apache.seatunnel.common.utils.JsonUtils;
import com.fasterxml.jackson.core.type.TypeReference;
+import static org.junit.jupiter.api.Assertions.assertTrue;
+
public class UserControllerWrapper extends SeatunnelWebTestingBase {
public Result<AddUserRes> addUser(AddUserReq addUserReq) {
@@ -51,8 +57,56 @@
return JSONTestUtils.parseObject(response, Result.class);
}
+ public Result<PageInfo<UserSimpleInfoRes>> listUsers(String name) {
+ String response = sendRequest(urlWithParam("user?name=" + name + "&pageNo=1&pageSize=10"));
+ return JSONTestUtils.parseObject(
+ response, new TypeReference<Result<PageInfo<UserSimpleInfoRes>>>() {});
+ }
+
+ public Result<PageInfo<UserSimpleInfoRes>> listUsers() {
+ String response = sendRequest(urlWithParam("user?pageNo=1&pageSize=10000"));
+ return JSONTestUtils.parseObject(
+ response, new TypeReference<Result<PageInfo<UserSimpleInfoRes>>>() {});
+ }
+
+ public Result<Void> disableUser(String userId) {
+ String response = sendRequest(url("user/" + userId + "/disable"), null, "PUT");
+ return JSONTestUtils.parseObject(response, Result.class);
+ }
+
+ public Result<Void> enableUser(String userId) {
+ String response = sendRequest(url("user/" + userId + "/enable"), null, "PATCH");
+ return JSONTestUtils.parseObject(response, Result.class);
+ }
+
+ public Result<AddUserRes> addUser(String userName, String password) {
+ String requestBody = JsonUtils.toJsonString(getAddUserReq(userName, password));
+ String response = sendRequest(url("user"), requestBody, "POST");
+ return JSONTestUtils.parseObject(response, new TypeReference<Result<AddUserRes>>() {});
+ }
+
public Result<Void> logout() {
String response = sendRequest(url("user/logout"), null, "PATCH");
- return JSONTestUtils.parseObject(response, Result.class);
+ Result<Void> logoutResult =
+ JSONTestUtils.parseObject(response, new TypeReference<Result<Void>>() {});
+ assert logoutResult != null;
+ if (logoutResult.isSuccess()) {
+ TokenProvider.setToken(null);
+ }
+ return logoutResult;
+ }
+
+ public void loginAndSetCurrentUser(UserLoginReq userLoginReq) {
+ Result<UserSimpleInfoRes> login = login(userLoginReq, null, true);
+ assertTrue(login.isSuccess());
+ }
+
+ private AddUserReq getAddUserReq(String user, String pass) {
+ AddUserReq addUserReq = new AddUserReq();
+ addUserReq.setUsername(user);
+ addUserReq.setPassword(pass);
+ addUserReq.setStatus((byte) 0);
+ addUserReq.setType((byte) 0);
+ return addUserReq;
}
}
diff --git a/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/controller/WorkspaceControllerWrapper.java b/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/controller/WorkspaceControllerWrapper.java
new file mode 100644
index 0000000..be57c97
--- /dev/null
+++ b/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/controller/WorkspaceControllerWrapper.java
@@ -0,0 +1,68 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+
+package org.apache.seatunnel.app.controller;
+
+import org.apache.seatunnel.app.common.Result;
+import org.apache.seatunnel.app.common.SeatunnelWebTestingBase;
+import org.apache.seatunnel.app.dal.entity.Workspace;
+import org.apache.seatunnel.app.domain.request.workspace.WorkspaceReq;
+import org.apache.seatunnel.app.utils.JSONTestUtils;
+import org.apache.seatunnel.common.utils.JsonUtils;
+
+import com.fasterxml.jackson.core.type.TypeReference;
+
+import java.util.List;
+
+import static org.junit.jupiter.api.Assertions.assertTrue;
+
+public class WorkspaceControllerWrapper extends SeatunnelWebTestingBase {
+
+ public Result<List<Workspace>> getAllWorkspaces() {
+ String response = sendRequest(url("workspace/list"));
+ return JSONTestUtils.parseObject(response, new TypeReference<Result<List<Workspace>>>() {});
+ }
+
+ public Result<Workspace> getWorkspacesById(Long workspaceId) {
+ String response = sendRequest(url("workspace/list/" + workspaceId));
+ return JSONTestUtils.parseObject(response, new TypeReference<Result<Workspace>>() {});
+ }
+
+ public Result<Long> createWorkspace(String workspaceName) {
+ WorkspaceReq workspaceReq = new WorkspaceReq(workspaceName, workspaceName + " description");
+ String requestBody = JsonUtils.toJsonString(workspaceReq);
+ String response = sendRequest(url("workspace/create"), requestBody, "POST");
+ return JSONTestUtils.parseObject(response, new TypeReference<Result<Long>>() {});
+ }
+
+ public void createWorkspaceAndVerify(String workspaceName) {
+ Result<Long> workspaceCreationResult = createWorkspace(workspaceName);
+ assertTrue(workspaceCreationResult.isSuccess());
+ assertTrue(workspaceCreationResult.getData() > 0);
+ }
+
+ public Result<Boolean> updateWorkspace(Long workspaceId, WorkspaceReq workspaceReq) {
+ String requestBody = JsonUtils.toJsonString(workspaceReq);
+ String response = sendRequest(url("workspace/update/" + workspaceId), requestBody, "PUT");
+ return JSONTestUtils.parseObject(response, new TypeReference<Result<Boolean>>() {});
+ }
+
+ public Result<Boolean> deleteWorkspace(Long workspaceId) {
+ String response = sendRequest(url("workspace/delete/" + workspaceId), null, "DELETE");
+ return JSONTestUtils.parseObject(response, new TypeReference<Result<Boolean>>() {});
+ }
+}
diff --git a/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/test/JobControllerTest.java b/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/test/JobControllerTest.java
index d3c0c8a..3fd5c17 100644
--- a/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/test/JobControllerTest.java
+++ b/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/test/JobControllerTest.java
@@ -26,7 +26,6 @@
import org.apache.seatunnel.app.domain.request.job.JobCreateReq;
import org.apache.seatunnel.app.domain.request.job.JobDAG;
import org.apache.seatunnel.app.domain.request.job.PluginConfig;
-import org.apache.seatunnel.app.domain.response.job.JobConfigRes;
import org.apache.seatunnel.app.domain.response.job.JobRes;
import org.apache.seatunnel.app.domain.response.metrics.JobPipelineDetailMetricsRes;
import org.apache.seatunnel.app.utils.JobTestingUtils;
@@ -154,7 +153,7 @@
jobCreateReq.getPluginConfigs().get(1).getName(),
jobRes.getPluginConfigs().get(1).getName());
- JobCreateReq jobUpdateReq = convertJobResToJobCreateReq(jobRes);
+ JobCreateReq jobUpdateReq = jobControllerWrapper.convertJobResToJobCreateReq(jobRes);
String jobName2 = "updateJob_single_api2" + uniqueId;
jobUpdateReq.getJobConfig().setName(jobName2);
jobUpdateReq.getJobConfig().setDescription(jobName2 + " description");
@@ -209,7 +208,7 @@
assertTrue(getJobResponse.isSuccess());
JobRes jobRes = getJobResponse.getData();
- JobCreateReq jobUpdateReq = convertJobResToJobCreateReq(jobRes);
+ JobCreateReq jobUpdateReq = jobControllerWrapper.convertJobResToJobCreateReq(jobRes);
jobUpdateReq.getPluginConfigs().add(getCopyTransformPlugin());
List<Edge> edges = new ArrayList<>();
@@ -242,7 +241,7 @@
assertTrue(getJobResponse.isSuccess());
JobRes jobRes = getJobResponse.getData();
- JobCreateReq jobUpdateReq = convertJobResToJobCreateReq(jobRes);
+ JobCreateReq jobUpdateReq = jobControllerWrapper.convertJobResToJobCreateReq(jobRes);
jobUpdateReq
.getPluginConfigs()
.removeIf(pluginConfig -> "transform-replace".equals(pluginConfig.getName()));
@@ -281,28 +280,6 @@
.build();
}
- private JobCreateReq convertJobResToJobCreateReq(JobRes jobRes) {
- JobCreateReq jobCreateReq = new JobCreateReq();
-
- // Assuming JobRes contains JobConfigRes and List<PluginConfig> and JobDAG
- JobConfigRes jobConfigRes = jobRes.getJobConfig();
- List<PluginConfig> pluginConfigs = jobRes.getPluginConfigs();
- JobDAG jobDAG = jobRes.getJobDAG();
-
- // Populate JobCreateReq with data from JobRes
- JobConfig jobConfig = new JobConfig();
- jobConfig.setName(jobConfigRes.getName());
- jobConfig.setDescription(jobConfigRes.getDescription());
- jobConfig.setEnv(jobConfigRes.getEnv());
- jobConfig.setEngine(jobConfigRes.getEngine());
-
- jobCreateReq.setJobConfig(jobConfig);
- jobCreateReq.setPluginConfigs(pluginConfigs);
- jobCreateReq.setJobDAG(jobDAG);
-
- return jobCreateReq;
- }
-
@AfterAll
public static void tearDown() {
seaTunnelWebCluster.stop();
diff --git a/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/test/JobExecutorControllerTest.java b/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/test/JobExecutorControllerTest.java
index 63488d1..bfe7464 100644
--- a/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/test/JobExecutorControllerTest.java
+++ b/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/test/JobExecutorControllerTest.java
@@ -21,14 +21,18 @@
import org.apache.seatunnel.app.controller.JobControllerWrapper;
import org.apache.seatunnel.app.controller.JobExecutorControllerWrapper;
import org.apache.seatunnel.app.controller.SeatunnelDatasourceControllerWrapper;
+import org.apache.seatunnel.app.controller.UserControllerWrapper;
+import org.apache.seatunnel.app.controller.WorkspaceControllerWrapper;
import org.apache.seatunnel.app.domain.dto.job.SeaTunnelJobInstanceDto;
import org.apache.seatunnel.app.domain.request.datasource.DatasourceReq;
import org.apache.seatunnel.app.domain.request.job.JobCreateReq;
import org.apache.seatunnel.app.domain.request.job.JobExecParam;
import org.apache.seatunnel.app.domain.request.job.PluginConfig;
+import org.apache.seatunnel.app.domain.request.user.UserLoginReq;
import org.apache.seatunnel.app.domain.response.executor.JobExecutionStatus;
import org.apache.seatunnel.app.domain.response.executor.JobExecutorRes;
import org.apache.seatunnel.app.domain.response.metrics.JobPipelineDetailMetricsRes;
+import org.apache.seatunnel.app.domain.response.user.AddUserRes;
import org.apache.seatunnel.app.utils.JobTestingUtils;
import org.apache.seatunnel.engine.core.job.JobStatus;
@@ -54,6 +58,8 @@
private static final String uniqueId = "_" + System.currentTimeMillis();
private static SeatunnelDatasourceControllerWrapper seatunnelDatasourceControllerWrapper;
private static JobControllerWrapper jobControllerWrapper;
+ private static WorkspaceControllerWrapper workspaceControllerWrapper;
+ private static UserControllerWrapper userControllerWrapper;
@BeforeAll
public static void setUp() {
@@ -61,6 +67,8 @@
jobExecutorControllerWrapper = new JobExecutorControllerWrapper();
seatunnelDatasourceControllerWrapper = new SeatunnelDatasourceControllerWrapper();
jobControllerWrapper = new JobControllerWrapper();
+ workspaceControllerWrapper = new WorkspaceControllerWrapper();
+ userControllerWrapper = new UserControllerWrapper();
}
@Test
@@ -79,6 +87,27 @@
}
@Test
+ public void executeJobWithWorkspaceLogin() {
+ String userName = "user_exec_job_with_workspace" + uniqueId;
+ String password = "somePass";
+ String workspaceName = "workspace_exec_job_with_workspace" + uniqueId;
+ createWorkspaceAndUser(workspaceName, userName, password);
+ userControllerWrapper.loginAndSetCurrentUser(
+ new UserLoginReq(userName, password, workspaceName));
+ String jobName = "execJob_within_workspace" + uniqueId;
+ long jobVersionId = JobTestingUtils.createJob(jobName);
+ Result<Long> result = jobExecutorControllerWrapper.jobExecutor(jobVersionId);
+ assertTrue(result.isSuccess());
+ assertTrue(result.getData() > 0);
+ Result<List<JobPipelineDetailMetricsRes>> listResult =
+ JobTestingUtils.waitForJobCompletion(result.getData());
+ assertEquals(1, listResult.getData().size());
+ assertEquals(JobStatus.FINISHED, listResult.getData().get(0).getStatus());
+ assertEquals(5, listResult.getData().get(0).getReadRowCount());
+ assertEquals(5, listResult.getData().get(0).getWriteRowCount());
+ }
+
+ @Test
public void executeJobWithParameters() {
String jobName = "execJobWithParam" + uniqueId;
JobCreateReq jobCreateReq =
@@ -301,6 +330,12 @@
seaTunnelWebCluster.stop();
}
+ private void createWorkspaceAndUser(String workspaceName, String username, String password) {
+ workspaceControllerWrapper.createWorkspaceAndVerify(workspaceName);
+ Result<AddUserRes> result = userControllerWrapper.addUser(username, password);
+ assertTrue(result.isSuccess());
+ }
+
private String getGenerateJobFile(String jobId) {
String filePath = "profile/" + jobId + ".conf";
String jsonContent;
diff --git a/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/test/UserControllerTest.java b/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/test/UserControllerTest.java
index 77363cc..535d9f3 100644
--- a/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/test/UserControllerTest.java
+++ b/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/test/UserControllerTest.java
@@ -19,6 +19,7 @@
import org.apache.seatunnel.app.common.Result;
import org.apache.seatunnel.app.common.SeaTunnelWebCluster;
import org.apache.seatunnel.app.controller.UserControllerWrapper;
+import org.apache.seatunnel.app.controller.WorkspaceControllerWrapper;
import org.apache.seatunnel.app.domain.request.user.AddUserReq;
import org.apache.seatunnel.app.domain.request.user.UpdateUserReq;
import org.apache.seatunnel.app.domain.request.user.UserLoginReq;
@@ -34,18 +35,19 @@
import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertFalse;
-import static org.junit.jupiter.api.Assertions.assertNotNull;
import static org.junit.jupiter.api.Assertions.assertTrue;
public class UserControllerTest {
private static final SeaTunnelWebCluster seaTunnelWebCluster = new SeaTunnelWebCluster();
private static UserControllerWrapper userControllerWrapper;
+ private static WorkspaceControllerWrapper workspaceControllerWrapper;
final Supplier<String> uniqueId = () -> "_" + System.nanoTime();
@BeforeAll
public static void setUp() {
seaTunnelWebCluster.start();
userControllerWrapper = new UserControllerWrapper();
+ workspaceControllerWrapper = new WorkspaceControllerWrapper();
}
@Test
@@ -99,7 +101,6 @@
public void listUsers_shouldReturnUsers_whenUsersExist() {
Result<Void> result = userControllerWrapper.listUsers(1, 10);
assertTrue(result.isSuccess());
- assertNotNull(result.getData());
}
@Test
@@ -179,6 +180,35 @@
SeatunnelErrorEnum.USERNAME_PASSWORD_NO_MATCHED.getCode(), loginResult.getCode());
}
+ @Test
+ public void loginWithWorkspace() {
+ String user = "userLoginWithWorkspace" + uniqueId.get();
+ String pass = "pass9";
+ String workspace = "workspaceForLogin" + uniqueId.get();
+
+ workspaceControllerWrapper.createWorkspaceAndVerify(workspace);
+ AddUserReq addUserReq = getAddUserReq(user, pass);
+ Result<AddUserRes> result = userControllerWrapper.addUser(addUserReq);
+ assertTrue(result.isSuccess());
+ UserLoginReq userLoginReq = new UserLoginReq();
+ userLoginReq.setUsername(user);
+ userLoginReq.setPassword(pass);
+ userLoginReq.setWorkspaceName(workspace);
+ Result<UserSimpleInfoRes> login = userControllerWrapper.login(userLoginReq);
+ assertTrue(login.isSuccess());
+
+ // login with workspace when workspace does not exist
+ userLoginReq.setWorkspaceName("nonExistentWorkspace");
+ Result<UserSimpleInfoRes> loginResult = userControllerWrapper.login(userLoginReq);
+ assertFalse(loginResult.isSuccess());
+ assertEquals(SeatunnelErrorEnum.RESOURCE_NOT_FOUND.getCode(), loginResult.getCode());
+
+ // login without any workspace, should login with the workspace of the user
+ userLoginReq.setWorkspaceName(null);
+ Result<UserSimpleInfoRes> loginWithoutWorkspace = userControllerWrapper.login(userLoginReq);
+ assertTrue(loginWithoutWorkspace.isSuccess());
+ }
+
@AfterAll
public static void tearDown() {
Result<Void> logout = userControllerWrapper.logout();
diff --git a/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/test/WorkspaceControllerTest.java b/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/test/WorkspaceControllerTest.java
new file mode 100644
index 0000000..316615a
--- /dev/null
+++ b/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/test/WorkspaceControllerTest.java
@@ -0,0 +1,158 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+
+package org.apache.seatunnel.app.test;
+
+import org.apache.seatunnel.app.common.Result;
+import org.apache.seatunnel.app.common.SeaTunnelWebCluster;
+import org.apache.seatunnel.app.controller.WorkspaceControllerWrapper;
+import org.apache.seatunnel.app.dal.entity.Workspace;
+import org.apache.seatunnel.app.domain.request.workspace.WorkspaceReq;
+import org.apache.seatunnel.server.common.SeatunnelErrorEnum;
+
+import org.junit.jupiter.api.AfterAll;
+import org.junit.jupiter.api.BeforeAll;
+import org.junit.jupiter.api.Test;
+
+import java.util.List;
+import java.util.stream.Collectors;
+
+import static org.junit.jupiter.api.Assertions.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertFalse;
+import static org.junit.jupiter.api.Assertions.assertNotNull;
+import static org.junit.jupiter.api.Assertions.assertTrue;
+
+public class WorkspaceControllerTest {
+ private static final SeaTunnelWebCluster seaTunnelWebCluster = new SeaTunnelWebCluster();
+ private static WorkspaceControllerWrapper workspaceControllerWrapper;
+ private static final String uniqueId = "_" + System.currentTimeMillis();
+
+ @BeforeAll
+ public static void setUp() {
+ seaTunnelWebCluster.start();
+ workspaceControllerWrapper = new WorkspaceControllerWrapper();
+ }
+
+ @Test
+ public void testCreateWorkspace() {
+ String workspaceName = "workspace_create" + uniqueId;
+ Long workspaceId = createWorkspace(workspaceName);
+ Workspace workspacesById = getWorkspace(workspaceId);
+ assertEquals(workspaceName, workspacesById.getWorkspaceName());
+ // test duplicated workspace name is not allowed
+ Result<Long> result = workspaceControllerWrapper.createWorkspace(workspaceName);
+ assertFalse(result.isSuccess());
+ assertEquals(SeatunnelErrorEnum.RESOURCE_ALREADY_EXISTS.getCode(), result.getCode());
+
+ // create workspace with empty workspace name
+ result = workspaceControllerWrapper.createWorkspace("");
+ assertFalse(result.isSuccess());
+ assertEquals(SeatunnelErrorEnum.PARAM_CAN_NOT_BE_NULL.getCode(), result.getCode());
+ }
+
+ @Test
+ public void testUpdateWorkspace() {
+ String workspaceName = "workspace_update" + uniqueId;
+ Long workspaceId = createWorkspace(workspaceName);
+
+ // update workspace
+ Workspace workspacesById = getWorkspace(workspaceId);
+ String newName = workspacesById.getWorkspaceName() + "_newName";
+ String newDescription = workspacesById.getDescription() + "_newDescription";
+ WorkspaceReq workspaceReq = new WorkspaceReq(newName, newDescription);
+ Result<Boolean> updateResult =
+ workspaceControllerWrapper.updateWorkspace(workspaceId, workspaceReq);
+ assertTrue(updateResult.isSuccess());
+ assertTrue(updateResult.getData());
+
+ workspacesById = getWorkspace(workspaceId);
+ assertEquals(workspacesById.getWorkspaceName(), newName);
+ assertEquals(workspacesById.getDescription(), newDescription);
+
+ // update workspace with empty workspace name
+ workspaceReq = new WorkspaceReq("", newDescription);
+ updateResult = workspaceControllerWrapper.updateWorkspace(workspaceId, workspaceReq);
+ assertFalse(updateResult.isSuccess());
+ assertEquals(SeatunnelErrorEnum.PARAM_CAN_NOT_BE_NULL.getCode(), updateResult.getCode());
+
+ // update workspace with duplicated workspace name
+ String workspaceName2 = "workspace_update2" + uniqueId;
+ createWorkspace(workspaceName2);
+
+ workspaceReq = new WorkspaceReq(workspaceName2, newDescription);
+ updateResult = workspaceControllerWrapper.updateWorkspace(workspaceId, workspaceReq);
+ assertFalse(updateResult.isSuccess());
+ assertEquals(SeatunnelErrorEnum.RESOURCE_ALREADY_EXISTS.getCode(), updateResult.getCode());
+ }
+
+ private static Long createWorkspace(String workspaceName) {
+ Result<Long> result = workspaceControllerWrapper.createWorkspace(workspaceName);
+ assertTrue(result.isSuccess());
+ assertTrue(result.getData() > 0);
+ return result.getData();
+ }
+
+ @Test
+ public void testDeleteWorkspace() {
+ String workspaceName = "workspace_delete" + uniqueId;
+ Long workspaceId = createWorkspace(workspaceName);
+ Result<Boolean> result = workspaceControllerWrapper.deleteWorkspace(workspaceId);
+ assertTrue(result.isSuccess());
+ assertTrue(result.getData());
+ }
+
+ @Test
+ public void testListWorkspaces() {
+ String workspaceName = "workspace_list_1" + uniqueId;
+ Long workspaceId1 = createWorkspace(workspaceName);
+ String workspaceName2 = "workspace_list_2" + uniqueId;
+ Long workspaceId2 = createWorkspace(workspaceName2);
+
+ Result<Workspace> workspacesById =
+ workspaceControllerWrapper.getWorkspacesById(workspaceId1);
+ assertTrue(workspacesById.isSuccess());
+ assertNotNull(workspacesById.getData());
+ assertEquals(workspacesById.getData().getWorkspaceName(), workspaceName);
+
+ Result<List<Workspace>> allWorkspaces = workspaceControllerWrapper.getAllWorkspaces();
+ assertTrue(allWorkspaces.isSuccess());
+ assertTrue(allWorkspaces.getData().size() > 2 || allWorkspaces.getData().size() == 2);
+
+ List<Long> workspaceIds =
+ allWorkspaces.getData().stream().map(Workspace::getId).collect(Collectors.toList());
+ assertTrue(workspaceIds.contains(workspaceId1));
+ assertTrue(workspaceIds.contains(workspaceId2));
+
+ // get workspace which do not exist, assuming 123456789 does not exist
+ workspacesById = workspaceControllerWrapper.getWorkspacesById(123456789L);
+ assertFalse(workspacesById.isSuccess());
+ assertEquals(SeatunnelErrorEnum.RESOURCE_NOT_FOUND.getCode(), workspacesById.getCode());
+ }
+
+ private Workspace getWorkspace(Long workspaceId) {
+ Result<Workspace> workspacesById =
+ workspaceControllerWrapper.getWorkspacesById(workspaceId);
+ assertTrue(workspacesById.isSuccess());
+ assertNotNull(workspacesById.getData());
+ return workspacesById.getData();
+ }
+
+ @AfterAll
+ public static void tearDown() {
+ seaTunnelWebCluster.stop();
+ }
+}
diff --git a/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/test/WorkspaceTest.java b/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/test/WorkspaceTest.java
new file mode 100644
index 0000000..addf20c
--- /dev/null
+++ b/seatunnel-web-it/src/test/java/org/apache/seatunnel/app/test/WorkspaceTest.java
@@ -0,0 +1,202 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+
+package org.apache.seatunnel.app.test;
+
+import org.apache.seatunnel.app.common.Result;
+import org.apache.seatunnel.app.common.SeaTunnelWebCluster;
+import org.apache.seatunnel.app.controller.JobDefinitionControllerWrapper;
+import org.apache.seatunnel.app.controller.JobExecutorControllerWrapper;
+import org.apache.seatunnel.app.controller.SeatunnelDatasourceControllerWrapper;
+import org.apache.seatunnel.app.controller.TaskInstanceControllerWrapper;
+import org.apache.seatunnel.app.controller.UserControllerWrapper;
+import org.apache.seatunnel.app.controller.WorkspaceControllerWrapper;
+import org.apache.seatunnel.app.domain.dto.job.SeaTunnelJobInstanceDto;
+import org.apache.seatunnel.app.domain.request.connector.BusinessMode;
+import org.apache.seatunnel.app.domain.request.datasource.DatasourceReq;
+import org.apache.seatunnel.app.domain.request.job.JobReq;
+import org.apache.seatunnel.app.domain.request.user.AddUserReq;
+import org.apache.seatunnel.app.domain.request.user.UserLoginReq;
+import org.apache.seatunnel.app.domain.response.user.AddUserRes;
+import org.apache.seatunnel.app.domain.response.user.UserSimpleInfoRes;
+import org.apache.seatunnel.app.utils.JobTestingUtils;
+
+import org.junit.jupiter.api.AfterAll;
+import org.junit.jupiter.api.AfterEach;
+import org.junit.jupiter.api.BeforeAll;
+import org.junit.jupiter.api.Test;
+
+import java.util.List;
+
+import static org.junit.jupiter.api.Assertions.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertFalse;
+import static org.junit.jupiter.api.Assertions.assertTrue;
+
+public class WorkspaceTest {
+ private static final SeaTunnelWebCluster seaTunnelWebCluster = new SeaTunnelWebCluster();
+ private static final String uniqueId = "_" + System.currentTimeMillis();
+ private static SeatunnelDatasourceControllerWrapper datasourceControllerWrapper;
+ private static WorkspaceControllerWrapper workspaceControllerWrapper;
+ private static UserControllerWrapper userControllerWrapper;
+ private static JobDefinitionControllerWrapper jobDefinitionControllerWrapper;
+ private static JobExecutorControllerWrapper jobExecutorControllerWrapper;
+ private static TaskInstanceControllerWrapper taskInstanceControllerWrapper;
+
+ @BeforeAll
+ public static void setUp() {
+ seaTunnelWebCluster.start();
+ datasourceControllerWrapper = new SeatunnelDatasourceControllerWrapper();
+ workspaceControllerWrapper = new WorkspaceControllerWrapper();
+ userControllerWrapper = new UserControllerWrapper();
+ jobDefinitionControllerWrapper = new JobDefinitionControllerWrapper();
+ jobExecutorControllerWrapper = new JobExecutorControllerWrapper();
+ taskInstanceControllerWrapper = new TaskInstanceControllerWrapper();
+ }
+
+ @Test
+ public void testDatasourceIsolation_WithinWorkspace() {
+ String user1 = "user_namespace_11" + uniqueId;
+ String user2 = "user_namespace_12" + uniqueId;
+ String pass = "somePassword";
+ String workspace1 = "workspace_namespace_11" + uniqueId;
+ String workspace2 = "workspace_namespace_12" + uniqueId;
+
+ createWorkspaceAndUser(workspace1, user1, pass);
+ createWorkspaceAndUser(workspace2, user2, pass);
+
+ login(new UserLoginReq(user1, pass, workspace1));
+ String datasourceName = "datasource_namespace_11" + uniqueId;
+ datasourceControllerWrapper.createFakeSourceDatasource(datasourceName);
+
+ // logout and login with another user with another namespace, should be able to create
+ // datasource with same name
+ userControllerWrapper.logout();
+ login(new UserLoginReq(user2, pass, workspace2));
+ DatasourceReq req = datasourceControllerWrapper.getFakeSourceDatasourceReq(datasourceName);
+ Result<String> dataSourceCreationResult = datasourceControllerWrapper.createDatasource(req);
+ assertTrue(dataSourceCreationResult.isSuccess());
+
+ // if create datasource with same name in same workspace, should fail
+ DatasourceReq req2 = datasourceControllerWrapper.getFakeSourceDatasourceReq(datasourceName);
+ Result<String> dataSourceCreationResult2 =
+ datasourceControllerWrapper.createDatasource(req2);
+ assertFalse(dataSourceCreationResult2.isSuccess());
+ }
+
+ @Test
+ public void testJobDefinitionIsolation_WithinWorkspace() {
+ String user1 = "user_workspace_21" + uniqueId;
+ String user2 = "user_workspace_22" + uniqueId;
+ String pass = "somePassword";
+ String workspace1 = "workspace_21" + uniqueId;
+ String workspace2 = "workspace_22" + uniqueId;
+
+ createWorkspaceAndUser(workspace1, user1, pass);
+ createWorkspaceAndUser(workspace2, user2, pass);
+
+ login(new UserLoginReq(user1, pass, workspace1));
+ String jobName = "job_definition_namespace_21" + uniqueId;
+ JobReq jobReq = createJobReq(jobName);
+ Result<Long> jobDefinition = jobDefinitionControllerWrapper.createJobDefinition(jobReq);
+ assertTrue(jobDefinition.isSuccess());
+
+ // logout and login with another user with another workspace, should be able to create
+ // job definition with same name
+ userControllerWrapper.logout();
+ login(new UserLoginReq(user2, pass, workspace2));
+ jobDefinition = jobDefinitionControllerWrapper.createJobDefinition(jobReq);
+ assertTrue(jobDefinition.isSuccess(), jobDefinition.getMsg());
+
+ // if create job definition with same name in same workspace, should fail
+ jobDefinition = jobDefinitionControllerWrapper.createJobDefinition(jobReq);
+ assertFalse(jobDefinition.isSuccess());
+ }
+
+ @Test
+ public void testJobExecutionIsolation_WithinWorkspace() {
+ String user1 = "user_workspace_31" + uniqueId;
+ String user2 = "user_workspace_32" + uniqueId;
+ String pass = "somePassword";
+ String workspace1 = "workspace_31" + uniqueId;
+ String workspace2 = "workspace_32" + uniqueId;
+
+ createWorkspaceAndUser(workspace1, user1, pass);
+ createWorkspaceAndUser(workspace2, user2, pass);
+
+ login(new UserLoginReq(user1, pass, workspace1));
+ String jobName = "execJob_namespace_31" + uniqueId;
+ long jobVersionId_1 = JobTestingUtils.createJob(jobName);
+ Result<Long> executionResult = jobExecutorControllerWrapper.jobExecutor(jobVersionId_1);
+ assertTrue(executionResult.isSuccess());
+ JobTestingUtils.waitForJobCompletion(executionResult.getData());
+ List<SeaTunnelJobInstanceDto> taskInstanceList =
+ taskInstanceControllerWrapper.getTaskInstanceList(jobName);
+ assertEquals(1, taskInstanceList.size());
+
+ // logout and login with another user with another workspace, should be able to create
+ // job execution with same name
+ userControllerWrapper.logout();
+ login(new UserLoginReq(user2, pass, workspace2));
+ long jobVersionId_2 = JobTestingUtils.createJob(jobName);
+ executionResult = jobExecutorControllerWrapper.jobExecutor(jobVersionId_2);
+ assertTrue(executionResult.isSuccess());
+ JobTestingUtils.waitForJobCompletion(executionResult.getData());
+
+ taskInstanceList = taskInstanceControllerWrapper.getTaskInstanceList(jobName);
+ // should be 1 because second time we have run in separate name space
+ assertEquals(1, taskInstanceList.size());
+ }
+
+ private void createWorkspaceAndUser(String workspaceName, String username, String password) {
+ workspaceControllerWrapper.createWorkspaceAndVerify(workspaceName);
+ Result<AddUserRes> result =
+ userControllerWrapper.addUser(getAddUserReq(username, password));
+ assertTrue(result.isSuccess());
+ }
+
+ private JobReq createJobReq(String jobName) {
+ JobReq jobReq = new JobReq();
+ jobReq.setName(jobName);
+ jobReq.setDescription(jobName + " description");
+ jobReq.setJobType(BusinessMode.DATA_INTEGRATION);
+ return jobReq;
+ }
+
+ private static void login(UserLoginReq userLoginReq) {
+ Result<UserSimpleInfoRes> login = userControllerWrapper.login(userLoginReq, null, true);
+ assertTrue(login.isSuccess(), login.getMsg());
+ }
+
+ private AddUserReq getAddUserReq(String user, String pass) {
+ AddUserReq addUserReq = new AddUserReq();
+ addUserReq.setUsername(user);
+ addUserReq.setPassword(pass);
+ addUserReq.setStatus((byte) 0);
+ addUserReq.setType((byte) 0);
+ return addUserReq;
+ }
+
+ @AfterEach
+ public void cleanup() {
+ userControllerWrapper.logout();
+ }
+
+ @AfterAll
+ public static void tearDown() {
+ seaTunnelWebCluster.stop();
+ }
+}