diff --git a/orion-ops-framework/orion-ops-spring-boot-starter-biz-operator-log/src/main/java/com/orion/ops/framework/biz/operator/log/core/constant/OperatorLogKeys.java b/orion-ops-framework/orion-ops-framework-common/src/main/java/com/orion/ops/framework/common/constant/ExtraFieldConst.java similarity index 61% rename from orion-ops-framework/orion-ops-spring-boot-starter-biz-operator-log/src/main/java/com/orion/ops/framework/biz/operator/log/core/constant/OperatorLogKeys.java rename to orion-ops-framework/orion-ops-framework-common/src/main/java/com/orion/ops/framework/common/constant/ExtraFieldConst.java index bba01da4..cc1e40d3 100644 --- a/orion-ops-framework/orion-ops-spring-boot-starter-biz-operator-log/src/main/java/com/orion/ops/framework/biz/operator/log/core/constant/OperatorLogKeys.java +++ b/orion-ops-framework/orion-ops-framework-common/src/main/java/com/orion/ops/framework/common/constant/ExtraFieldConst.java @@ -1,15 +1,17 @@ -package com.orion.ops.framework.biz.operator.log.core.constant; - -import com.orion.ops.framework.common.constant.FieldConst; +package com.orion.ops.framework.common.constant; /** - * 操作日志常量 + * 额外字段常量 * * @author Jiahang Li * @version 1.0.0 - * @since 2023/10/10 19:00 + * @since 2023/12/28 18:34 */ -public interface OperatorLogKeys extends FieldConst { +public interface ExtraFieldConst extends FieldConst { + + String USER_ID = "userId"; + + String TRACE_ID = "traceId"; String GROUP_NAME = "groupName"; diff --git a/orion-ops-framework/orion-ops-framework-common/src/main/java/com/orion/ops/framework/common/entity/RequestIdentity.java b/orion-ops-framework/orion-ops-framework-common/src/main/java/com/orion/ops/framework/common/entity/RequestIdentity.java index 57983f67..82848f0f 100644 --- a/orion-ops-framework/orion-ops-framework-common/src/main/java/com/orion/ops/framework/common/entity/RequestIdentity.java +++ b/orion-ops-framework/orion-ops-framework-common/src/main/java/com/orion/ops/framework/common/entity/RequestIdentity.java @@ -3,7 +3,7 @@ package com.orion.ops.framework.common.entity; import java.io.Serializable; /** - * 请求身份 + * 请求留痕 * * @author Jiahang Li * @version 1.0.0 diff --git a/orion-ops-framework/orion-ops-framework-common/src/main/java/com/orion/ops/framework/common/utils/Requests.java b/orion-ops-framework/orion-ops-framework-common/src/main/java/com/orion/ops/framework/common/utils/Requests.java index 778f6877..4442fa0e 100644 --- a/orion-ops-framework/orion-ops-framework-common/src/main/java/com/orion/ops/framework/common/utils/Requests.java +++ b/orion-ops-framework/orion-ops-framework-common/src/main/java/com/orion/ops/framework/common/utils/Requests.java @@ -20,7 +20,7 @@ public class Requests { } /** - * 填充请求身份信息 + * 填充请求留痕信息 * * @param identity identity */ diff --git a/orion-ops-framework/orion-ops-spring-boot-starter-biz-operator-log/src/main/java/com/orion/ops/framework/biz/operator/log/core/aspect/OperatorLogAspect.java b/orion-ops-framework/orion-ops-spring-boot-starter-biz-operator-log/src/main/java/com/orion/ops/framework/biz/operator/log/core/aspect/OperatorLogAspect.java index b309da88..b07e061f 100644 --- a/orion-ops-framework/orion-ops-spring-boot-starter-biz-operator-log/src/main/java/com/orion/ops/framework/biz/operator/log/core/aspect/OperatorLogAspect.java +++ b/orion-ops-framework/orion-ops-spring-boot-starter-biz-operator-log/src/main/java/com/orion/ops/framework/biz/operator/log/core/aspect/OperatorLogAspect.java @@ -242,7 +242,7 @@ public class OperatorLogAspect { } /** - * 填充请求信息 + * 填充请求留痕信息 * * @param model model */ diff --git a/orion-ops-framework/orion-ops-spring-boot-starter-biz-operator-log/src/main/java/com/orion/ops/framework/biz/operator/log/core/uitls/OperatorLogs.java b/orion-ops-framework/orion-ops-spring-boot-starter-biz-operator-log/src/main/java/com/orion/ops/framework/biz/operator/log/core/uitls/OperatorLogs.java index 82ec15b5..c0c5e003 100644 --- a/orion-ops-framework/orion-ops-spring-boot-starter-biz-operator-log/src/main/java/com/orion/ops/framework/biz/operator/log/core/uitls/OperatorLogs.java +++ b/orion-ops-framework/orion-ops-spring-boot-starter-biz-operator-log/src/main/java/com/orion/ops/framework/biz/operator/log/core/uitls/OperatorLogs.java @@ -2,7 +2,7 @@ package com.orion.ops.framework.biz.operator.log.core.uitls; import com.alibaba.fastjson.JSON; import com.alibaba.fastjson.serializer.SerializeFilter; -import com.orion.ops.framework.biz.operator.log.core.constant.OperatorLogKeys; +import com.orion.ops.framework.common.constant.ExtraFieldConst; import com.orion.ops.framework.common.security.LoginUser; import java.util.HashMap; @@ -15,7 +15,7 @@ import java.util.Map; * @version 1.0.0 * @since 2023/10/10 11:32 */ -public class OperatorLogs implements OperatorLogKeys { +public class OperatorLogs implements ExtraFieldConst { private static final String UN_SAVE_FLAG = "__un__save__"; diff --git a/orion-ops-framework/orion-ops-spring-boot-starter-websocket/src/main/java/com/orion/ops/framework/websocket/config/OrionWebSocketAutoConfiguration.java b/orion-ops-framework/orion-ops-spring-boot-starter-websocket/src/main/java/com/orion/ops/framework/websocket/config/OrionWebSocketAutoConfiguration.java index b9a709cb..7d5aa428 100644 --- a/orion-ops-framework/orion-ops-spring-boot-starter-websocket/src/main/java/com/orion/ops/framework/websocket/config/OrionWebSocketAutoConfiguration.java +++ b/orion-ops-framework/orion-ops-spring-boot-starter-websocket/src/main/java/com/orion/ops/framework/websocket/config/OrionWebSocketAutoConfiguration.java @@ -1,13 +1,11 @@ package com.orion.ops.framework.websocket.config; import com.orion.ops.framework.common.constant.AutoConfigureOrderConst; -import com.orion.ops.framework.websocket.core.interceptor.UserHandshakeInterceptor; import org.springframework.boot.autoconfigure.AutoConfiguration; import org.springframework.boot.autoconfigure.AutoConfigureOrder; import org.springframework.boot.context.properties.EnableConfigurationProperties; import org.springframework.context.annotation.Bean; import org.springframework.web.socket.config.annotation.EnableWebSocket; -import org.springframework.web.socket.server.HandshakeInterceptor; import org.springframework.web.socket.server.standard.ServletServerContainerFactoryBean; /** @@ -35,12 +33,4 @@ public class OrionWebSocketAutoConfiguration { return factory; } - /** - * @return 用户认证拦截器 按需注入 - */ - @Bean - public HandshakeInterceptor userHandshakeInterceptor() { - return new UserHandshakeInterceptor(); - } - } diff --git a/orion-ops-framework/orion-ops-spring-boot-starter-websocket/src/main/java/com/orion/ops/framework/websocket/core/constant/WsAttr.java b/orion-ops-framework/orion-ops-spring-boot-starter-websocket/src/main/java/com/orion/ops/framework/websocket/core/constant/WsAttr.java deleted file mode 100644 index 8dd48c81..00000000 --- a/orion-ops-framework/orion-ops-spring-boot-starter-websocket/src/main/java/com/orion/ops/framework/websocket/core/constant/WsAttr.java +++ /dev/null @@ -1,22 +0,0 @@ -package com.orion.ops.framework.websocket.core.constant; - -/** - * websocket 属性 - * - * @author Jiahang Li - * @version 1.0.0 - * @since 2023/6/25 20:25 - */ -public interface WsAttr { - - String USER = "user"; - - String UID = "uid"; - - String TOKEN = "token"; - - String READONLY = "readonly"; - - String CONNECTED = "connected"; - -} diff --git a/orion-ops-framework/orion-ops-spring-boot-starter-websocket/src/main/java/com/orion/ops/framework/websocket/core/constant/WsProtocol.java b/orion-ops-framework/orion-ops-spring-boot-starter-websocket/src/main/java/com/orion/ops/framework/websocket/core/constant/WsProtocol.java deleted file mode 100644 index e8b5efdb..00000000 --- a/orion-ops-framework/orion-ops-spring-boot-starter-websocket/src/main/java/com/orion/ops/framework/websocket/core/constant/WsProtocol.java +++ /dev/null @@ -1,79 +0,0 @@ -package com.orion.ops.framework.websocket.core.constant; - -import com.orion.lang.utils.Exceptions; -import com.orion.lang.utils.Strings; -import com.orion.lang.utils.Valid; -import lombok.AllArgsConstructor; - -import java.io.ByteArrayOutputStream; -import java.io.IOException; - -/** - * ws服务端响应常量 - * - * @author Jiahang Li - * @version 1.0.0 - * @since 2021/4/16 21:48 - */ -@AllArgsConstructor -public enum WsProtocol { - - /** - * 正常返回 - */ - OK("0"), - - /** - * 连接成功 - */ - CONNECTED("1"), - - /** - * ping - */ - PING("2"), - - /** - * pong - */ - PONG("3"), - - /** - * 未知操作 - */ - ERROR("4"), - - ; - - private final String code; - - /** - * 分隔符 - */ - public static final String SYMBOL = "|"; - - public byte[] get() { - return Strings.bytes(code); - } - - public byte[] msg(String body) { - Valid.notNull(body); - return this.msg(Strings.bytes(body)); - } - - public byte[] msg(byte[] body) { - return this.msg(body, 0, body.length); - } - - public byte[] msg(byte[] body, int offset, int len) { - Valid.notNull(body); - try (ByteArrayOutputStream o = new ByteArrayOutputStream()) { - o.write(Strings.bytes(code + SYMBOL)); - o.write(body, offset, len); - return o.toByteArray(); - } catch (IOException e) { - throw Exceptions.ioRuntime(e); - } - } - -} diff --git a/orion-ops-framework/orion-ops-spring-boot-starter-websocket/src/main/java/com/orion/ops/framework/websocket/core/interceptor/UserHandshakeInterceptor.java b/orion-ops-framework/orion-ops-spring-boot-starter-websocket/src/main/java/com/orion/ops/framework/websocket/core/interceptor/UserHandshakeInterceptor.java deleted file mode 100644 index 76af99ef..00000000 --- a/orion-ops-framework/orion-ops-spring-boot-starter-websocket/src/main/java/com/orion/ops/framework/websocket/core/interceptor/UserHandshakeInterceptor.java +++ /dev/null @@ -1,41 +0,0 @@ -package com.orion.ops.framework.websocket.core.interceptor; - -import com.orion.ops.framework.common.security.SecurityHolder; -import com.orion.ops.framework.websocket.core.constant.WsAttr; -import org.springframework.http.server.ServerHttpRequest; -import org.springframework.http.server.ServerHttpResponse; -import org.springframework.web.socket.WebSocketHandler; -import org.springframework.web.socket.server.HandshakeInterceptor; - -import javax.annotation.Resource; -import java.util.Map; - -/** - * 用户拦截器 - * - * @author Jiahang Li - * @version 1.0.0 - * @since 2023/6/25 20:16 - */ -public class UserHandshakeInterceptor implements HandshakeInterceptor { - - @Resource - private SecurityHolder securityHolder; - - @Override - public boolean beforeHandshake(ServerHttpRequest request, ServerHttpResponse response, WebSocketHandler wsHandler, Map attributes) { - // TODO TEST - attributes.put(WsAttr.USER, securityHolder.getLoginUserId()); - // if (user == null){ - // return false; - // response.setStatusCode(HttpStatus.MULTI_STATUS); - // } - // HttpSessionHandshakeInterceptor - return true; - } - - @Override - public void afterHandshake(ServerHttpRequest request, ServerHttpResponse response, WebSocketHandler wsHandler, Exception exception) { - } - -} diff --git a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/config/AssetWebSocketConfiguration.java b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/config/AssetWebSocketConfiguration.java new file mode 100644 index 00000000..29b8a79b --- /dev/null +++ b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/config/AssetWebSocketConfiguration.java @@ -0,0 +1,39 @@ +package com.orion.ops.module.asset.config; + +import com.orion.ops.module.asset.handler.host.terminal.TerminalDispatchHandler; +import com.orion.ops.module.asset.interceptor.TerminalInterceptor; +import org.springframework.beans.factory.annotation.Value; +import org.springframework.context.annotation.Configuration; +import org.springframework.web.socket.config.annotation.WebSocketConfigurer; +import org.springframework.web.socket.config.annotation.WebSocketHandlerRegistry; + +import javax.annotation.Resource; + +/** + * 资产模块 websocket 配置 + * + * @author Jiahang Li + * @version 1.0.0 + * @since 2023/12/28 11:39 + */ +@Configuration +public class AssetWebSocketConfiguration implements WebSocketConfigurer { + + @Value("${orion.websocket.prefix}") + private String prefix; + + @Resource + private TerminalInterceptor terminalInterceptor; + + @Resource + private TerminalDispatchHandler terminalDispatchHandler; + + @Override + public void registerWebSocketHandlers(WebSocketHandlerRegistry registry) { + // 终端 + registry.addHandler(terminalDispatchHandler, prefix + "/host/terminal/{token}") + .addInterceptors(terminalInterceptor) + .setAllowedOrigins("*"); + } + +} diff --git a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/controller/HostTerminalController.http b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/controller/HostTerminalController.http index 434d9f89..8b3b3399 100644 --- a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/controller/HostTerminalController.http +++ b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/controller/HostTerminalController.http @@ -1,11 +1,6 @@ ### 获取主机终端连接 token -POST {{baseUrl}}/asset/host-terminal/access -Content-Type: application/json +GET {{baseUrl}}/asset/host-terminal/access Authorization: {{token}} -{ - "hostId": 1 -} - ### diff --git a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/controller/HostTerminalController.java b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/controller/HostTerminalController.java index fd1e971b..9ea09182 100644 --- a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/controller/HostTerminalController.java +++ b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/controller/HostTerminalController.java @@ -1,18 +1,14 @@ package com.orion.ops.module.asset.controller; -import com.orion.ops.framework.biz.operator.log.core.annotation.OperatorLog; import com.orion.ops.framework.security.core.utils.SecurityUtils; import com.orion.ops.framework.web.core.annotation.RestWrapper; -import com.orion.ops.module.asset.define.operator.HostTerminalOperatorType; -import com.orion.ops.module.asset.entity.request.host.HostTerminalConnectRequest; import com.orion.ops.module.asset.service.HostTerminalService; import io.swagger.v3.oas.annotations.Operation; import io.swagger.v3.oas.annotations.tags.Tag; import lombok.extern.slf4j.Slf4j; import org.springframework.security.access.prepost.PreAuthorize; import org.springframework.validation.annotation.Validated; -import org.springframework.web.bind.annotation.PostMapping; -import org.springframework.web.bind.annotation.RequestBody; +import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RestController; @@ -37,12 +33,11 @@ public class HostTerminalController { @Resource private HostTerminalService hostTerminalService; - @OperatorLog(HostTerminalOperatorType.ACCESS) - @PostMapping("/access") - @Operation(summary = "获取主机终端连接 token") + @GetMapping("/access") + @Operation(summary = "获取主机终端 accessToken") @PreAuthorize("@ss.hasPermission('asset:host-terminal:access')") - public String getHostAccessToken(@Validated @RequestBody HostTerminalConnectRequest request) { - return hostTerminalService.getHostAccessToken(request.getHostId(), SecurityUtils.getLoginUserId()); + public String getHostTerminalAccessToken() { + return hostTerminalService.getHostTerminalAccessToken(SecurityUtils.getLoginUserId()); } } diff --git a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/convert/HostConnectLogConvert.java b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/convert/HostConnectLogConvert.java index 66760df4..fa1cbc2d 100644 --- a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/convert/HostConnectLogConvert.java +++ b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/convert/HostConnectLogConvert.java @@ -1,7 +1,7 @@ package com.orion.ops.module.asset.convert; import com.orion.ops.module.asset.entity.domain.HostConnectLogDO; -import com.orion.ops.module.asset.entity.dto.HostSshConnectDTO; +import com.orion.ops.module.asset.entity.dto.HostTerminalConnectDTO; import com.orion.ops.module.asset.entity.request.host.HostConnectLogCreateRequest; import com.orion.ops.module.asset.entity.request.host.HostConnectLogQueryRequest; import com.orion.ops.module.asset.entity.vo.HostConnectLogVO; @@ -28,7 +28,7 @@ public interface HostConnectLogConvert { HostConnectLogVO to(HostConnectLogDO domain); - HostConnectLogCreateRequest to(HostSshConnectDTO dto); + HostConnectLogCreateRequest to(HostTerminalConnectDTO dto); List to(List list); diff --git a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/define/cache/HostTerminalCacheKeyDefine.java b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/define/cache/HostTerminalCacheKeyDefine.java index e0ec2389..19cbb0ac 100644 --- a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/define/cache/HostTerminalCacheKeyDefine.java +++ b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/define/cache/HostTerminalCacheKeyDefine.java @@ -3,7 +3,7 @@ package com.orion.ops.module.asset.define.cache; import com.orion.lang.define.cache.key.CacheKeyBuilder; import com.orion.lang.define.cache.key.CacheKeyDefine; import com.orion.lang.define.cache.key.struct.RedisCacheStruct; -import com.orion.ops.module.asset.entity.dto.HostSshConnectDTO; +import com.orion.ops.module.asset.entity.dto.HostTerminalAccessDTO; import java.util.concurrent.TimeUnit; @@ -16,10 +16,10 @@ import java.util.concurrent.TimeUnit; */ public interface HostTerminalCacheKeyDefine { - CacheKeyDefine HOST_TERMINAL_CONNECT = new CacheKeyBuilder() - .key("host:terminal:connect:{}") - .desc("主机终端连接信息 ${token}") - .type(HostSshConnectDTO.class) + CacheKeyDefine HOST_TERMINAL_ACCESS = new CacheKeyBuilder() + .key("host:terminal:access:{}") + .desc("主机终端访问token ${token}") + .type(HostTerminalAccessDTO.class) .struct(RedisCacheStruct.STRING) .timeout(3, TimeUnit.MINUTES) .build(); diff --git a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/define/operator/HostTerminalOperatorType.java b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/define/operator/HostTerminalOperatorType.java index 47a286d5..802d863a 100644 --- a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/define/operator/HostTerminalOperatorType.java +++ b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/define/operator/HostTerminalOperatorType.java @@ -16,12 +16,12 @@ import static com.orion.ops.framework.biz.operator.log.core.enums.OperatorRiskLe @Module("asset:host-terminal") public class HostTerminalOperatorType extends InitializingOperatorTypes { - public static final String ACCESS = "host-terminal:access"; + public static final String CONNECT = "host-terminal:connect"; @Override public OperatorType[] types() { return new OperatorType[]{ - new OperatorType(L, ACCESS, "连接主机终端 ${hostName}"), + new OperatorType(L, CONNECT, "连接主机终端 ${hostName}"), }; } diff --git a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/entity/dto/HostTerminalAccessDTO.java b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/entity/dto/HostTerminalAccessDTO.java new file mode 100644 index 00000000..50767e31 --- /dev/null +++ b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/entity/dto/HostTerminalAccessDTO.java @@ -0,0 +1,31 @@ +package com.orion.ops.module.asset.entity.dto; + +import com.orion.ops.framework.desensitize.core.annotation.DesensitizeObject; +import io.swagger.v3.oas.annotations.media.Schema; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +/** + * 主机终端访问参数 + * + * @author Jiahang Li + * @version 1.0.0 + * @since 2023/12/26 15:47 + */ +@Data +@Builder +@NoArgsConstructor +@AllArgsConstructor +@DesensitizeObject +@Schema(name = "HostTerminalAccessDTO", description = "主机终端访问参数") +public class HostTerminalAccessDTO { + + @Schema(description = "userId") + private Long userId; + + @Schema(description = "token") + private String token; + +} diff --git a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/entity/dto/HostSshConnectDTO.java b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/entity/dto/HostTerminalConnectDTO.java similarity index 91% rename from orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/entity/dto/HostSshConnectDTO.java rename to orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/entity/dto/HostTerminalConnectDTO.java index ffc06851..c0211fc6 100644 --- a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/entity/dto/HostSshConnectDTO.java +++ b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/entity/dto/HostTerminalConnectDTO.java @@ -9,7 +9,7 @@ import lombok.Data; import lombok.NoArgsConstructor; /** - * 主机连接参数 + * 主机终端连接参数 * * @author Jiahang Li * @version 1.0.0 @@ -20,8 +20,8 @@ import lombok.NoArgsConstructor; @NoArgsConstructor @AllArgsConstructor @DesensitizeObject -@Schema(name = "HostSshConnectDTO", description = "主机连接参数") -public class HostSshConnectDTO { +@Schema(name = "HostTerminalConnectDTO", description = "主机终端连接参数") +public class HostTerminalConnectDTO { @Schema(description = "token") private String token; diff --git a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/entity/request/host/HostTerminalConnectRequest.java b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/entity/request/host/HostTerminalConnectRequest.java deleted file mode 100644 index 52dc0a99..00000000 --- a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/entity/request/host/HostTerminalConnectRequest.java +++ /dev/null @@ -1,30 +0,0 @@ -package com.orion.ops.module.asset.entity.request.host; - -import io.swagger.v3.oas.annotations.media.Schema; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -import javax.validation.constraints.NotNull; -import java.io.Serializable; - -/** - * 主机终端连接 请求对象 - * - * @author Jiahang Li - * @version 1.0.0 - * @since 2023-9-20 11:55 - */ -@Data -@Builder -@NoArgsConstructor -@AllArgsConstructor -@Schema(name = "HostTerminalConnectRequest", description = "主机终端连接 请求对象") -public class HostTerminalConnectRequest implements Serializable { - - @NotNull - @Schema(description = "hostId") - private Long hostId; - -} diff --git a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/handler/host/terminal/TerminalDispatchHandler.java b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/handler/host/terminal/TerminalDispatchHandler.java new file mode 100644 index 00000000..e53e1670 --- /dev/null +++ b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/handler/host/terminal/TerminalDispatchHandler.java @@ -0,0 +1,52 @@ +package com.orion.ops.module.asset.handler.host.terminal; + +import com.orion.ops.framework.biz.operator.log.core.service.OperatorLogFrameworkService; +import lombok.extern.slf4j.Slf4j; +import org.springframework.stereotype.Component; +import org.springframework.web.socket.CloseStatus; +import org.springframework.web.socket.WebSocketHandler; +import org.springframework.web.socket.WebSocketMessage; +import org.springframework.web.socket.WebSocketSession; + +import javax.annotation.Resource; + +/** + * 终端处理器 + * + * @author Jiahang Li + * @version 1.0.0 + * @since 2023/12/28 14:33 + */ +@Slf4j +@Component +public class TerminalDispatchHandler implements WebSocketHandler { + + @Resource + private OperatorLogFrameworkService operatorLogFrameworkService; + + @Override + public void afterConnectionEstablished(WebSocketSession session) throws Exception { + log.info("afterConnectionEstablished"); + } + + @Override + public void handleMessage(WebSocketSession session, WebSocketMessage message) throws Exception { + log.info("handleMessage"); + } + + @Override + public void handleTransportError(WebSocketSession session, Throwable exception) throws Exception { + log.info("handleTransportError"); + } + + @Override + public void afterConnectionClosed(WebSocketSession session, CloseStatus closeStatus) throws Exception { + log.info("afterConnectionClosed"); + } + + @Override + public boolean supportsPartialMessages() { + return false; + } + +} diff --git a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/interceptor/TerminalInterceptor.java b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/interceptor/TerminalInterceptor.java index 5ee5984f..5ab567b4 100644 --- a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/interceptor/TerminalInterceptor.java +++ b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/interceptor/TerminalInterceptor.java @@ -1,63 +1,57 @@ package com.orion.ops.module.asset.interceptor; -import com.orion.ops.framework.websocket.core.interceptor.UserHandshakeInterceptor; -import org.springframework.context.annotation.Configuration; +import com.orion.lang.utils.Urls; +import com.orion.ops.framework.biz.operator.log.core.model.OperatorLogModel; +import com.orion.ops.framework.common.constant.ExtraFieldConst; +import com.orion.ops.framework.common.entity.RequestIdentity; +import com.orion.ops.framework.common.utils.Requests; +import com.orion.ops.module.asset.entity.dto.HostTerminalAccessDTO; +import com.orion.ops.module.asset.service.HostTerminalService; +import lombok.extern.slf4j.Slf4j; +import org.springframework.http.server.ServerHttpRequest; +import org.springframework.http.server.ServerHttpResponse; import org.springframework.stereotype.Component; -import org.springframework.web.socket.*; -import org.springframework.web.socket.config.annotation.WebSocketConfigurer; -import org.springframework.web.socket.config.annotation.WebSocketHandlerRegistry; -import org.springframework.web.socket.handler.TextWebSocketHandler; +import org.springframework.web.socket.WebSocketHandler; +import org.springframework.web.socket.server.HandshakeInterceptor; import javax.annotation.Resource; +import java.util.Map; /** + * 终端拦截器 + * * @author Jiahang Li * @version 1.0.0 * @since 2023/12/27 23:53 */ -@Configuration -public class TerminalInterceptor implements WebSocketConfigurer { - - // https://blog.csdn.net/oNew_Lifeo/article/details/130003676 - // https://wstool.js.org/ +@Slf4j +@Component +public class TerminalInterceptor implements HandshakeInterceptor { @Resource - private UserHandshakeInterceptor userHandshakeInterceptor; + private HostTerminalService hostTerminalService; @Override - public void registerWebSocketHandlers(WebSocketHandlerRegistry registry) { - registry.addHandler(new WebSocketHandler1(), "/orion/keep-alive/host/terminal") - .addInterceptors(userHandshakeInterceptor) - .setAllowedOrigins("*"); - System.out.println("123"); - } - - static class WebSocketHandler1 implements WebSocketHandler { - - @Override - public void afterConnectionEstablished(WebSocketSession session) throws Exception { - System.out.println(1); - } - - @Override - public void handleMessage(WebSocketSession session, WebSocketMessage message) throws Exception { - System.out.println(message); - } - - @Override - public void handleTransportError(WebSocketSession session, Throwable exception) throws Exception { - System.out.println(1); - } - - @Override - public void afterConnectionClosed(WebSocketSession session, CloseStatus closeStatus) throws Exception { - System.out.println(1); - } - - @Override - public boolean supportsPartialMessages() { + public boolean beforeHandshake(ServerHttpRequest request, ServerHttpResponse response, WebSocketHandler wsHandler, Map attributes) throws Exception { + // 获取 token + String token = Urls.getUrlSource(request.getURI().getPath()); + log.info("TerminalInterceptor-beforeHandshake start token: {}", token); + // 获取连接数据 + HostTerminalAccessDTO access = hostTerminalService.getAccessInfoByToken(token); + if (access == null) { + log.error("TerminalInterceptor-beforeHandshake absent token: {}", token); return false; } + // 设置参数 + attributes.put(ExtraFieldConst.USER_ID, access.getUserId()); + OperatorLogModel identity = new OperatorLogModel(); + Requests.fillIdentity(identity); + return true; + } + + @Override + public void afterHandshake(ServerHttpRequest request, ServerHttpResponse response, WebSocketHandler wsHandler, Exception exception) { + log.info("afterHandshake"); } } diff --git a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/service/HostTerminalService.java b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/service/HostTerminalService.java index 99f43684..a0afe31d 100644 --- a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/service/HostTerminalService.java +++ b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/service/HostTerminalService.java @@ -1,7 +1,8 @@ package com.orion.ops.module.asset.service; import com.orion.net.host.SessionStore; -import com.orion.ops.module.asset.entity.dto.HostSshConnectDTO; +import com.orion.ops.module.asset.entity.dto.HostTerminalAccessDTO; +import com.orion.ops.module.asset.entity.dto.HostTerminalConnectDTO; /** * 主机终端服务 @@ -13,21 +14,29 @@ import com.orion.ops.module.asset.entity.dto.HostSshConnectDTO; public interface HostTerminalService { /** - * 获取主机终端连接 token + * 获取主机终端访问 accessToken + * + * @param userId userId + * @return session + */ + String getHostTerminalAccessToken(Long userId); + + /** + * 通过 accessToken 获取主机终端访问信息 + * + * @param token token + * @return config + */ + HostTerminalAccessDTO getAccessInfoByToken(String token); + + /** + * 使用用户配置打开获取连接信息 * * @param hostId hostId * @param userId userId * @return session */ - String getHostAccessToken(Long hostId, Long userId); - - /** - * 通过 token 获取主机终端连接信息 - * - * @param token token - * @return config - */ - HostSshConnectDTO getConnectInfoByToken(String token); + HostTerminalConnectDTO getTerminalConnectInfo(Long userId, Long hostId); /** * 使用默认配置打开主机会话 @@ -43,6 +52,6 @@ public interface HostTerminalService { * @param conn conn * @return session */ - SessionStore openSessionStore(HostSshConnectDTO conn); + SessionStore openSessionStore(HostTerminalConnectDTO conn); } diff --git a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/service/impl/HostTerminalServiceImpl.java b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/service/impl/HostTerminalServiceImpl.java index 244f112e..1dfe0c80 100644 --- a/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/service/impl/HostTerminalServiceImpl.java +++ b/orion-ops-module-asset/orion-ops-module-asset-service/src/main/java/com/orion/ops/module/asset/service/impl/HostTerminalServiceImpl.java @@ -6,13 +6,11 @@ import com.orion.lang.utils.Exceptions; import com.orion.lang.utils.Strings; import com.orion.net.host.SessionHolder; import com.orion.net.host.SessionStore; -import com.orion.ops.framework.biz.operator.log.core.uitls.OperatorLogs; import com.orion.ops.framework.common.constant.Const; import com.orion.ops.framework.common.constant.ErrorMessage; import com.orion.ops.framework.common.utils.CryptoUtils; import com.orion.ops.framework.common.utils.Valid; import com.orion.ops.framework.redis.core.utils.RedisStrings; -import com.orion.ops.module.asset.convert.HostConnectLogConvert; import com.orion.ops.module.asset.dao.HostDAO; import com.orion.ops.module.asset.dao.HostIdentityDAO; import com.orion.ops.module.asset.dao.HostKeyDAO; @@ -20,9 +18,12 @@ import com.orion.ops.module.asset.define.cache.HostTerminalCacheKeyDefine; import com.orion.ops.module.asset.entity.domain.HostDO; import com.orion.ops.module.asset.entity.domain.HostIdentityDO; import com.orion.ops.module.asset.entity.domain.HostKeyDO; -import com.orion.ops.module.asset.entity.dto.HostSshConnectDTO; -import com.orion.ops.module.asset.entity.request.host.HostConnectLogCreateRequest; -import com.orion.ops.module.asset.enums.*; +import com.orion.ops.module.asset.entity.dto.HostTerminalAccessDTO; +import com.orion.ops.module.asset.entity.dto.HostTerminalConnectDTO; +import com.orion.ops.module.asset.enums.HostConfigTypeEnum; +import com.orion.ops.module.asset.enums.HostExtraItemEnum; +import com.orion.ops.module.asset.enums.HostExtraSshAuthTypeEnum; +import com.orion.ops.module.asset.enums.HostSshAuthTypeEnum; import com.orion.ops.module.asset.handler.host.config.model.HostSshConfigModel; import com.orion.ops.module.asset.handler.host.extra.model.HostSshExtraModel; import com.orion.ops.module.asset.service.HostConfigService; @@ -79,8 +80,34 @@ public class HostTerminalServiceImpl implements HostTerminalService { private SystemUserApi systemUserApi; @Override - public String getHostAccessToken(Long hostId, Long userId) { - log.info("HostConnectService.getHostAccessToken hostId: {}, userId: {}", hostId, userId); + public String getHostTerminalAccessToken(Long userId) { + log.info("HostConnectService.getHostAccessToken userId: {}", userId); + String token = UUIds.random19(); + HostTerminalAccessDTO access = HostTerminalAccessDTO.builder() + .token(token) + .userId(userId) + .build(); + // 设置缓存 + String key = HostTerminalCacheKeyDefine.HOST_TERMINAL_ACCESS.format(token); + RedisStrings.setJson(key, HostTerminalCacheKeyDefine.HOST_TERMINAL_ACCESS, access); + return token; + } + + @Override + public HostTerminalAccessDTO getAccessInfoByToken(String token) { + // 获取缓存 + String key = HostTerminalCacheKeyDefine.HOST_TERMINAL_ACCESS.format(token); + HostTerminalAccessDTO access = RedisStrings.getJson(key, HostTerminalCacheKeyDefine.HOST_TERMINAL_ACCESS); + // 删除缓存 + if (access != null) { + RedisStrings.delete(key); + } + return access; + } + + @Override + public HostTerminalConnectDTO getTerminalConnectInfo(Long userId, Long hostId) { + log.info("HostConnectService.getTerminalConnectInfo hostId: {}, userId: {}", hostId, userId); // 查询主机 HostDO host = hostDAO.selectById(hostId); Valid.notNull(host, ErrorMessage.HOST_ABSENT); @@ -115,27 +142,11 @@ public class HostTerminalServiceImpl implements HostTerminalService { } } } - String token = UUIds.random32(); // 获取连接配置 - HostSshConnectDTO connect = this.getHostConnectInfo(host, config, extra); + HostTerminalConnectDTO connect = this.getHostConnectInfo(host, config, extra); connect.setUserId(userId); - connect.setToken(token); - // 设置缓存 - String key = HostTerminalCacheKeyDefine.HOST_TERMINAL_CONNECT.format(token); - RedisStrings.setJson(key, HostTerminalCacheKeyDefine.HOST_TERMINAL_CONNECT, connect); - // 记录连接日志 - HostConnectLogCreateRequest log = HostConnectLogConvert.MAPPER.to(connect); - log.setUsername(user.getUsername()); - hostConnectLogService.create(HostConnectTypeEnum.SSH, log); - // 设置日志参数 - OperatorLogs.add(connect); - return token; - } - - @Override - public HostSshConnectDTO getConnectInfoByToken(String token) { - String key = HostTerminalCacheKeyDefine.HOST_TERMINAL_CONNECT.format(token); - return RedisStrings.getJson(key, HostTerminalCacheKeyDefine.HOST_TERMINAL_CONNECT); + connect.setToken(UUIds.random15()); + return connect; } @Override @@ -148,13 +159,13 @@ public class HostTerminalServiceImpl implements HostTerminalService { HostSshConfigModel model = hostConfigService.getHostConfig(hostId, HostConfigTypeEnum.SSH); Valid.notNull(model, ErrorMessage.CONFIG_ABSENT); // 获取配置 - HostSshConnectDTO connect = this.getHostConnectInfo(host, model, null); + HostTerminalConnectDTO connect = this.getHostConnectInfo(host, model, null); // 打开连接 return this.openSessionStore(connect); } @Override - public SessionStore openSessionStore(HostSshConnectDTO conn) { + public SessionStore openSessionStore(HostTerminalConnectDTO conn) { Long hostId = conn.getHostId(); String address = conn.getHostAddress(); String username = conn.getUsername(); @@ -212,9 +223,9 @@ public class HostTerminalServiceImpl implements HostTerminalService { * @param extra extra * @return session */ - private HostSshConnectDTO getHostConnectInfo(HostDO host, - HostSshConfigModel config, - HostSshExtraModel extra) { + private HostTerminalConnectDTO getHostConnectInfo(HostDO host, + HostSshConfigModel config, + HostSshExtraModel extra) { // 获取认证方式 HostSshAuthTypeEnum authType = HostSshAuthTypeEnum.of(config.getAuthType()); HostExtraSshAuthTypeEnum extraAuthType = Optional.ofNullable(extra) @@ -235,7 +246,7 @@ public class HostTerminalServiceImpl implements HostTerminalService { } Long keyId = null; // 填充认证信息 - HostSshConnectDTO conn = new HostSshConnectDTO(); + HostTerminalConnectDTO conn = new HostTerminalConnectDTO(); conn.setHostId(host.getId()); conn.setHostName(host.getName()); conn.setHostAddress(host.getAddress());