Skip to content

Commit

Permalink
pref:研发商店敏感接口签名校验优化 TencentBlueKing#10759
Browse files Browse the repository at this point in the history
  • Loading branch information
carlyin0801 committed Aug 2, 2024
1 parent 983284e commit 312dec1
Show file tree
Hide file tree
Showing 12 changed files with 62 additions and 43 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -119,3 +119,4 @@ const val AUTH_HEADER_DEVOPS_OS_ARCH: String = "X-DEVOPS-OS-ARCH"
const val AUTH_HEADER_DEVOPS_STORE_CODE: String = "X-DEVOPS-STORE-CODE"
const val AUTH_HEADER_DEVOPS_STORE_TYPE: String = "X-DEVOPS-STORE-TYPE"
const val AUTH_HEADER_DEVOPS_STORE_VERSION: String = "X-DEVOPS-STORE-VERSION"
const val AUTH_HEADER_DEVOPS_SIGN_FILE_NAME: String = "X-DEVOPS-SIGN-FILE-NAME"
Original file line number Diff line number Diff line change
Expand Up @@ -163,7 +163,7 @@ const val KEY_BRANCH_TEST_FLAG = "branchTestFlag"
const val KEY_TASK_ATOM = "taskAtom"
const val KEY_ELEMENT_ENABLE = "elementEnable"
const val KEY_SHA_CONTENT = "shaContent"
const val KEY_INSTALLED_PKG_SHA_CONTENT = "installedPkgShaContent"
const val KEY_FILE_SHA_CONTENT = "fileShaContent"

const val BK_BUILD_ENV_START_FAILED = "bkBuildEnvStartFailed" // 构建环境启动失败
const val BK_START_PULL_IMAGE = "bkStartPullImage" // 开始拉取镜像,镜像名称:
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@ import com.tencent.devops.common.api.auth.AUTH_HEADER_DEVOPS_BUILD_ID
import com.tencent.devops.common.api.auth.AUTH_HEADER_DEVOPS_OS_ARCH
import com.tencent.devops.common.api.auth.AUTH_HEADER_DEVOPS_OS_NAME
import com.tencent.devops.common.api.auth.AUTH_HEADER_DEVOPS_SHA_CONTENT
import com.tencent.devops.common.api.auth.AUTH_HEADER_DEVOPS_SIGN_FILE_NAME
import com.tencent.devops.common.api.auth.AUTH_HEADER_DEVOPS_STORE_CODE
import com.tencent.devops.common.api.auth.AUTH_HEADER_DEVOPS_STORE_TYPE
import com.tencent.devops.common.api.auth.AUTH_HEADER_DEVOPS_STORE_VERSION
Expand Down Expand Up @@ -120,17 +121,19 @@ class SensitiveApiPermissionAspect constructor(
val version = request.getHeader(AUTH_HEADER_DEVOPS_STORE_VERSION)
val checkParamFlag = !storeType.isNullOrBlank() && !version.isNullOrBlank()
if (checkParamFlag && !apiName.isNullOrBlank() && !storeCode.isNullOrBlank()) {
val installedPkgShaContent = request.getHeader(AUTH_HEADER_DEVOPS_SHA_CONTENT)
val signFileName = request.getHeader(AUTH_HEADER_DEVOPS_SIGN_FILE_NAME)
val fileShaContent = request.getHeader(AUTH_HEADER_DEVOPS_SHA_CONTENT)
val osName = request.getHeader(AUTH_HEADER_DEVOPS_OS_NAME)
val osArch = request.getHeader(AUTH_HEADER_DEVOPS_OS_ARCH)
return verifyApi(
storeType = storeType,
storeCode = storeCode,
apiName = apiName,
version = version,
installedPkgShaContent = installedPkgShaContent,
osName = osName,
osArch = osArch
osArch = osArch,
signFileName = signFileName,
fileShaContent = fileShaContent
)
}
return false
Expand All @@ -142,14 +145,16 @@ class SensitiveApiPermissionAspect constructor(
storeCode: String,
apiName: String,
version: String? = null,
installedPkgShaContent: String? = null,
osName: String? = null,
osArch: String? = null
osArch: String? = null,
signFileName: String? = null,
fileShaContent: String? = null
): Boolean {
val cacheKey = "$storeType:$storeCode:$apiName"
val cacheKey = "$storeType:$storeCode:$apiName:$version:$osName:$osArch:$signFileName:$fileShaContent"
return apiPermissionCache.getIfPresent(cacheKey) ?: run {
val apiPermission = client.get(ServiceSensitiveApiPermissionResource::class).verifyApi(
installedPkgShaContent = installedPkgShaContent,
signFileName = signFileName,
fileShaContent = fileShaContent,
osName = osName,
osArch = osArch,
storeCode = storeCode,
Expand Down Expand Up @@ -204,6 +209,6 @@ class SensitiveApiPermissionAspect constructor(

companion object {
private val logger = LoggerFactory.getLogger(SensitiveApiPermissionAspect::class.java)
private const val CACHE_MAX_SIZE = 1000L
private const val CACHE_MAX_SIZE = 2000L
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -31,9 +31,11 @@ import com.tencent.devops.common.api.annotation.ServiceInterface
import com.tencent.devops.common.api.auth.AUTH_HEADER_DEVOPS_OS_ARCH
import com.tencent.devops.common.api.auth.AUTH_HEADER_DEVOPS_OS_NAME
import com.tencent.devops.common.api.auth.AUTH_HEADER_DEVOPS_SHA_CONTENT
import com.tencent.devops.common.api.auth.AUTH_HEADER_DEVOPS_SIGN_FILE_NAME
import com.tencent.devops.common.api.pojo.Result
import io.swagger.v3.oas.annotations.Parameter
import javax.ws.rs.Consumes
import javax.ws.rs.DefaultValue
import javax.ws.rs.GET
import javax.ws.rs.HeaderParam
import javax.ws.rs.Path
Expand All @@ -54,7 +56,8 @@ interface ServiceSensitiveApiPermissionResource {
/**
* 验证组件是否有该api接口的权限
*
* @param installedPkgShaContent 已安装组件包sha1摘要值
* @param signFileName 签名文件名称
* @param fileShaContent 文件sha1摘要值
* @param osName 操作系统名称
* @param osArch 操作系统CPU架构
* @param storeCode 组件标识
Expand All @@ -66,9 +69,12 @@ interface ServiceSensitiveApiPermissionResource {
@GET
@Suppress("LongParameterList")
fun verifyApi(
@Parameter(description = "已安装组件包sha1摘要值", required = false)
@Parameter(description = "签名文件名称", required = false)
@HeaderParam(AUTH_HEADER_DEVOPS_SIGN_FILE_NAME)
signFileName: String? = null,
@Parameter(description = "文件sha1摘要值", required = false)
@HeaderParam(AUTH_HEADER_DEVOPS_SHA_CONTENT)
installedPkgShaContent: String? = null,
fileShaContent: String? = null,
@Parameter(description = "操作系统名称", required = false)
@HeaderParam(AUTH_HEADER_DEVOPS_OS_NAME)
osName: String? = null,
Expand All @@ -83,6 +89,7 @@ interface ServiceSensitiveApiPermissionResource {
apiName: String,
@QueryParam("storeType")
@Parameter(description = "组件类型", required = true)
@DefaultValue("ATOM")
storeType: String = "ATOM",
@QueryParam("version")
@Parameter(description = "组件版本", required = false)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ import com.tencent.devops.common.api.pojo.Page
import com.tencent.devops.common.api.pojo.Result
import com.tencent.devops.common.web.annotation.BkField
import com.tencent.devops.common.web.constant.BkStyleEnum
import com.tencent.devops.store.pojo.common.InstalledPkgShaContentRequest
import com.tencent.devops.store.pojo.common.InstalledPkgFileShaContentRequest
import com.tencent.devops.store.pojo.common.MyStoreComponent
import com.tencent.devops.store.pojo.common.StoreBaseInfoUpdateRequest
import com.tencent.devops.store.pojo.common.StoreDetailInfo
Expand Down Expand Up @@ -221,10 +221,10 @@ interface OpStoreComponentResource {
storeOfflineRequest: StoreOfflineRequest
): Result<Boolean>

@Operation(summary = "更新组件已安装包sha1摘要值")
@Operation(summary = "更新组件已安装包文件sha1摘要值")
@PUT
@Path("/types/{storeType}/codes/{storeCode}/versions/{version}/component/installed/pkg/sha/update")
fun updateComponentInstalledPkgShaContent(
@Path("/types/{storeType}/codes/{storeCode}/versions/{version}/component/installed/pkg/file/sha/update")
fun updateComponentInstalledPkgFileShaContent(
@Parameter(description = "用户ID", required = true, example = AUTH_HEADER_USER_ID_DEFAULT_VALUE)
@HeaderParam(AUTH_HEADER_USER_ID)
userId: String,
Expand All @@ -239,7 +239,7 @@ interface OpStoreComponentResource {
@Parameter(description = "组件版本", required = true)
@PathParam("version")
version: String,
@Parameter(description = "更新组件已安装包sha1摘要值请求报文", required = true)
installedPkgShaContentRequest: InstalledPkgShaContentRequest
@Parameter(description = "更新组件已安装包文件sha1摘要值请求报文", required = true)
installedPkgFileShaContentRequest: InstalledPkgFileShaContentRequest
): Result<Boolean>
}
Original file line number Diff line number Diff line change
Expand Up @@ -30,9 +30,11 @@ package com.tencent.devops.store.pojo.common
import io.swagger.v3.oas.annotations.media.Schema

@Schema(title = "更新组件已安装包sha1摘要值请求报文")
data class InstalledPkgShaContentRequest(
@get:Schema(title = "已安装包sha1摘要值", required = true)
val installedPkgShaContent: String,
data class InstalledPkgFileShaContentRequest(
@get:Schema(title = "签名文件名称", required = true)
val signFileName: String,
@get:Schema(title = "文件sha1摘要值", required = true)
val fileShaContent: String,
@get:Schema(title = "操作系统名称", required = false)
val osName: String? = null,
@get:Schema(title = "操作系统CPU架构", required = false)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ import com.tencent.devops.store.common.service.OpStoreComponentService
import com.tencent.devops.store.common.service.StoreComponentManageService
import com.tencent.devops.store.common.service.StoreComponentQueryService
import com.tencent.devops.store.common.service.StoreReleaseService
import com.tencent.devops.store.pojo.common.InstalledPkgShaContentRequest
import com.tencent.devops.store.pojo.common.InstalledPkgFileShaContentRequest
import com.tencent.devops.store.pojo.common.MyStoreComponent
import com.tencent.devops.store.pojo.common.QueryComponentsParam
import com.tencent.devops.store.pojo.common.StoreBaseInfoUpdateRequest
Expand Down Expand Up @@ -163,19 +163,19 @@ class OpStoreComponentResourceImpl @Autowired constructor(
)
}

override fun updateComponentInstalledPkgShaContent(
override fun updateComponentInstalledPkgFileShaContent(
userId: String,
storeType: StoreTypeEnum,
storeCode: String,
version: String,
installedPkgShaContentRequest: InstalledPkgShaContentRequest
installedPkgFileShaContentRequest: InstalledPkgFileShaContentRequest
): Result<Boolean> {
return storeComponentManageService.updateComponentInstalledPkgShaContent(
userId = userId,
storeType = storeType,
storeCode = storeCode,
version = version,
installedPkgShaContentRequest = installedPkgShaContentRequest
installedPkgFileShaContentRequest = installedPkgFileShaContentRequest
)
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,8 @@ class ServiceSensitiveApiPermissionResourceImpl @Autowired constructor(
) : ServiceSensitiveApiPermissionResource {

override fun verifyApi(
installedPkgShaContent: String?,
signFileName: String?,
fileShaContent: String?,
osName: String?,
osArch: String?,
storeCode: String,
Expand All @@ -49,7 +50,8 @@ class ServiceSensitiveApiPermissionResourceImpl @Autowired constructor(
version: String?
): Result<Boolean> {
return sensitiveApiService.verifyApi(
installedPkgShaContent = installedPkgShaContent,
signFileName = signFileName,
fileShaContent = fileShaContent,
osName = osName,
osArch = osArch,
storeType = StoreTypeEnum.valueOf(storeType),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -72,7 +72,8 @@ interface SensitiveApiService {

@Suppress("LongParameterList")
fun verifyApi(
installedPkgShaContent: String? = null,
signFileName: String? = null,
fileShaContent: String? = null,
osName: String? = null,
osArch: String? = null,
storeType: StoreTypeEnum,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ package com.tencent.devops.store.common.service
import com.tencent.devops.common.api.pojo.Result
import com.tencent.devops.common.pipeline.enums.ChannelCode
import com.tencent.devops.store.pojo.common.InstallStoreReq
import com.tencent.devops.store.pojo.common.InstalledPkgShaContentRequest
import com.tencent.devops.store.pojo.common.InstalledPkgFileShaContentRequest
import com.tencent.devops.store.pojo.common.StoreBaseInfoUpdateRequest
import com.tencent.devops.store.pojo.common.UnInstallReq
import com.tencent.devops.store.pojo.common.enums.StoreTypeEnum
Expand Down Expand Up @@ -66,6 +66,6 @@ interface StoreComponentManageService {
storeType: StoreTypeEnum,
storeCode: String,
version: String,
installedPkgShaContentRequest: InstalledPkgShaContentRequest
installedPkgFileShaContentRequest: InstalledPkgFileShaContentRequest
): Result<Boolean>
}
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ package com.tencent.devops.store.common.service.impl
import com.fasterxml.jackson.core.type.TypeReference
import com.tencent.devops.common.api.auth.AUTH_HEADER_DEVOPS_SHA_CONTENT
import com.tencent.devops.common.api.constant.CommonMessageCode
import com.tencent.devops.common.api.constant.KEY_INSTALLED_PKG_SHA_CONTENT
import com.tencent.devops.common.api.constant.KEY_FILE_SHA_CONTENT
import com.tencent.devops.common.api.constant.KEY_VERSION
import com.tencent.devops.common.api.exception.ErrorCodeException
import com.tencent.devops.common.api.pojo.Page
Expand Down Expand Up @@ -229,7 +229,8 @@ class SensitiveApiServiceImpl @Autowired constructor(
}

override fun verifyApi(
installedPkgShaContent: String?,
signFileName: String?,
fileShaContent: String?,
osName: String?,
osArch: String?,
storeType: StoreTypeEnum,
Expand All @@ -241,7 +242,7 @@ class SensitiveApiServiceImpl @Autowired constructor(
if (version.isNullOrBlank()) {
throw ErrorCodeException(errorCode = CommonMessageCode.ERROR_NEED_PARAM_, params = arrayOf(KEY_VERSION))
}
if (installedPkgShaContent.isNullOrBlank()) {
if (fileShaContent.isNullOrBlank()) {
throw ErrorCodeException(
errorCode = CommonMessageCode.ERROR_NEED_PARAM_,
params = arrayOf(AUTH_HEADER_DEVOPS_SHA_CONTENT)
Expand All @@ -266,12 +267,12 @@ class SensitiveApiServiceImpl @Autowired constructor(
errorCode = CommonMessageCode.PARAMETER_IS_INVALID,
params = arrayOf("$osName:$osArch")
)
val dbInstalledPkgShaContent = storeBaseEnvExtQueryDao.getBaseExtEnvsByEnvId(
val dbFileShaContent = storeBaseEnvExtQueryDao.getBaseExtEnvsByEnvId(
dslContext = dslContext,
envId = baseEnvRecord.id,
fieldName = KEY_INSTALLED_PKG_SHA_CONTENT
fieldName = "${KEY_FILE_SHA_CONTENT}_$signFileName"
)?.getOrNull(0)?.fieldValue ?: baseEnvRecord.shaContent
if (installedPkgShaContent.lowercase() != dbInstalledPkgShaContent) {
if (fileShaContent.lowercase() != dbFileShaContent) {
throw ErrorCodeException(
errorCode = CommonMessageCode.PARAMETER_VALIDATE_ERROR,
params = arrayOf(AUTH_HEADER_DEVOPS_SHA_CONTENT, "wrong sha1 content")
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@ package com.tencent.devops.store.common.service.impl

import com.tencent.devops.common.api.auth.AUTH_HEADER_USER_ID
import com.tencent.devops.common.api.constant.CommonMessageCode
import com.tencent.devops.common.api.constant.KEY_INSTALLED_PKG_SHA_CONTENT
import com.tencent.devops.common.api.constant.KEY_FILE_SHA_CONTENT
import com.tencent.devops.common.api.exception.ErrorCodeException
import com.tencent.devops.common.api.pojo.Result
import com.tencent.devops.common.api.util.UUIDUtil
Expand Down Expand Up @@ -62,7 +62,7 @@ import com.tencent.devops.store.common.utils.StoreReleaseUtils
import com.tencent.devops.store.common.utils.StoreUtils
import com.tencent.devops.store.constant.StoreMessageCode
import com.tencent.devops.store.pojo.common.InstallStoreReq
import com.tencent.devops.store.pojo.common.InstalledPkgShaContentRequest
import com.tencent.devops.store.pojo.common.InstalledPkgFileShaContentRequest
import com.tencent.devops.store.pojo.common.StoreBaseInfoUpdateRequest
import com.tencent.devops.store.pojo.common.UnInstallReq
import com.tencent.devops.store.pojo.common.enums.ReasonTypeEnum
Expand Down Expand Up @@ -432,7 +432,7 @@ class StoreComponentManageServiceImpl : StoreComponentManageService {
storeType: StoreTypeEnum,
storeCode: String,
version: String,
installedPkgShaContentRequest: InstalledPkgShaContentRequest
installedPkgFileShaContentRequest: InstalledPkgFileShaContentRequest
): Result<Boolean> {
val storeId = storeBaseQueryDao.getComponentId(
dslContext = dslContext,
Expand All @@ -443,15 +443,15 @@ class StoreComponentManageServiceImpl : StoreComponentManageService {
val baseEnvRecord = storeBaseEnvQueryDao.getBaseEnvsByStoreId(
dslContext = dslContext,
storeId = storeId,
osName = installedPkgShaContentRequest.osName,
osArch = installedPkgShaContentRequest.osArch
osName = installedPkgFileShaContentRequest.osName,
osArch = installedPkgFileShaContentRequest.osArch
)?.get(0) ?: throw ErrorCodeException(errorCode = CommonMessageCode.ERROR_CLIENT_REST_ERROR)
val storeBaseEnvExtDataPO = StoreBaseEnvExtDataPO(
id = UUIDUtil.generate(),
envId = baseEnvRecord.id,
storeId = storeId,
fieldName = KEY_INSTALLED_PKG_SHA_CONTENT,
fieldValue = installedPkgShaContentRequest.installedPkgShaContent,
fieldName = "${KEY_FILE_SHA_CONTENT}_${installedPkgFileShaContentRequest.signFileName}",
fieldValue = installedPkgFileShaContentRequest.fileShaContent,
creator = userId,
modifier = userId
)
Expand Down

0 comments on commit 312dec1

Please sign in to comment.