mirror of
https://github.com/certd/certd.git
synced 2026-04-24 04:17:25 +08:00
feat: 腾讯云cdn支持
This commit is contained in:
@@ -9,13 +9,44 @@ export class AbstractPlugin {
|
||||
const { contextPath } = options
|
||||
const contextJson = fs.readFileSync(contextPath)
|
||||
const context = JSON.parse(contextJson)
|
||||
const newContext = await this.execute(options, context)
|
||||
options.context = context
|
||||
const newContext = await this.execute(options)
|
||||
fs.writeFileSync(JSON.stringify(newContext || context))
|
||||
}
|
||||
|
||||
async execute (options, context) {
|
||||
console.log('请实现此方法,context:', context)
|
||||
return context
|
||||
async doExecute (options) {
|
||||
try {
|
||||
return await this.execute(options)
|
||||
} catch (e) {
|
||||
logger.error('插件执行出错:', e)
|
||||
throw e
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 执行
|
||||
* @param options
|
||||
* @returns {Promise<void>}
|
||||
*/
|
||||
async execute (options) {
|
||||
console.error('请实现此方法,context:', options.context)
|
||||
}
|
||||
|
||||
async doRollback (options) {
|
||||
try {
|
||||
return await this.rollback(options)
|
||||
} catch (e) {
|
||||
logger.error('插件rollback出错:', e)
|
||||
throw e
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 回退,如有必要
|
||||
* @param options
|
||||
*/
|
||||
async rollback (options) {
|
||||
console.error('请实现此方法,rollback:', options.context)
|
||||
}
|
||||
|
||||
getAccessProvider (accessProvider, accessProviders) {
|
||||
|
||||
@@ -20,7 +20,7 @@ export class DeployCertToAliyunCDN extends AbstractAliyunPlugin {
|
||||
certName: {
|
||||
label: '证书名称'
|
||||
},
|
||||
certType: {
|
||||
from: {
|
||||
value: 'upload',
|
||||
label: '证书来源',
|
||||
options: [
|
||||
@@ -51,10 +51,10 @@ export class DeployCertToAliyunCDN extends AbstractAliyunPlugin {
|
||||
}
|
||||
}
|
||||
|
||||
async execute ({ accessProviders, cert, args, context }) {
|
||||
const accessProvider = this.getAccessProvider(args.accessProvider, accessProviders)
|
||||
async execute ({ accessProviders, cert, props, context }) {
|
||||
const accessProvider = this.getAccessProvider(props.accessProvider, accessProviders)
|
||||
const client = this.getClient(accessProvider)
|
||||
const params = this.buildParams(args, context, cert)
|
||||
const params = this.buildParams(props, context, cert)
|
||||
await this.doRequest(client, params)
|
||||
}
|
||||
|
||||
@@ -68,7 +68,7 @@ export class DeployCertToAliyunCDN extends AbstractAliyunPlugin {
|
||||
}
|
||||
|
||||
buildParams (args, context, cert) {
|
||||
const { certName, certType, domainName } = args
|
||||
const { certName, from, domainName } = args
|
||||
const CertName = certName + '-' + dayjs().format('YYYYMMDDHHmmss')
|
||||
|
||||
const params = {
|
||||
@@ -76,7 +76,7 @@ export class DeployCertToAliyunCDN extends AbstractAliyunPlugin {
|
||||
DomainName: domainName,
|
||||
ServerCertificateStatus: 'on',
|
||||
CertName: CertName,
|
||||
CertType: certType,
|
||||
CertType: from,
|
||||
ServerCertificate: super.format(cert.crt.toString()),
|
||||
PrivateKey: super.format(cert.key.toString())
|
||||
}
|
||||
|
||||
@@ -41,9 +41,9 @@ export class UploadCertToAliyun extends AbstractAliyunPlugin {
|
||||
})
|
||||
}
|
||||
|
||||
async execute ({ accessProviders, cert, args, context, logger }) {
|
||||
const { name, accessProvider } = args
|
||||
const certName = name + '-' + dayjs().format('YYYYMMDDHHmmss')
|
||||
async execute ({ accessProviders, cert, props, context, logger }) {
|
||||
const { name, accessProvider } = props
|
||||
const certName = name + '-' + dayjs().format('YYYYMMDD-HHmmss')
|
||||
const params = {
|
||||
RegionId: 'cn-hangzhou',
|
||||
Name: certName,
|
||||
@@ -59,7 +59,7 @@ export class UploadCertToAliyun extends AbstractAliyunPlugin {
|
||||
const client = this.getClient(provider)
|
||||
const ret = await client.request('CreateUserCertificate', params, requestOption)
|
||||
this.checkRet(ret)
|
||||
this.logger.info('证书上传成功:certId=', ret.CertId)
|
||||
this.logger.info('证书上传成功:aliyunCertId=', ret.CertId)
|
||||
context.aliyunCertId = ret.CertId
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,16 @@
|
||||
import { AbstractPlugin } from '../abstract-plugin/index.js'
|
||||
|
||||
export class AbstractTencentPlugin extends AbstractPlugin {
|
||||
format (pem) {
|
||||
pem = pem.replace(/\r/g, '')
|
||||
pem = pem.replace(/\n\n/g, '\n')
|
||||
pem = pem.replace(/\n$/g, '')
|
||||
return pem
|
||||
}
|
||||
|
||||
checkRet (ret) {
|
||||
if (ret && ret.Error) {
|
||||
throw new Error('执行失败:' + ret.Error.Code + ',' + ret.Error.Message)
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,116 @@
|
||||
import { AbstractTencentPlugin } from '../../tencent/abstract-tencent.js'
|
||||
import dayjs from 'dayjs'
|
||||
import tencentcloud from 'tencentcloud-sdk-nodejs'
|
||||
|
||||
export class DeployCertToTencentCDN extends AbstractTencentPlugin {
|
||||
/**
|
||||
* 插件定义
|
||||
* 名称
|
||||
* 入参
|
||||
* 出参
|
||||
*/
|
||||
static define () {
|
||||
return {
|
||||
name: 'deployCertToTencentCDN',
|
||||
label: '部署到腾讯云CDN',
|
||||
input: {
|
||||
domainName: {
|
||||
label: 'cdn加速域名',
|
||||
required: true
|
||||
},
|
||||
certName: {
|
||||
label: '证书名称'
|
||||
},
|
||||
certType: {
|
||||
value: 'upload',
|
||||
label: '证书来源',
|
||||
options: [
|
||||
{ value: 'upload', label: '直接上传' },
|
||||
{ value: 'cloud', label: '从证书库', desc: '需要uploadCertToTencent作为前置任务' }
|
||||
],
|
||||
required: true
|
||||
},
|
||||
// serverCertificateStatus: {
|
||||
// label: '启用https',
|
||||
// options: [
|
||||
// { value: 'on', label: '开启HTTPS,并更新证书' },
|
||||
// { value: 'auto', label: '若HTTPS开启则更新,未开启不更新' }
|
||||
// ],
|
||||
// required:true
|
||||
// },
|
||||
accessProvider: {
|
||||
label: 'Access提供者',
|
||||
type: [String, Object],
|
||||
desc: 'AccessProviders的key 或 一个包含accessKeyId与accessKeySecret的对象',
|
||||
options: 'accessProviders[type=aliyun]',
|
||||
required: true
|
||||
}
|
||||
},
|
||||
output: {
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
async execute ({ accessProviders, cert, props, context }) {
|
||||
const accessProvider = this.getAccessProvider(props.accessProvider, accessProviders)
|
||||
const client = this.getClient(accessProvider)
|
||||
const params = this.buildParams(props, context, cert)
|
||||
await this.doRequest(client, params)
|
||||
return context
|
||||
}
|
||||
|
||||
async rollback ({ accessProviders, cert, props, context }) {
|
||||
|
||||
}
|
||||
|
||||
getClient (accessProvider) {
|
||||
const CdnClient = tencentcloud.cdn.v20180606.Client
|
||||
|
||||
const clientConfig = {
|
||||
credential: {
|
||||
secretId: accessProvider.secretId,
|
||||
secretKey: accessProvider.secretKey
|
||||
},
|
||||
region: '',
|
||||
profile: {
|
||||
httpProfile: {
|
||||
endpoint: 'cdn.tencentcloudapi.com'
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return new CdnClient(clientConfig)
|
||||
}
|
||||
|
||||
buildParams (props, context, cert) {
|
||||
const { domainName, from } = props
|
||||
const { tencentCertId } = context
|
||||
|
||||
const params = {
|
||||
Https: {
|
||||
Switch: 'on',
|
||||
CertInfo: {
|
||||
CertId: tencentCertId
|
||||
// Certificate: '1231',
|
||||
// PrivateKey: '1231'
|
||||
}
|
||||
},
|
||||
Domain: domainName
|
||||
}
|
||||
if (from === 'upload') {
|
||||
params.Https.CertInfo = {
|
||||
Certificate: this.format(cert.crt.toString()),
|
||||
PrivateKey: this.format(cert.key.toString())
|
||||
}
|
||||
}
|
||||
return params
|
||||
}
|
||||
|
||||
async doRequest (client, params) {
|
||||
const ret = await client.UpdateDomainConfig(params)
|
||||
this.checkRet(ret)
|
||||
this.logger.info('设置腾讯云CDN证书成功:', ret.RequestId)
|
||||
return ret.RequestId
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,87 @@
|
||||
import dayjs from 'dayjs'
|
||||
import tencentcloud from 'tencentcloud-sdk-nodejs'
|
||||
import { AbstractTencentPlugin } from '../abstract-tencent.js'
|
||||
|
||||
export class UploadCertToTencent extends AbstractTencentPlugin {
|
||||
/**
|
||||
* 插件定义
|
||||
* 名称
|
||||
* 入参
|
||||
* 出参
|
||||
*/
|
||||
static define () {
|
||||
return {
|
||||
name: 'uploadCertToTencent',
|
||||
label: '上传证书到腾讯云',
|
||||
input: {
|
||||
name: {
|
||||
label: '证书名称'
|
||||
},
|
||||
accessProvider: {
|
||||
label: 'Access提供者',
|
||||
type: [String, Object],
|
||||
desc: 'AccessProviders的key 或 一个包含accessKeyId与accessKeySecret的对象',
|
||||
options: 'accessProviders[type=tencent]'
|
||||
}
|
||||
},
|
||||
output: {
|
||||
tencentCertId: {
|
||||
type: String,
|
||||
desc: '上传成功后的腾讯云CertId'
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
getClient (accessProvider) {
|
||||
const SslClient = tencentcloud.ssl.v20191205.Client
|
||||
|
||||
const clientConfig = {
|
||||
credential: {
|
||||
secretId: accessProvider.secretId,
|
||||
secretKey: accessProvider.secretKey
|
||||
},
|
||||
region: '',
|
||||
profile: {
|
||||
httpProfile: {
|
||||
endpoint: 'ssl.tencentcloudapi.com'
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return new SslClient(clientConfig)
|
||||
}
|
||||
|
||||
async execute ({ accessProviders, cert, props, context, logger }) {
|
||||
const { name, accessProvider } = props
|
||||
const certName = name + '-' + dayjs().format('YYYYMMDD-HHmmss')
|
||||
|
||||
const provider = super.getAccessProvider(accessProvider, accessProviders)
|
||||
const client = this.getClient(provider)
|
||||
|
||||
const params = {
|
||||
CertificatePublicKey: this.format(cert.crt.toString()),
|
||||
CertificatePrivateKey: this.format(cert.key.toString()),
|
||||
Alias: certName
|
||||
}
|
||||
const ret = await client.UploadCertificate(params)
|
||||
this.checkRet(ret)
|
||||
this.logger.info('证书上传成功:tencentCertId=', ret.CertificateId)
|
||||
context.tencentCertId = ret.CertificateId
|
||||
}
|
||||
|
||||
async rollback ({ accessProviders, cert, props, context, logger }) {
|
||||
const { accessProvider } = props
|
||||
const provider = super.getAccessProvider(accessProvider, accessProviders)
|
||||
const client = this.getClient(provider)
|
||||
|
||||
const { tencentCertId } = context
|
||||
const params = {
|
||||
CertificateId: tencentCertId
|
||||
}
|
||||
const ret = await client.DeleteCertificate(params)
|
||||
this.checkRet(ret)
|
||||
this.logger.info('证书删除成功:DeleteResult=', ret.DeleteResult)
|
||||
delete context.tencentCertId
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user