update at 2023/08/14

This commit is contained in:
2023-08-14 21:41:37 +08:00
parent a039a664f1
commit 44e8cbee2c
255 changed files with 20426 additions and 233 deletions

64
tools/ca/cmca.go Normal file
View File

@@ -0,0 +1,64 @@
package main
import (
"crypto/rand"
"crypto/rsa"
"crypto/x509"
"encoding/pem"
"fmt"
"os"
)
func main() {
// 生成RSA密钥对
privateKey, err := rsa.GenerateKey(rand.Reader, 2048)
if err != nil {
fmt.Println("Failed to generate RSA private key:", err)
return
}
// 将私钥保存到文件
privateKeyFile, err := os.Create("private_key.pem")
if err != nil {
fmt.Println("Failed to create private key file:", err)
return
}
defer privateKeyFile.Close()
privateKeyBlock := &pem.Block{
Type: "RSA PRIVATE KEY",
Bytes: x509.MarshalPKCS1PrivateKey(privateKey),
}
err = pem.Encode(privateKeyFile, privateKeyBlock)
if err != nil {
fmt.Println("Failed to write private key to file:", err)
return
}
fmt.Println("Private key generated and saved to private_key.pem")
// 获取公钥
publicKey := &privateKey.PublicKey
// 将公钥保存到文件
publicKeyFile, err := os.Create("public_key.pem")
if err != nil {
fmt.Println("Failed to create public key file:", err)
return
}
defer publicKeyFile.Close()
publicKeyBlock := &pem.Block{
Type: "RSA PUBLIC KEY",
Bytes: x509.MarshalPKCS1PublicKey(publicKey),
}
err = pem.Encode(publicKeyFile, publicKeyBlock)
if err != nil {
fmt.Println("Failed to write public key to file:", err)
return
}
fmt.Println("Public key generated and saved to public_key.pem")
}

27
tools/ca/private_key.pem Normal file
View File

@@ -0,0 +1,27 @@
-----BEGIN RSA PRIVATE KEY-----
MIIEpAIBAAKCAQEA1ox38PK2qgSpJDzsRvdSDPQP6hYnuCasUMV6gJsb/CVcGK3v
7MDW1X4VSgJvxqPtHH5hdWOM1rT29DtC7rU4MhK0i+9SJixvFjyijABOuXCAFtw1
zJDJN9EFGvA/WBsCFlwmpK9qKofF3n37/N2PvgCMDWVBrGe2uszQv9O5hnqE0X2J
33ddxRMX+7SVSCz8H1U+3FWLNF2SF4sIUXn1NdzouMtEGeaxvh+czYXCEB+rtewY
7Iwvoz7VamOOxMC9FmwKvFTePjvdYcdayiImunJtS1yg1/tiKGh+BCU9YFOkZ0dw
eP982EybQYw39L8UVJqXTMPKqErKDJxkNpg/nQIDAQABAoIBAA8rm4eEAfp/nd4c
GLDj5/9WepGYw3I3+dM0Q3c4gIARvDNaiS56bDZoVeUHyxOGn8t1/Doqsdi0rwmR
7yel1LVlsTJ715kvZyNxYiT4GJjwJX54T62JR1EVDIFdH32BW2JtXaYjaSRcuVcE
HX9Bw1ox+7UuxbgFFVycAt6tf97MRdBwgJX6pNM63RzIjOFPoVPirsaWJu1PWeGt
AIRrIdMyPS+oMMTvfFNSlTuVEgDzwtecrYIeXoMhYH0pCBMx3aX7F71lww70957t
k0g+YMR50OrNMxOMHe9/jnDceLmLvfEvZVxCggMc7wPn2Llwa0SG87cjHDe/T0tg
Ob6MKlkCgYEA9Aq8tgqYTijOALVfvxWUYSEhL3AfguwNPhK+Rbx2vdYKkm5qfVkw
ZKj5rZTCUp9b1VW3EqQ6+MwzujmL8Eb85H9G3uTiVBAwqJHATF1OlZmHjDAGTZdI
kNZNdYwkOI5UteGz9/7Gq+ayapBu402ttBlChlX+q9/jzm23hq5T6CcCgYEA4Q/E
o00DloXbqq9QNv4WFYzz8NukU3Ge7ftcDU3EciK36M2Ptck0oR59TK9pFElxwaOF
SYaHUX7FE/q60vXeUQfNPQzzdCcxLqGOgK3sJlmtCiyRHIUijJ5ew/F9c2rikI5X
Vc2lvfX4NUk1YdcRHap7hPiaSWI6LYXzRwFd0JsCgYEAqlDcBwg550JfEuuCGO/M
kET4zgyoUUzAqTOXiz/OdwpscmmQ9E5MkdPD/Lq3K8Z/5tFdZSss5PpOl4cV/Oju
EeIp6eE/e3+ZFewykpkEATAXA2V44KnWQQ7vHDxkAvyCbjVIzqkGqm3k0q5eVVCf
C/QdE3fstrMYX7b+wIXllT0CgYEAvJ5ncWjhAezLbeAhvQTzYzpPU2Pw81H9HXwU
6L1tTy6TrVNiBrtLFWElJ/i2ex8WbG/sC/PoQr+Y0abHnngayxRbyLeq7YTPLkKN
2IBqsrVjVWyGbT2S+ADecR9ZwToqCXaR8UI5jtuvGpFxYL9LA+7WOFnVjHz7Px3N
Bow5oNMCgYB8m2O/rY8bjA25M/348gQ51dtR5Y+QU93rK1SSQnrbu70kZKZjBfIj
x1C6HgIECowQ56Jg/pYEQmiv+bk/0yf8uHCcCbOCEzl42gRjleO/GCt+WZD2jR3Y
bt4gG7xHklNYZU5+m45RWWLLik2LSGfY7yerhV2585lQjoYNqRBY4g==
-----END RSA PRIVATE KEY-----

8
tools/ca/public_key.pem Normal file
View File

@@ -0,0 +1,8 @@
-----BEGIN RSA PUBLIC KEY-----
MIIBCgKCAQEA1ox38PK2qgSpJDzsRvdSDPQP6hYnuCasUMV6gJsb/CVcGK3v7MDW
1X4VSgJvxqPtHH5hdWOM1rT29DtC7rU4MhK0i+9SJixvFjyijABOuXCAFtw1zJDJ
N9EFGvA/WBsCFlwmpK9qKofF3n37/N2PvgCMDWVBrGe2uszQv9O5hnqE0X2J33dd
xRMX+7SVSCz8H1U+3FWLNF2SF4sIUXn1NdzouMtEGeaxvh+czYXCEB+rtewY7Iwv
oz7VamOOxMC9FmwKvFTePjvdYcdayiImunJtS1yg1/tiKGh+BCU9YFOkZ0dweP98
2EybQYw39L8UVJqXTMPKqErKDJxkNpg/nQIDAQAB
-----END RSA PUBLIC KEY-----

View File

@@ -0,0 +1,18 @@
-----BEGIN CERTIFICATE-----
MIIC4jCCAcqgAwIBAgICB+cwDQYJKoZIhvcNAQELBQAwEjEQMA4GA1UEAxMHUm9v
dCBDQTAeFw0yMzA4MTIxODA5MzZaFw0zMzA4MTIxODA5MzZaMBIxEDAOBgNVBAMT
B1Jvb3QgQ0EwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCUTcFiT1GT
Zq9ROKTuWm6IfFthO6ysthEKevwkgJGDRCwF+K6rx3j7izTDfLkXum5OPbcd/yiE
B40Yrq9X2ckX260xG9PjDmGUaq8q5sza85Gg2hrW6wiLF9y8yYK3/v7716d0y6st
jt71pH554R98m0zHkbkmrFEagWR5cEoVM6MPZp2wdDnOFBBRiB1BrbHMpAFiKJ6s
oqm1yhUwCeeR/Hs09JF8KfOFhV4qAEVvE1cviHucCEvLBaG6xBzbKvYV2iOPu6u2
o818wphqmSZYoj3/O4/EyVgvj1VdSqmkTSudiiIhLAa8/2JKrW1v7wFQjRkwNwdf
h6UR5liIUwk7AgMBAAGjQjBAMA4GA1UdDwEB/wQEAwIBBjAPBgNVHRMBAf8EBTAD
AQH/MB0GA1UdDgQWBBRtEF/Jyw6Zz3v0K5uA6aMOr9LXRTANBgkqhkiG9w0BAQsF
AAOCAQEAErmFo6JjEoFZv8R2gwNUq7ln+YEh2hX4myLlNDfTpYeGnn2Ge70Kmb0o
dkSyanDd9tGImcbEOttWAYve3vetvN3g+GONbf5pV7ClIbVV5MsjN/aGwj/TQWhu
ttmfu9IV2b5HyFEM61eoHVrNoWiNpbNHTu5D/XF8sg5JkseTnJF06foykzAx28i6
JcttunYn5SoWTIS9Ydu07X7uBcTeFBcKfH0xg4QlsNppiM5lIxBbp0WjQ8jyWw+b
Lyef4N6hmiaOf6P6qwaVZkEBhK6MVf1zadURuUSWAkhwGFjA7IbjbJ7OfYLXkYp3
mIrXQzjxz6AfyOcY/FsgcaDLf5xbYw==
-----END CERTIFICATE-----

18
tools/casign/ca_cert.pem Normal file
View File

@@ -0,0 +1,18 @@
-----BEGIN CERTIFICATE-----
MIIC4jCCAcqgAwIBAgICB+cwDQYJKoZIhvcNAQELBQAwEjEQMA4GA1UEAxMHUm9v
dCBDQTAeFw0yMzA4MTIxODA5MzZaFw0zMzA4MTIxODA5MzZaMBIxEDAOBgNVBAMT
B1Jvb3QgQ0EwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCUTcFiT1GT
Zq9ROKTuWm6IfFthO6ysthEKevwkgJGDRCwF+K6rx3j7izTDfLkXum5OPbcd/yiE
B40Yrq9X2ckX260xG9PjDmGUaq8q5sza85Gg2hrW6wiLF9y8yYK3/v7716d0y6st
jt71pH554R98m0zHkbkmrFEagWR5cEoVM6MPZp2wdDnOFBBRiB1BrbHMpAFiKJ6s
oqm1yhUwCeeR/Hs09JF8KfOFhV4qAEVvE1cviHucCEvLBaG6xBzbKvYV2iOPu6u2
o818wphqmSZYoj3/O4/EyVgvj1VdSqmkTSudiiIhLAa8/2JKrW1v7wFQjRkwNwdf
h6UR5liIUwk7AgMBAAGjQjBAMA4GA1UdDwEB/wQEAwIBBjAPBgNVHRMBAf8EBTAD
AQH/MB0GA1UdDgQWBBRtEF/Jyw6Zz3v0K5uA6aMOr9LXRTANBgkqhkiG9w0BAQsF
AAOCAQEAErmFo6JjEoFZv8R2gwNUq7ln+YEh2hX4myLlNDfTpYeGnn2Ge70Kmb0o
dkSyanDd9tGImcbEOttWAYve3vetvN3g+GONbf5pV7ClIbVV5MsjN/aGwj/TQWhu
ttmfu9IV2b5HyFEM61eoHVrNoWiNpbNHTu5D/XF8sg5JkseTnJF06foykzAx28i6
JcttunYn5SoWTIS9Ydu07X7uBcTeFBcKfH0xg4QlsNppiM5lIxBbp0WjQ8jyWw+b
Lyef4N6hmiaOf6P6qwaVZkEBhK6MVf1zadURuUSWAkhwGFjA7IbjbJ7OfYLXkYp3
mIrXQzjxz6AfyOcY/FsgcaDLf5xbYw==
-----END CERTIFICATE-----

99
tools/casign/casign.go Normal file
View File

@@ -0,0 +1,99 @@
package main
import (
"crypto/rand"
"crypto/rsa"
"crypto/x509"
"crypto/x509/pkix"
"encoding/pem"
"fmt"
"math/big"
"os"
"time"
)
func main() {
// 生成私钥
privateKey, err := rsa.GenerateKey(rand.Reader, 2048)
if err != nil {
fmt.Println("Failed to generate private key:", err)
return
}
// 创建根证书模板
ca := &x509.Certificate{
SerialNumber: big.NewInt(2023),
Subject: pkix.Name{CommonName: "Root CA"},
NotBefore: time.Now(),
NotAfter: time.Now().AddDate(10, 0, 0), // 有效期为10年
KeyUsage: x509.KeyUsageCertSign | x509.KeyUsageCRLSign,
BasicConstraintsValid: true,
IsCA: true,
}
// 使用私钥对根证书进行签名
caBytes, err := x509.CreateCertificate(rand.Reader, ca, ca, &privateKey.PublicKey, privateKey)
if err != nil {
fmt.Println("Failed to create CA certificate:", err)
return
}
// 将根证书保存到文件
caFile, err := os.Create("ca_cert.pem")
if err != nil {
fmt.Println("Failed to create CA certificate file:", err)
return
}
defer caFile.Close()
err = pem.Encode(caFile, &pem.Block{
Type: "CERTIFICATE",
Bytes: caBytes,
})
if err != nil {
fmt.Println("Failed to write CA certificate to file:", err)
return
}
fmt.Println("Root CA certificate generated successfully.")
// 将公钥保存到文件
publicKeyBytes := x509.MarshalPKCS1PublicKey(&privateKey.PublicKey)
publicKeyFile, err := os.Create("public_key.pem")
if err != nil {
fmt.Println("Failed to create public key file:", err)
return
}
defer publicKeyFile.Close()
err = pem.Encode(publicKeyFile, &pem.Block{
Type: "RSA PUBLIC KEY",
Bytes: publicKeyBytes,
})
if err != nil {
fmt.Println("Failed to write public key to file:", err)
return
}
fmt.Println("Public key generated successfully.")
// 将私钥保存到文件
privateKeyBytes := x509.MarshalPKCS1PrivateKey(privateKey)
privateKeyFile, err := os.Create("private_key.pem")
if err != nil {
fmt.Println("Failed to create private key file:", err)
return
}
defer privateKeyFile.Close()
err = pem.Encode(privateKeyFile, &pem.Block{
Type: "RSA PRIVATE KEY",
Bytes: privateKeyBytes,
})
if err != nil {
fmt.Println("Failed to write private key to file:", err)
return
}
fmt.Println("Private key generated successfully.")
}

View File

@@ -0,0 +1,27 @@
-----BEGIN RSA PRIVATE KEY-----
MIIEpAIBAAKCAQEAlE3BYk9Rk2avUTik7lpuiHxbYTusrLYRCnr8JICRg0QsBfiu
q8d4+4s0w3y5F7puTj23Hf8ohAeNGK6vV9nJF9utMRvT4w5hlGqvKubM2vORoNoa
1usIixfcvMmCt/7++9endMurLY7e9aR+eeEffJtMx5G5JqxRGoFkeXBKFTOjD2ad
sHQ5zhQQUYgdQa2xzKQBYiierKKptcoVMAnnkfx7NPSRfCnzhYVeKgBFbxNXL4h7
nAhLywWhusQc2yr2Fdojj7urtqPNfMKYapkmWKI9/zuPxMlYL49VXUqppE0rnYoi
ISwGvP9iSq1tb+8BUI0ZMDcHX4elEeZYiFMJOwIDAQABAoIBAFVJVhIsXVRwdBg4
hBkS5ogVRBPp1obIeYpWadSwH36m4M5aUlE1eKzoRGK7wlIUA8V5FmroxysOkKUG
KI5UD6Jp0fLw9uyX46QPqkb4zgyIkFI5u7+nEJW1Flt3Y3Ze7dJ1FbdEPWAIzs3j
WFzNC2eEhCYs9pZ3+HhOuzJfUitYU6ts83tazSms+7E027e/v2ubtYOzluEoj4YK
MM+ocqJOlXUOhyTATDaLs4fM567bwwFeriODQqmMIhXLf3HiBPfPYhoAlwPUV51L
bAjIPwG2/jy0yXPenYOUqSMP1i+XkyTL4eVqOLLQUI+BsEaToS8M7Lf4KRQE0vQm
uAkEA9ECgYEAxCsKXtkYXrma8UziSJgQBj88TfACyuYZBPkpBFJhffPVOreYzqmn
gsE38oHlLhCrezsxvScivS/Cwt7kgBTE9r6xmH8y2f0P3PNmtazQCqovG1gsNZ1t
9PZQmxbVUfx/7KRJ1Q5zX3x5C0P2c6XYv/1h/SQQ8PYXDhRxWZFVSikCgYEAwYlt
AoP8j6yHDMk10vJd0fKT1lztcHcQLvH3HQn2kHci2GCxySvcac49hpXTDeNdUzcQ
I9UWo1MggNojME3WHUTiZD5DYUzuNUBTkc0kMHWy79/YNAzvF9312MSyJ0NlytBQ
ISh0z0sPSxDjW+XCi/8LGu1rrremBqvh0rNIrMMCgYEAt+C8VNHcZRZHpX3y8icP
hjuKFGgwxe3Pb/j5uKJb3ktMCUEFjFo8uXTSM5AMuhRIGTgQVIS1rG5zemSh/Wj6
g2uWXyKEEQ+D6hGBqjP1wrlpdJE+x3btFdw5DFbn2HT9mF0bFAn6nXu4npWzEw5X
UQd67WT8OFIEpF8HLPTs5JkCgYBQlL6dmITU8Vm9mh1d+mnT23NwgnqeJATJ9xcT
sS1HE0Of4grEHw4Dw8pcOg+JLcyStE91C+kEEb1ryOdz2kS3JRI5+K6nWZeo9mKV
R1u1DZx2QbZMXcJDJriRC7y9mlNMsZVbaPPRx4fTknGHts9c6NEf4hC+y1pGVtSM
nPc6bwKBgQCrtb6srow9o0acH7mMmieDuqvT8DQ6rHWoizgneZTuvIo6SPO6nRnR
jfgfQkqr9IiLh9awSblQEN9fnddog7a1yS4cUZueiP5dmtFvp4B9Scnt+BoHpOLk
rrU2i7grAye4Cd003+pqhSERGCKSzb3fTSYiMypKsxeH2bs8nrRu2A==
-----END RSA PRIVATE KEY-----

View File

@@ -0,0 +1,8 @@
-----BEGIN RSA PUBLIC KEY-----
MIIBCgKCAQEAlE3BYk9Rk2avUTik7lpuiHxbYTusrLYRCnr8JICRg0QsBfiuq8d4
+4s0w3y5F7puTj23Hf8ohAeNGK6vV9nJF9utMRvT4w5hlGqvKubM2vORoNoa1usI
ixfcvMmCt/7++9endMurLY7e9aR+eeEffJtMx5G5JqxRGoFkeXBKFTOjD2adsHQ5
zhQQUYgdQa2xzKQBYiierKKptcoVMAnnkfx7NPSRfCnzhYVeKgBFbxNXL4h7nAhL
ywWhusQc2yr2Fdojj7urtqPNfMKYapkmWKI9/zuPxMlYL49VXUqppE0rnYoiISwG
vP9iSq1tb+8BUI0ZMDcHX4elEeZYiFMJOwIDAQAB
-----END RSA PUBLIC KEY-----

137
tools/cmca/ca.go Normal file
View File

@@ -0,0 +1,137 @@
package main
import (
"crypto"
"crypto/rand"
"crypto/rsa"
"crypto/sha256"
"crypto/x509"
"encoding/pem"
"fmt"
"os"
)
// LoadCert 读取证书文件
func LoadCert(path string) (*x509.Certificate, error) {
//1.打开磁盘的公钥文件
file, err := os.Open(path)
if err != nil {
return nil, err
}
defer file.Close()
fileInfo, err := file.Stat()
if err != nil {
return nil, err
}
buf := make([]byte, fileInfo.Size())
_, err = file.Read(buf)
if err != nil {
return nil, err
}
//2.使用pem解码得到pem.Block结构体变量
block, _ := pem.Decode(buf)
//证书解析
certBody, err := x509.ParseCertificate(block.Bytes)
if err != nil {
return nil, err
}
return certBody, nil
}
// LoadPriKey 读取私钥文件
func LoadPriKey(path string) (*rsa.PrivateKey, error) {
//1.打开磁盘的私钥文件
file, err := os.Open(path)
if err != nil {
return nil, err
}
defer file.Close()
//2.将私钥文件中的内容读出
fileInfo, err := file.Stat()
if err != nil {
return nil, err
}
buf := make([]byte, fileInfo.Size())
_, err = file.Read(buf)
if err != nil {
return nil, err
}
//3.使用pem对数据解码得到pem.Block结构体变量
block, _ := pem.Decode(buf)
//4.x509将数据解析成私钥结构体得到私钥
privateKey, err := x509.ParsePKCS1PrivateKey(block.Bytes)
if err != nil {
return nil, err
}
return privateKey, nil
}
// SignRSA RSA 签名
func SignRSA(plainText []byte, priKey *rsa.PrivateKey) ([]byte, error) {
//1.创建一个哈希对象
hash := sha256.New()
//2.给哈希对象添加数据
_, err := hash.Write(plainText)
if err != nil {
return nil, err
}
//3.计算哈希值
hashed := hash.Sum(nil)
//4.使用rsa中的函数对散列值签名
signText, err := rsa.SignPKCS1v15(rand.Reader, priKey, crypto.SHA256, hashed)
if err != nil {
return nil, err
}
return signText, nil
}
func VerifyRSA(plainText, signText []byte, cert *x509.Certificate) error {
publicKeyDer, err := x509.MarshalPKIXPublicKey(cert.PublicKey)
if err != nil {
return err
}
pubKeyInterface, err := x509.ParsePKIXPublicKey(publicKeyDer)
if err != nil {
return err
}
//进行类型断言得到公钥结构体
publicKey := pubKeyInterface.(*rsa.PublicKey)
//* 创建哈希接口
hash := sha256.New()
//* 添加数据
hash.Write(plainText)
//* 哈希运算
hasded := hash.Sum(nil)
//
//6.签名认证
err = rsa.VerifyPKCS1v15(publicKey, crypto.SHA256, hasded, signText)
if err != nil {
return err
}
return nil
}
var rootCertPool *x509.CertPool
func VerifyCert(cert *x509.Certificate) error {
//block, _ := pem.Decode([]byte(certPEM))
//if block == nil {
// return fmt.Errorf("failed to parse certificate PEM")
//}
//cert, err := x509.ParseCertificate(block.Bytes)
//if err != nil {
// return fmt.Errorf("failed to parse certificate: %v", err.Error())
//}
opts := x509.VerifyOptions{
Roots: rootCertPool,
}
if _, err := cert.Verify(opts); err != nil {
return fmt.Errorf("failed to verify certificate: %v", err.Error())
}
return nil
}

View File

@@ -0,0 +1,81 @@
Certificate:
Data:
Version: 3 (0x2)
Serial Number: 1 (0x1)
Signature Algorithm: sha256WithRSAEncryption
Issuer: C=CN, ST=GD, L=shenzhen, O=https://www.agrandtech.com.cn/, CN=test
Validity
Not Before: Jul 1 10:05:48 2023 GMT
Not After : Mar 27 10:05:48 2026 GMT
Subject: C=CN, ST=GD, O=https://www.agrandtech.com.cn/, CN=test
Subject Public Key Info:
Public Key Algorithm: rsaEncryption
RSA Public-Key: (2048 bit)
Modulus:
00:f3:bd:e9:fe:aa:a6:c1:d9:7b:74:20:f0:d0:f3:
ee:7c:d0:69:84:8d:1a:37:1e:29:42:98:86:51:87:
fe:5d:48:2e:97:b0:c6:16:9c:46:6a:38:7b:34:54:
ec:76:d2:52:50:bb:31:a8:de:7d:3f:8c:c5:f8:fb:
e3:e3:73:37:36:10:e8:55:df:80:cf:c0:d9:40:30:
b7:54:49:69:e3:a8:79:49:47:d8:74:b0:07:13:dd:
47:72:89:69:bd:0c:40:8b:f4:ee:49:02:cb:f4:b9:
c1:7a:7d:da:10:1b:b2:b1:9f:0d:70:66:d1:86:31:
dc:e3:d6:e5:f5:2c:e1:57:bd:72:ea:4a:1d:0c:4c:
58:09:2b:2e:e5:53:40:73:55:e9:78:c3:7a:95:25:
b7:9d:80:ac:e4:79:c3:d7:9b:d1:c3:73:78:da:03:
f4:aa:68:21:81:f2:53:b8:3d:91:60:e0:91:47:2e:
6d:5d:01:ae:f2:82:c0:8a:dd:06:8c:70:6e:77:7e:
14:ae:61:a5:d8:e0:13:1b:2c:f7:d3:62:0c:d1:5c:
48:fe:59:ca:b5:b1:2b:89:2b:2f:69:5d:40:42:05:
ab:76:58:4f:36:1a:36:1c:21:eb:85:1c:da:22:1b:
c2:60:8e:c1:7d:50:33:39:c0:40:e0:49:20:a0:f7:
c3:4f
Exponent: 65537 (0x10001)
X509v3 extensions:
X509v3 Basic Constraints:
CA:FALSE
Netscape Comment:
OpenSSL Generated Certificate
X509v3 Subject Key Identifier:
D7:A0:3F:5F:C0:65:83:88:6F:5E:98:DB:30:3D:9F:24:6A:D0:DE:54
X509v3 Authority Key Identifier:
keyid:6D:B3:1D:B6:78:4E:C8:19:8F:FA:4D:6B:3A:5E:A9:7D:CB:07:98:BA
Signature Algorithm: sha256WithRSAEncryption
39:8a:89:a2:79:0f:c0:fd:d8:db:d5:38:d2:03:b4:38:be:a2:
6e:6b:1c:28:93:0a:a6:0b:af:0a:69:6b:8b:d5:df:3d:de:76:
ad:24:23:98:7a:21:a1:2f:90:47:9b:98:9e:d2:b4:75:21:bd:
d0:38:34:6b:b1:96:3d:24:da:ac:1a:45:e4:01:1d:a2:20:c3:
43:d3:ec:d9:2d:3b:d1:ee:0d:1e:21:15:e7:7f:d3:95:1c:dc:
fa:88:3a:05:4b:c5:08:5d:f4:40:89:29:80:fe:6b:40:b9:34:
92:2e:48:94:d2:4b:0b:4d:1e:3c:64:17:cf:34:ec:36:5c:6d:
3d:90:9c:74:95:d7:c8:96:a2:70:59:4a:d2:b5:e1:c1:a9:b7:
ad:f0:99:ff:b4:4d:89:e7:e3:9d:7d:79:36:40:05:6d:20:46:
54:af:18:73:c9:07:17:26:18:86:99:cc:e2:58:27:96:84:58:
18:d4:fe:dc:36:cd:8a:48:cc:e6:51:27:e5:76:81:2f:c7:9c:
7b:f9:fb:19:c9:7c:e4:27:06:75:cd:16:88:74:3c:0b:23:d6:
86:6b:95:41:10:cf:b2:fc:e8:1e:e0:d6:a5:8c:d1:c0:1b:d5:
6e:15:8c:9a:67:5c:9d:ac:02:5a:69:17:e8:4c:42:d0:5d:88:
da:08:4e:c0
-----BEGIN CERTIFICATE-----
MIIDrTCCApWgAwIBAgIBATANBgkqhkiG9w0BAQsFADBlMQswCQYDVQQGEwJDTjEL
MAkGA1UECAwCR0QxETAPBgNVBAcMCHNoZW56aGVuMScwJQYDVQQKDB5odHRwczov
L3d3dy5hZ3JhbmR0ZWNoLmNvbS5jbi8xDTALBgNVBAMMBHRlc3QwHhcNMjMwNzAx
MTAwNTQ4WhcNMjYwMzI3MTAwNTQ4WjBSMQswCQYDVQQGEwJDTjELMAkGA1UECAwC
R0QxJzAlBgNVBAoMHmh0dHBzOi8vd3d3LmFncmFuZHRlY2guY29tLmNuLzENMAsG
A1UEAwwEdGVzdDCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAPO96f6q
psHZe3Qg8NDz7nzQaYSNGjceKUKYhlGH/l1ILpewxhacRmo4ezRU7HbSUlC7Maje
fT+Mxfj74+NzNzYQ6FXfgM/A2UAwt1RJaeOoeUlH2HSwBxPdR3KJab0MQIv07kkC
y/S5wXp92hAbsrGfDXBm0YYx3OPW5fUs4Ve9cupKHQxMWAkrLuVTQHNV6XjDepUl
t52ArOR5w9eb0cNzeNoD9KpoIYHyU7g9kWDgkUcubV0BrvKCwIrdBoxwbnd+FK5h
pdjgExss99NiDNFcSP5ZyrWxK4krL2ldQEIFq3ZYTzYaNhwh64Uc2iIbwmCOwX1Q
MznAQOBJIKD3w08CAwEAAaN7MHkwCQYDVR0TBAIwADAsBglghkgBhvhCAQ0EHxYd
T3BlblNTTCBHZW5lcmF0ZWQgQ2VydGlmaWNhdGUwHQYDVR0OBBYEFNegP1/AZYOI
b16Y2zA9nyRq0N5UMB8GA1UdIwQYMBaAFG2zHbZ4TsgZj/pNazpeqX3LB5i6MA0G
CSqGSIb3DQEBCwUAA4IBAQA5iomieQ/A/djb1TjSA7Q4vqJuaxwokwqmC68KaWuL
1d893natJCOYeiGhL5BHm5ie0rR1Ib3QODRrsZY9JNqsGkXkAR2iIMND0+zZLTvR
7g0eIRXnf9OVHNz6iDoFS8UIXfRAiSmA/mtAuTSSLkiU0ksLTR48ZBfPNOw2XG09
kJx0ldfIlqJwWUrSteHBqbet8Jn/tE2J5+OdfXk2QAVtIEZUrxhzyQcXJhiGmczi
WCeWhFgY1P7cNs2KSMzmUSfldoEvx5x7+fsZyXzkJwZ1zRaIdDwLI9aGa5VBEM+y
/Oge4NaljNHAG9VuFYyaZ1ydrAJaaRfoTELQXYjaCE7A
-----END CERTIFICATE-----

View File

@@ -0,0 +1,81 @@
Certificate:
Data:
Version: 3 (0x2)
Serial Number: 2 (0x2)
Signature Algorithm: sha256WithRSAEncryption
Issuer: C=CN, ST=GD, L=shenzhen, O=https://www.agrandtech.com.cn/, CN=test
Validity
Not Before: Jul 1 10:08:44 2023 GMT
Not After : Mar 27 10:08:44 2026 GMT
Subject: C=CN, ST=GD, O=https://www.agrandtech.com.cn/, CN=test1
Subject Public Key Info:
Public Key Algorithm: rsaEncryption
RSA Public-Key: (2048 bit)
Modulus:
00:ed:73:63:a4:7d:8c:00:e6:e5:df:f5:1e:8a:d4:
22:e4:37:16:62:6b:64:f1:90:ec:4b:4c:37:c5:2e:
de:ef:11:93:15:da:e9:2d:7b:69:72:2d:94:29:f8:
04:75:22:37:a4:83:53:a3:7b:b1:37:2d:a0:57:af:
0e:65:3c:cf:fe:1a:65:de:e8:66:7b:19:81:ab:10:
9b:9e:27:5b:a9:7c:cc:3a:44:ee:6e:af:3a:ef:67:
72:60:a8:8d:bb:4d:3e:ce:34:1f:08:9c:72:f7:52:
44:d7:af:eb:f7:9b:3f:62:94:09:db:26:e3:0f:eb:
b3:85:d3:c3:2d:ec:c1:14:d8:2d:b0:4c:10:c7:b1:
22:cf:74:a7:cd:94:b7:18:9e:78:0b:0b:64:00:e0:
e1:8a:97:57:11:5d:7c:f3:c9:6c:e0:97:c1:6c:01:
b5:c4:75:fa:71:96:9a:89:c7:73:61:bd:4a:2b:28:
17:81:4b:9f:92:ee:8e:a0:57:7f:7a:7c:89:a6:7e:
4d:a8:f3:b8:aa:03:aa:de:30:a7:19:94:a7:87:fc:
ab:5a:e5:8d:a9:64:51:5a:f4:ad:64:e1:aa:e4:45:
b7:e4:03:dc:6b:cf:fa:4a:0d:09:ef:4f:82:39:cc:
2f:91:c1:94:55:57:58:16:0b:14:00:62:43:c9:67:
e0:d3
Exponent: 65537 (0x10001)
X509v3 extensions:
X509v3 Basic Constraints:
CA:FALSE
Netscape Comment:
OpenSSL Generated Certificate
X509v3 Subject Key Identifier:
51:A3:41:B8:14:F9:2C:04:DE:0C:49:24:58:B5:5A:34:0E:07:FE:40
X509v3 Authority Key Identifier:
keyid:6D:B3:1D:B6:78:4E:C8:19:8F:FA:4D:6B:3A:5E:A9:7D:CB:07:98:BA
Signature Algorithm: sha256WithRSAEncryption
3c:f2:58:cd:8c:39:90:b4:f5:0f:ef:f6:a7:eb:26:4c:43:63:
dc:9f:94:a1:43:6c:9a:82:2b:e4:8e:24:c5:40:da:78:93:c5:
dd:8a:5d:63:76:00:ef:c6:ca:a7:a8:10:a3:9a:ae:d1:20:d1:
19:e1:46:03:03:98:a4:71:9a:45:8d:34:33:ce:c8:52:82:22:
33:5f:79:74:61:88:ab:52:6f:98:75:8f:07:bf:ff:d9:2e:30:
67:ce:05:8b:6c:ac:24:ec:2c:ac:c5:42:f7:71:b6:da:53:bc:
48:d1:29:82:aa:03:27:81:84:0a:f5:12:e2:8c:3a:77:f9:a8:
0e:d4:1f:7e:1f:98:28:f7:15:f0:78:8a:ba:b7:77:20:b7:82:
0d:cd:d5:47:ed:9e:61:a7:9b:35:1b:35:c7:74:91:0b:6c:1c:
27:1a:a9:cc:11:5b:22:0d:35:40:43:ae:f2:44:66:aa:9e:dc:
22:ca:a7:8b:8c:44:6a:f6:b1:6d:1e:3a:51:c0:2a:02:81:d7:
b6:4a:77:1e:e0:13:19:0c:51:4c:67:e1:2f:97:c9:4a:88:25:
c8:b4:65:dc:0d:a5:71:c2:45:dd:4f:01:bf:f0:43:9c:41:37:
28:eb:15:fc:90:f8:b6:3a:4b:57:79:df:74:4c:a9:aa:27:a2:
77:22:37:7f
-----BEGIN CERTIFICATE-----
MIIDrjCCApagAwIBAgIBAjANBgkqhkiG9w0BAQsFADBlMQswCQYDVQQGEwJDTjEL
MAkGA1UECAwCR0QxETAPBgNVBAcMCHNoZW56aGVuMScwJQYDVQQKDB5odHRwczov
L3d3dy5hZ3JhbmR0ZWNoLmNvbS5jbi8xDTALBgNVBAMMBHRlc3QwHhcNMjMwNzAx
MTAwODQ0WhcNMjYwMzI3MTAwODQ0WjBTMQswCQYDVQQGEwJDTjELMAkGA1UECAwC
R0QxJzAlBgNVBAoMHmh0dHBzOi8vd3d3LmFncmFuZHRlY2guY29tLmNuLzEOMAwG
A1UEAwwFdGVzdDEwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDtc2Ok
fYwA5uXf9R6K1CLkNxZia2TxkOxLTDfFLt7vEZMV2ukte2lyLZQp+AR1Ijekg1Oj
e7E3LaBXrw5lPM/+GmXe6GZ7GYGrEJueJ1upfMw6RO5urzrvZ3JgqI27TT7ONB8I
nHL3UkTXr+v3mz9ilAnbJuMP67OF08Mt7MEU2C2wTBDHsSLPdKfNlLcYnngLC2QA
4OGKl1cRXXzzyWzgl8FsAbXEdfpxlpqJx3NhvUorKBeBS5+S7o6gV396fImmfk2o
87iqA6reMKcZlKeH/Kta5Y2pZFFa9K1k4arkRbfkA9xrz/pKDQnvT4I5zC+RwZRV
V1gWCxQAYkPJZ+DTAgMBAAGjezB5MAkGA1UdEwQCMAAwLAYJYIZIAYb4QgENBB8W
HU9wZW5TU0wgR2VuZXJhdGVkIENlcnRpZmljYXRlMB0GA1UdDgQWBBRRo0G4FPks
BN4MSSRYtVo0Dgf+QDAfBgNVHSMEGDAWgBRtsx22eE7IGY/6TWs6Xql9yweYujAN
BgkqhkiG9w0BAQsFAAOCAQEAPPJYzYw5kLT1D+/2p+smTENj3J+UoUNsmoIr5I4k
xUDaeJPF3YpdY3YA78bKp6gQo5qu0SDRGeFGAwOYpHGaRY00M87IUoIiM195dGGI
q1JvmHWPB7//2S4wZ84Fi2ysJOwsrMVC93G22lO8SNEpgqoDJ4GECvUS4ow6d/mo
DtQffh+YKPcV8HiKurd3ILeCDc3VR+2eYaebNRs1x3SRC2wcJxqpzBFbIg01QEOu
8kRmqp7cIsqni4xEavaxbR46UcAqAoHXtkp3HuATGQxRTGfhL5fJSoglyLRl3A2l
ccJF3U8Bv/BDnEE3KOsV/JD4tjpLV3nfdEypqieidyI3fw==
-----END CERTIFICATE-----

View File

@@ -0,0 +1,17 @@
-----BEGIN CERTIFICATE REQUEST-----
MIICqjCCAZICAQAwZTELMAkGA1UEBhMCQ04xCzAJBgNVBAgMAkdEMREwDwYDVQQH
DAhzaGVuemhlbjEnMCUGA1UECgweaHR0cHM6Ly93d3cuYWdyYW5kdGVjaC5jb20u
Y24vMQ0wCwYDVQQDDAR0ZXN0MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKC
AQEA873p/qqmwdl7dCDw0PPufNBphI0aNx4pQpiGUYf+XUgul7DGFpxGajh7NFTs
dtJSULsxqN59P4zF+Pvj43M3NhDoVd+Az8DZQDC3VElp46h5SUfYdLAHE91Hcolp
vQxAi/TuSQLL9LnBen3aEBuysZ8NcGbRhjHc49bl9SzhV71y6kodDExYCSsu5VNA
c1XpeMN6lSW3nYCs5HnD15vRw3N42gP0qmghgfJTuD2RYOCRRy5tXQGu8oLAit0G
jHBud34UrmGl2OATGyz302IM0VxI/lnKtbEriSsvaV1AQgWrdlhPNho2HCHrhRza
IhvCYI7BfVAzOcBA4EkgoPfDTwIDAQABoAAwDQYJKoZIhvcNAQELBQADggEBAE7E
xGSbr/UbRNE3dzD42GnTRTUCJGgk0sUFgURfuZhKhFNSloEQBzfL7hb4M2uuirOB
t8NxImkp70/3Cw+UuewBAO5Ajp6GIYr4dZGb1KNWxqFMC1k0RCoEDcRPow5+okzf
d8QbHVQnyYNahAfxWdxLmq9g3dBmJA9d3Z4XfbPWbp3sDk7fb08Fg9Uond33vW1J
Qzco4UTcwLuicNwh6vytikjUV5zX0RS9QHSu9+akMbZbOwX9cFOhjbpmw4oGLx8h
fXeB9pgqbvdQ4Q5Bj+bScK2CR344yKY6nEw4pxdS78a7Sor+njSgvNlbBzjg+EP0
UpTObJ9sModlMYn6h70=
-----END CERTIFICATE REQUEST-----

View File

@@ -0,0 +1,27 @@
-----BEGIN RSA PRIVATE KEY-----
MIIEowIBAAKCAQEA873p/qqmwdl7dCDw0PPufNBphI0aNx4pQpiGUYf+XUgul7DG
FpxGajh7NFTsdtJSULsxqN59P4zF+Pvj43M3NhDoVd+Az8DZQDC3VElp46h5SUfY
dLAHE91HcolpvQxAi/TuSQLL9LnBen3aEBuysZ8NcGbRhjHc49bl9SzhV71y6kod
DExYCSsu5VNAc1XpeMN6lSW3nYCs5HnD15vRw3N42gP0qmghgfJTuD2RYOCRRy5t
XQGu8oLAit0GjHBud34UrmGl2OATGyz302IM0VxI/lnKtbEriSsvaV1AQgWrdlhP
Nho2HCHrhRzaIhvCYI7BfVAzOcBA4EkgoPfDTwIDAQABAoIBAFTFQ0GABnk681XD
Mx3pCJO+RESGcoyi38S6mVR30L6OoS2+nFY2ycKdnDPqKUd2BIzxXecWYkcc5amf
qXVsl9Ik9TkQf5NBxg0uJESbN8mmyW/0HdMPeZauCfBK3EyUm0pRyCH6aAbYJ/M7
HAEoMPDXmWvzRoG+i81t6xJnJoRFwI8xQfKf6DbiP4KUlU7MVRWpVFkCXzZkyoqi
NWKyYfv7cBTZrWpeBCvyKRtUDvA9xjgfRTmR5rBfre9XCcu0hD2HwYBR8Nh0kz0g
4/ZgEX4LYpL40r/tbzL1hlG2zaKQw/Hmb90CvUBfwwNFA/Xvhq5NYJhwVaauPhVN
vDxIf/ECgYEA/gyooDz0B/OGSDeetBuZyQ1HjlWc7wNSCG+SBbaDb5WCLAcJCOEc
ybCg81s3P1p4IRo1BR0II1RM8RHhMLVlL/NgYQsvpYJd/02BTxYQka7EXXOdL533
CuKYTEKODisSSjNPF051kADHs0iL5Jc8iDT21Rb8C6E4N1J1lCEWsCkCgYEA9Zz+
16P7UVKGZzEF6/xtOf59H+Arrty9eW9nlGH+Wjkz+xySYAVSaa/6n6LiBGOwXvKc
GmUSMhanIgvnTXVkwpCEAl6cVufwuPR5V0Y66xnSsAtpascJqvCgVAxS9b0SVAju
WvExxRrEquvYUlZ7kwN2a8Rnm02BjFPijy8D5rcCgYBZWApVkBoiUbp/20+s96f1
1P29SM6QIBLRdKtd5voCXAoTgcXjoYeGRt/TtdiQJzjoK1dKHROnmRYWEbuobaLQ
Yj8a4dw30MlN5+v57ECXe2cDlo1JGbyvz1DQQPfEc9FS1wiRob4mjp+spW7NTYK0
RCwqdJLfZCtpCU7gcWKRQQKBgG9DB064Qgi80ZW9Z2lXmENFPXlLG37DEDIKfWmC
Wq6Uay+96bEFuCeYSHg4WRqT7jmUvZJXZr659ExACC/WliZtQN+x7DCSMUIXvUAD
2HzX3dFR2hc8wuxkxLxOOOaJF9xpj1AzItCfJ6gl3oCuHJykXOjEuApqOd1PwroK
GkJRAoGBANzf7rFrVxapMa5W/Q5fGFMwzF6sKPU0xZUhYKen0jwndl4NEQakWoiI
oWjeeFgPoKQa7LPfwfPEsCNTt3D/7ow/5kk39kTpegmICDcF+f1ij8w5ekuw4QyO
ltQsHXNdzdulT8Mhg1+R6EabgvBGZEFyWMH2yeF3QKhg6ezRAzcV
-----END RSA PRIVATE KEY-----

View File

@@ -0,0 +1,17 @@
-----BEGIN CERTIFICATE REQUEST-----
MIICqzCCAZMCAQAwZjELMAkGA1UEBhMCQ04xCzAJBgNVBAgMAkdEMREwDwYDVQQH
DAhzaGVuemhlbjEnMCUGA1UECgweaHR0cHM6Ly93d3cuYWdyYW5kdGVjaC5jb20u
Y24vMQ4wDAYDVQQDDAV0ZXN0MTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoC
ggEBAO1zY6R9jADm5d/1HorUIuQ3FmJrZPGQ7EtMN8Uu3u8RkxXa6S17aXItlCn4
BHUiN6SDU6N7sTctoFevDmU8z/4aZd7oZnsZgasQm54nW6l8zDpE7m6vOu9ncmCo
jbtNPs40HwiccvdSRNev6/ebP2KUCdsm4w/rs4XTwy3swRTYLbBMEMexIs90p82U
txieeAsLZADg4YqXVxFdfPPJbOCXwWwBtcR1+nGWmonHc2G9SisoF4FLn5LujqBX
f3p8iaZ+TajzuKoDqt4wpxmUp4f8q1rljalkUVr0rWThquRFt+QD3GvP+koNCe9P
gjnML5HBlFVXWBYLFABiQ8ln4NMCAwEAAaAAMA0GCSqGSIb3DQEBCwUAA4IBAQBh
7RKvFZzrt7cDmIPEaTpXZnXKbSaU6Yq4PzG6mnG0B2wd15wZ41nVQobprVEd/hIY
ifjtTh0fZp7IBhBomX2QJWlhqdK4RvlMDX9w0Q6oSYjbHKj7TfGnBpyi5gjK/a12
cQvupDTXWp5Hq5McnBKdo/SDow1papl4jFkGeNq8ItD+2FQQhcJGMLnNndQ9p9Mj
3TRtcfxbsJgmDHBQyefM5ASnG4j5X7wi2zSdgN9hEFIzm9weFpYGAnNx431BE0Vg
9bR1YWFBPzjMI4x5DN7HWt+z5acZlXjws2OM68zum3MR7UbreV/eJjtE3Un9AuNW
e5nUqnFMJ7RVZnTvPlGz
-----END CERTIFICATE REQUEST-----

View File

@@ -0,0 +1,27 @@
-----BEGIN RSA PRIVATE KEY-----
MIIEpAIBAAKCAQEA7XNjpH2MAObl3/UeitQi5DcWYmtk8ZDsS0w3xS7e7xGTFdrp
LXtpci2UKfgEdSI3pINTo3uxNy2gV68OZTzP/hpl3uhmexmBqxCbnidbqXzMOkTu
bq8672dyYKiNu00+zjQfCJxy91JE16/r95s/YpQJ2ybjD+uzhdPDLezBFNgtsEwQ
x7Eiz3SnzZS3GJ54CwtkAODhipdXEV1888ls4JfBbAG1xHX6cZaaicdzYb1KKygX
gUufku6OoFd/enyJpn5NqPO4qgOq3jCnGZSnh/yrWuWNqWRRWvStZOGq5EW35APc
a8/6Sg0J70+COcwvkcGUVVdYFgsUAGJDyWfg0wIDAQABAoIBAQCWcM8mvmxffesS
s8iACNt6X/SMsqIn8rvjEQ0cnw+bxDS+Wg32RQSP1JTU6lBYri82ygXJxGqJHR1D
sKOcPKVCxxLX4cJcJ9LhwQn3b9RBU9JI8Ldn5Rmf6Jis6N2zV8N8/cTTvduRGsyH
IuyL2g6UtFpyQPcHdTwug/ZbOG80dnI9Z4qWFLKe5JFgsrpTyOIC9ta8CcHYNZiV
uSPYEH/CWvgZQOc6VpfnnNefiLxMKq2Tbpk/FbioUiqGwxtWBmE9YyFvtSpUb/TU
MKwPidMV/0V7wRQafjD3qL/Y2V8ZVaEnwVAT8GjQECPCLPON6i8gr/oi6bVrpwb4
B8tixqWBAoGBAPj36K5ofGPVi2TsK78q3+pPKrGL1HHpdloVglME+8H1AbMf1nBX
iH2T4iAR4o13KDa0gc3vUttW1P8fiTTGHL32mF6gvUPG2u3T9riZoKGQ+2aKHG6e
0MwcXmq53WwLseNykwb2qOSISBSkjjv4mkbpuOrurOF0UMKnA04k9eizAoGBAPQo
NJOZTQiLW61ckc1Cy3pDtW4dTKsAomt8Aw6AbZyZUqP3smB/DhnsHXe3W84f6DZC
pkIvnX7WMWQLLBEpe09rKfhWMGbk8gGo9sOf0RYVE93rwxFVA/sXSle4HeGur2ku
YgaJ86YGRgN4ctb9CCZ3IqZmL5jds73ajmAHcvdhAoGAPBdJ996MN2RxUpiWLnvg
s6MMAPJpAl2BDVknrXYEddn24Q8MKO1XqkepSmhGsDJUaG/E7LmY3AvnOPSZnz05
7re4Kw7M37D9Ym3InOGnnZdqtmMbXa/DYaBvQX8+7DceZnFe/01FknM6QpE9K0hj
pD4BPeMBoyD55SF+cLwHBnUCgYBypPJTIBe43F7231GjFSsgROzLQLzASvL5D2kM
BSfy8VeJoIREpUREzcbkcNeNyROrbs5Mo7kLVp4ogMp3YIgDOamiby4ZEoXEW8dL
Ah8WhF0oxkx5NfdBjqUc3VpCn1jERcBHm70phyaW+JbL9lI+ZZCCm9bbq7Z7fkV+
N+E24QKBgQDNKwrWWtm5GAf8CFxE8ZSyqa3Si9Fa65GIb+5ful8VuklK6bhGkCjd
gV0zDTBnV0Cm7CBhGsKaXGy49J7Ti5BwFv/txEsnU0ZmC7qXKExckm/gJ/uer0QU
XWCIGtHDn2UNtv1wS6MBIYEeb09aoUhjFDXLPDNipdLh1Wh25wF2sw==
-----END RSA PRIVATE KEY-----

View File

@@ -0,0 +1,22 @@
-----BEGIN CERTIFICATE-----
MIIDqzCCApOgAwIBAgIUDs5kTQVLnC1MdhXHj0KqYIG+nyAwDQYJKoZIhvcNAQEL
BQAwZTELMAkGA1UEBhMCQ04xCzAJBgNVBAgMAkdEMREwDwYDVQQHDAhzaGVuemhl
bjEnMCUGA1UECgweaHR0cHM6Ly93d3cuYWdyYW5kdGVjaC5jb20uY24vMQ0wCwYD
VQQDDAR0ZXN0MB4XDTIzMDcwMTA4NDQzOFoXDTMzMDYyODA4NDQzOFowZTELMAkG
A1UEBhMCQ04xCzAJBgNVBAgMAkdEMREwDwYDVQQHDAhzaGVuemhlbjEnMCUGA1UE
CgweaHR0cHM6Ly93d3cuYWdyYW5kdGVjaC5jb20uY24vMQ0wCwYDVQQDDAR0ZXN0
MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA0SMdRLkcxy3PKOSCusJ+
AnGiJyW6AxyujqZj4xjgtIFjYIMVW5ZXVbWnY0xzRPddFddnEWgMeMLn9V3zcESV
3tu9exm6Ijop8/KaDJ1EJAESunxkP9x/1ek3kgQvuK3YAcizTeB5ODUZ/KFJw9MP
R/KUB+TYqCp50mr6mlIZE6lvhhvMxHz6ZmOFh2RvYg0h8oXpo5G8nmRVb4gNrlXK
y/HZpGtbm/mfbOtxWgvSFy3PE/49V8nOYJbhDaoOXWVN06Z7w1y4KzSKbIoZfC9C
WdWRrrhIv+Px1QLQItL17kAKqtp+vtG8lZjC5vsAgXLVAZLK71b6onv1Ir3Yuwwf
vQIDAQABo1MwUTAdBgNVHQ4EFgQUbbMdtnhOyBmP+k1rOl6pfcsHmLowHwYDVR0j
BBgwFoAUbbMdtnhOyBmP+k1rOl6pfcsHmLowDwYDVR0TAQH/BAUwAwEB/zANBgkq
hkiG9w0BAQsFAAOCAQEAdGZdTglVP1hI0wcxD0rkkHu7IkfFGlaad1vFL+VfujlV
6H3/WrDLCDhLDBZrdZ3m0LrQqpJjZriOaqc0O8LbT4ktquVuAgYtT/il6EQzLpyE
pEW+iM4Ae2tu9rMH1F365+C8ffQWuSenvQOOjL8L9BP5N0bguVsWA+uMNprMado4
lLuyHOt5S36WOKh4mnMlkDBuCNnBCiFS8rcQXJugk6jrOYKji5wJGNAVMoSEtRvN
LdZh5XOkbXuFrhltPxMG/7BaPc9xS46chBKDvCQPweKGeu2eG+y6KTwCDYmakmVX
OE8TnP4Zr0miTprzkmbWhIkUWkg/FclJs1/TcSkCGw==
-----END CERTIFICATE-----

View File

@@ -0,0 +1,2 @@
V 260327100548Z 01 unknown /C=CN/ST=GD/O=https://www.agrandtech.com.cn//CN=test
V 260327100844Z 02 unknown /C=CN/ST=GD/O=https://www.agrandtech.com.cn//CN=test1

View File

@@ -0,0 +1 @@
unique_subject = yes

View File

@@ -0,0 +1 @@
unique_subject = yes

View File

@@ -0,0 +1 @@
V 260327100548Z 01 unknown /C=CN/ST=GD/O=https://www.agrandtech.com.cn//CN=test

View File

@@ -0,0 +1,81 @@
Certificate:
Data:
Version: 3 (0x2)
Serial Number: 1 (0x1)
Signature Algorithm: sha256WithRSAEncryption
Issuer: C=CN, ST=GD, L=shenzhen, O=https://www.agrandtech.com.cn/, CN=test
Validity
Not Before: Jul 1 10:05:48 2023 GMT
Not After : Mar 27 10:05:48 2026 GMT
Subject: C=CN, ST=GD, O=https://www.agrandtech.com.cn/, CN=test
Subject Public Key Info:
Public Key Algorithm: rsaEncryption
RSA Public-Key: (2048 bit)
Modulus:
00:f3:bd:e9:fe:aa:a6:c1:d9:7b:74:20:f0:d0:f3:
ee:7c:d0:69:84:8d:1a:37:1e:29:42:98:86:51:87:
fe:5d:48:2e:97:b0:c6:16:9c:46:6a:38:7b:34:54:
ec:76:d2:52:50:bb:31:a8:de:7d:3f:8c:c5:f8:fb:
e3:e3:73:37:36:10:e8:55:df:80:cf:c0:d9:40:30:
b7:54:49:69:e3:a8:79:49:47:d8:74:b0:07:13:dd:
47:72:89:69:bd:0c:40:8b:f4:ee:49:02:cb:f4:b9:
c1:7a:7d:da:10:1b:b2:b1:9f:0d:70:66:d1:86:31:
dc:e3:d6:e5:f5:2c:e1:57:bd:72:ea:4a:1d:0c:4c:
58:09:2b:2e:e5:53:40:73:55:e9:78:c3:7a:95:25:
b7:9d:80:ac:e4:79:c3:d7:9b:d1:c3:73:78:da:03:
f4:aa:68:21:81:f2:53:b8:3d:91:60:e0:91:47:2e:
6d:5d:01:ae:f2:82:c0:8a:dd:06:8c:70:6e:77:7e:
14:ae:61:a5:d8:e0:13:1b:2c:f7:d3:62:0c:d1:5c:
48:fe:59:ca:b5:b1:2b:89:2b:2f:69:5d:40:42:05:
ab:76:58:4f:36:1a:36:1c:21:eb:85:1c:da:22:1b:
c2:60:8e:c1:7d:50:33:39:c0:40:e0:49:20:a0:f7:
c3:4f
Exponent: 65537 (0x10001)
X509v3 extensions:
X509v3 Basic Constraints:
CA:FALSE
Netscape Comment:
OpenSSL Generated Certificate
X509v3 Subject Key Identifier:
D7:A0:3F:5F:C0:65:83:88:6F:5E:98:DB:30:3D:9F:24:6A:D0:DE:54
X509v3 Authority Key Identifier:
keyid:6D:B3:1D:B6:78:4E:C8:19:8F:FA:4D:6B:3A:5E:A9:7D:CB:07:98:BA
Signature Algorithm: sha256WithRSAEncryption
39:8a:89:a2:79:0f:c0:fd:d8:db:d5:38:d2:03:b4:38:be:a2:
6e:6b:1c:28:93:0a:a6:0b:af:0a:69:6b:8b:d5:df:3d:de:76:
ad:24:23:98:7a:21:a1:2f:90:47:9b:98:9e:d2:b4:75:21:bd:
d0:38:34:6b:b1:96:3d:24:da:ac:1a:45:e4:01:1d:a2:20:c3:
43:d3:ec:d9:2d:3b:d1:ee:0d:1e:21:15:e7:7f:d3:95:1c:dc:
fa:88:3a:05:4b:c5:08:5d:f4:40:89:29:80:fe:6b:40:b9:34:
92:2e:48:94:d2:4b:0b:4d:1e:3c:64:17:cf:34:ec:36:5c:6d:
3d:90:9c:74:95:d7:c8:96:a2:70:59:4a:d2:b5:e1:c1:a9:b7:
ad:f0:99:ff:b4:4d:89:e7:e3:9d:7d:79:36:40:05:6d:20:46:
54:af:18:73:c9:07:17:26:18:86:99:cc:e2:58:27:96:84:58:
18:d4:fe:dc:36:cd:8a:48:cc:e6:51:27:e5:76:81:2f:c7:9c:
7b:f9:fb:19:c9:7c:e4:27:06:75:cd:16:88:74:3c:0b:23:d6:
86:6b:95:41:10:cf:b2:fc:e8:1e:e0:d6:a5:8c:d1:c0:1b:d5:
6e:15:8c:9a:67:5c:9d:ac:02:5a:69:17:e8:4c:42:d0:5d:88:
da:08:4e:c0
-----BEGIN CERTIFICATE-----
MIIDrTCCApWgAwIBAgIBATANBgkqhkiG9w0BAQsFADBlMQswCQYDVQQGEwJDTjEL
MAkGA1UECAwCR0QxETAPBgNVBAcMCHNoZW56aGVuMScwJQYDVQQKDB5odHRwczov
L3d3dy5hZ3JhbmR0ZWNoLmNvbS5jbi8xDTALBgNVBAMMBHRlc3QwHhcNMjMwNzAx
MTAwNTQ4WhcNMjYwMzI3MTAwNTQ4WjBSMQswCQYDVQQGEwJDTjELMAkGA1UECAwC
R0QxJzAlBgNVBAoMHmh0dHBzOi8vd3d3LmFncmFuZHRlY2guY29tLmNuLzENMAsG
A1UEAwwEdGVzdDCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAPO96f6q
psHZe3Qg8NDz7nzQaYSNGjceKUKYhlGH/l1ILpewxhacRmo4ezRU7HbSUlC7Maje
fT+Mxfj74+NzNzYQ6FXfgM/A2UAwt1RJaeOoeUlH2HSwBxPdR3KJab0MQIv07kkC
y/S5wXp92hAbsrGfDXBm0YYx3OPW5fUs4Ve9cupKHQxMWAkrLuVTQHNV6XjDepUl
t52ArOR5w9eb0cNzeNoD9KpoIYHyU7g9kWDgkUcubV0BrvKCwIrdBoxwbnd+FK5h
pdjgExss99NiDNFcSP5ZyrWxK4krL2ldQEIFq3ZYTzYaNhwh64Uc2iIbwmCOwX1Q
MznAQOBJIKD3w08CAwEAAaN7MHkwCQYDVR0TBAIwADAsBglghkgBhvhCAQ0EHxYd
T3BlblNTTCBHZW5lcmF0ZWQgQ2VydGlmaWNhdGUwHQYDVR0OBBYEFNegP1/AZYOI
b16Y2zA9nyRq0N5UMB8GA1UdIwQYMBaAFG2zHbZ4TsgZj/pNazpeqX3LB5i6MA0G
CSqGSIb3DQEBCwUAA4IBAQA5iomieQ/A/djb1TjSA7Q4vqJuaxwokwqmC68KaWuL
1d893natJCOYeiGhL5BHm5ie0rR1Ib3QODRrsZY9JNqsGkXkAR2iIMND0+zZLTvR
7g0eIRXnf9OVHNz6iDoFS8UIXfRAiSmA/mtAuTSSLkiU0ksLTR48ZBfPNOw2XG09
kJx0ldfIlqJwWUrSteHBqbet8Jn/tE2J5+OdfXk2QAVtIEZUrxhzyQcXJhiGmczi
WCeWhFgY1P7cNs2KSMzmUSfldoEvx5x7+fsZyXzkJwZ1zRaIdDwLI9aGa5VBEM+y
/Oge4NaljNHAG9VuFYyaZ1ydrAJaaRfoTELQXYjaCE7A
-----END CERTIFICATE-----

View File

@@ -0,0 +1,81 @@
Certificate:
Data:
Version: 3 (0x2)
Serial Number: 2 (0x2)
Signature Algorithm: sha256WithRSAEncryption
Issuer: C=CN, ST=GD, L=shenzhen, O=https://www.agrandtech.com.cn/, CN=test
Validity
Not Before: Jul 1 10:08:44 2023 GMT
Not After : Mar 27 10:08:44 2026 GMT
Subject: C=CN, ST=GD, O=https://www.agrandtech.com.cn/, CN=test1
Subject Public Key Info:
Public Key Algorithm: rsaEncryption
RSA Public-Key: (2048 bit)
Modulus:
00:ed:73:63:a4:7d:8c:00:e6:e5:df:f5:1e:8a:d4:
22:e4:37:16:62:6b:64:f1:90:ec:4b:4c:37:c5:2e:
de:ef:11:93:15:da:e9:2d:7b:69:72:2d:94:29:f8:
04:75:22:37:a4:83:53:a3:7b:b1:37:2d:a0:57:af:
0e:65:3c:cf:fe:1a:65:de:e8:66:7b:19:81:ab:10:
9b:9e:27:5b:a9:7c:cc:3a:44:ee:6e:af:3a:ef:67:
72:60:a8:8d:bb:4d:3e:ce:34:1f:08:9c:72:f7:52:
44:d7:af:eb:f7:9b:3f:62:94:09:db:26:e3:0f:eb:
b3:85:d3:c3:2d:ec:c1:14:d8:2d:b0:4c:10:c7:b1:
22:cf:74:a7:cd:94:b7:18:9e:78:0b:0b:64:00:e0:
e1:8a:97:57:11:5d:7c:f3:c9:6c:e0:97:c1:6c:01:
b5:c4:75:fa:71:96:9a:89:c7:73:61:bd:4a:2b:28:
17:81:4b:9f:92:ee:8e:a0:57:7f:7a:7c:89:a6:7e:
4d:a8:f3:b8:aa:03:aa:de:30:a7:19:94:a7:87:fc:
ab:5a:e5:8d:a9:64:51:5a:f4:ad:64:e1:aa:e4:45:
b7:e4:03:dc:6b:cf:fa:4a:0d:09:ef:4f:82:39:cc:
2f:91:c1:94:55:57:58:16:0b:14:00:62:43:c9:67:
e0:d3
Exponent: 65537 (0x10001)
X509v3 extensions:
X509v3 Basic Constraints:
CA:FALSE
Netscape Comment:
OpenSSL Generated Certificate
X509v3 Subject Key Identifier:
51:A3:41:B8:14:F9:2C:04:DE:0C:49:24:58:B5:5A:34:0E:07:FE:40
X509v3 Authority Key Identifier:
keyid:6D:B3:1D:B6:78:4E:C8:19:8F:FA:4D:6B:3A:5E:A9:7D:CB:07:98:BA
Signature Algorithm: sha256WithRSAEncryption
3c:f2:58:cd:8c:39:90:b4:f5:0f:ef:f6:a7:eb:26:4c:43:63:
dc:9f:94:a1:43:6c:9a:82:2b:e4:8e:24:c5:40:da:78:93:c5:
dd:8a:5d:63:76:00:ef:c6:ca:a7:a8:10:a3:9a:ae:d1:20:d1:
19:e1:46:03:03:98:a4:71:9a:45:8d:34:33:ce:c8:52:82:22:
33:5f:79:74:61:88:ab:52:6f:98:75:8f:07:bf:ff:d9:2e:30:
67:ce:05:8b:6c:ac:24:ec:2c:ac:c5:42:f7:71:b6:da:53:bc:
48:d1:29:82:aa:03:27:81:84:0a:f5:12:e2:8c:3a:77:f9:a8:
0e:d4:1f:7e:1f:98:28:f7:15:f0:78:8a:ba:b7:77:20:b7:82:
0d:cd:d5:47:ed:9e:61:a7:9b:35:1b:35:c7:74:91:0b:6c:1c:
27:1a:a9:cc:11:5b:22:0d:35:40:43:ae:f2:44:66:aa:9e:dc:
22:ca:a7:8b:8c:44:6a:f6:b1:6d:1e:3a:51:c0:2a:02:81:d7:
b6:4a:77:1e:e0:13:19:0c:51:4c:67:e1:2f:97:c9:4a:88:25:
c8:b4:65:dc:0d:a5:71:c2:45:dd:4f:01:bf:f0:43:9c:41:37:
28:eb:15:fc:90:f8:b6:3a:4b:57:79:df:74:4c:a9:aa:27:a2:
77:22:37:7f
-----BEGIN CERTIFICATE-----
MIIDrjCCApagAwIBAgIBAjANBgkqhkiG9w0BAQsFADBlMQswCQYDVQQGEwJDTjEL
MAkGA1UECAwCR0QxETAPBgNVBAcMCHNoZW56aGVuMScwJQYDVQQKDB5odHRwczov
L3d3dy5hZ3JhbmR0ZWNoLmNvbS5jbi8xDTALBgNVBAMMBHRlc3QwHhcNMjMwNzAx
MTAwODQ0WhcNMjYwMzI3MTAwODQ0WjBTMQswCQYDVQQGEwJDTjELMAkGA1UECAwC
R0QxJzAlBgNVBAoMHmh0dHBzOi8vd3d3LmFncmFuZHRlY2guY29tLmNuLzEOMAwG
A1UEAwwFdGVzdDEwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDtc2Ok
fYwA5uXf9R6K1CLkNxZia2TxkOxLTDfFLt7vEZMV2ukte2lyLZQp+AR1Ijekg1Oj
e7E3LaBXrw5lPM/+GmXe6GZ7GYGrEJueJ1upfMw6RO5urzrvZ3JgqI27TT7ONB8I
nHL3UkTXr+v3mz9ilAnbJuMP67OF08Mt7MEU2C2wTBDHsSLPdKfNlLcYnngLC2QA
4OGKl1cRXXzzyWzgl8FsAbXEdfpxlpqJx3NhvUorKBeBS5+S7o6gV396fImmfk2o
87iqA6reMKcZlKeH/Kta5Y2pZFFa9K1k4arkRbfkA9xrz/pKDQnvT4I5zC+RwZRV
V1gWCxQAYkPJZ+DTAgMBAAGjezB5MAkGA1UdEwQCMAAwLAYJYIZIAYb4QgENBB8W
HU9wZW5TU0wgR2VuZXJhdGVkIENlcnRpZmljYXRlMB0GA1UdDgQWBBRRo0G4FPks
BN4MSSRYtVo0Dgf+QDAfBgNVHSMEGDAWgBRtsx22eE7IGY/6TWs6Xql9yweYujAN
BgkqhkiG9w0BAQsFAAOCAQEAPPJYzYw5kLT1D+/2p+smTENj3J+UoUNsmoIr5I4k
xUDaeJPF3YpdY3YA78bKp6gQo5qu0SDRGeFGAwOYpHGaRY00M87IUoIiM195dGGI
q1JvmHWPB7//2S4wZ84Fi2ysJOwsrMVC93G22lO8SNEpgqoDJ4GECvUS4ow6d/mo
DtQffh+YKPcV8HiKurd3ILeCDc3VR+2eYaebNRs1x3SRC2wcJxqpzBFbIg01QEOu
8kRmqp7cIsqni4xEavaxbR46UcAqAoHXtkp3HuATGQxRTGfhL5fJSoglyLRl3A2l
ccJF3U8Bv/BDnEE3KOsV/JD4tjpLV3nfdEypqieidyI3fw==
-----END CERTIFICATE-----

View File

@@ -0,0 +1,27 @@
-----BEGIN RSA PRIVATE KEY-----
MIIEpgIBAAKCAQEA0SMdRLkcxy3PKOSCusJ+AnGiJyW6AxyujqZj4xjgtIFjYIMV
W5ZXVbWnY0xzRPddFddnEWgMeMLn9V3zcESV3tu9exm6Ijop8/KaDJ1EJAESunxk
P9x/1ek3kgQvuK3YAcizTeB5ODUZ/KFJw9MPR/KUB+TYqCp50mr6mlIZE6lvhhvM
xHz6ZmOFh2RvYg0h8oXpo5G8nmRVb4gNrlXKy/HZpGtbm/mfbOtxWgvSFy3PE/49
V8nOYJbhDaoOXWVN06Z7w1y4KzSKbIoZfC9CWdWRrrhIv+Px1QLQItL17kAKqtp+
vtG8lZjC5vsAgXLVAZLK71b6onv1Ir3YuwwfvQIDAQABAoIBAQCi1khvvgJeQ5jN
Kj9v0wfyNzAecw2GZsqzX3Le2/v6D9SkzOvQSBrwLWSLuHb39/KOkw05TF6JmJir
P9/QRla7EzVRqBJ5m/gWbYrsz3bC4eMHONuFrdYLZG9UTdYqYZGSsgaKWIGJ9i6p
uZuJ0chQKNyB2Pmo1onMAGfnyIyl9RruM0G3KOl2tHOqJnoqOoJAdWvq/vjmEb1H
lypiZZpIede2Q58oXC1HZFNT/q1NA3SGMbPoXmG4XoCTtq9Llt1kyk9FMbhKV1oj
FoneRwXRMEqu0AEGgk9XSEdSPVLZ4nspgrdA5mkTxa/fUyPvWjantzR/ovR6zx95
mKKnEVIBAoGBAOwtRkIciCNSa7xwJD8QvEFCADvZDU/+RmFk2tDbbA+gDYPy1bdD
1qDqbzwdCnuMeVbTSAP+KNxxa1M9pOun21t6nC7sUPdqGbQEwkQrFs9v859wf2j9
GU/oeu+aQabDGFXjwTC23wifqXTVc1/JnfGsqd3+9WwqR31SG+88/OjdAoGBAOKw
1r7/9XqrYxL3SuxYhEm6Qasj3OwRgTXBfRYBcwyN8NDTqY/QvsTwPvLVaDy8lrjc
kHJUx+zxmOBg/aKlxmzH5OTp0vRoVBFAOW4bITfGHKTjPjud7lfeAP2txPUR4i/4
vHgYIlVFjGT6+p4oMsX7wtYl8ZmO184pVHNbZzRhAoGBAOJQQBL55Dp0sGhRzWnh
T4P5CuBOjUMqFaceTc/1cwdGB6149PI4P2LTQuQHsBPT+DILI+cvlVgoFwAdAfwP
TVPLmf4c1TlAooCuTrmj0KfWT01pL64bWjYIQEV5O4/hQ2CKboWPtwk8ddVO9M/F
E2SSX/QqbGLJ4Ndl5v7JIlDBAoGBAJQnnzIVdwpFGOs8U+tDrrHA2UpQlgJzLk9D
tcy8BcUev1S8AQXNF+D+YyWx8/4+AwOuo3kVj9R70b5TpXC3h4dw3Vf+ubCivs7H
esFLWdpp0C6zlejAvxUOMveYqjDBD2Lq3cJfg5DXc3pLzZ+wBf7/G8d55PzHLqO+
v0Llaf4BAoGBAI4Fu4Sr0fD38pAUAehfDlzngoXIs7eqdJU5Gu19U3PKKhDRKptp
YBKt6mGv1R9rk9hCwXpXGRpABy6mpNkOCcYYmTtLGbwyy8Y1dbY9kNBrdhvrCcLh
RZL9VrFMOuoHrd/yB4AEwvoZHAhNAkheU6CC/R6uiWof6eH8YmXJEt0n
-----END RSA PRIVATE KEY-----

View File

@@ -0,0 +1 @@
03

View File

@@ -0,0 +1 @@
02

BIN
tools/cmca/casign.exe Normal file

Binary file not shown.

71
tools/cmca/casign.go Normal file
View File

@@ -0,0 +1,71 @@
package main
import (
"crypto/x509"
"encoding/base64"
"fmt"
"os"
"ems.agt/cmca/config"
)
// func init() {
// roots := x509.NewCertPool()
// rootCert, err := LoadCert(config.CaConfig.CA.RootCert)
// if err != nil {
// os.Exit(1)
// }
// roots.AddCert(rootCert)
// rootCertPool = roots
// }
func main() {
// 初始化
//config.CaConfig.CA.RootCert = "./certs/cacert.pem"
//Init()
fmt.Println("CaConfig:", config.CaConfig)
roots := x509.NewCertPool()
rootCert, err := LoadCert(config.CaConfig.CA.RootCert)
if err != nil {
os.Exit(1)
}
roots.AddCert(rootCert)
rootCertPool = roots
//证书验证:
cert, err := LoadCert(config.CaConfig.CA.Cert)
if err != nil {
fmt.Println("LoadCert:", err)
return
}
err = VerifyCert(cert)
fmt.Println("VerifyCert:", err)
//签名
fmt.Println("RSA签名认证:")
pri, err := LoadPriKey(config.CaConfig.CA.PrivateKey)
if err != nil {
fmt.Println("LoadPriKey:", err)
return
}
username := config.UserName
rsaSign, err := SignRSA([]byte(*username), pri)
if err != nil {
fmt.Println("SignRSA:", err)
return
}
rsaSign64 := base64.StdEncoding.EncodeToString(rsaSign)
fmt.Println("rsaSign64:", rsaSign64)
//签证验证
cert, err = LoadCert(config.CaConfig.CA.Cert)
if err != nil {
fmt.Println("LoadCert:", err)
return
}
err = VerifyRSA([]byte(*username), rsaSign, cert)
fmt.Println("VerifyRSA sign:", err)
}

BIN
tools/cmca/casign.zip Normal file

Binary file not shown.

View File

@@ -0,0 +1,22 @@
-----BEGIN CERTIFICATE-----
MIIDnzCCAoegAwIBAgIUSBd+zbdjx31N0Q51+NrVdeDEPKYwDQYJKoZIhvcNAQEL
BQAwXzELMAkGA1UEBhMCQ04xEDAOBgNVBAgMB0JlaWppbmcxCzAJBgNVBAcMAkJK
MSIwIAYDVQQKDBlodHRwczovL3d3dy5ydWlqaWUuY29tLmNuMQ0wCwYDVQQDDAR0
ZXN0MB4XDTIzMDgxMjA5MzMxMloXDTMzMDgwOTA5MzMxMlowXzELMAkGA1UEBhMC
Q04xEDAOBgNVBAgMB0JlaWppbmcxCzAJBgNVBAcMAkJKMSIwIAYDVQQKDBlodHRw
czovL3d3dy5ydWlqaWUuY29tLmNuMQ0wCwYDVQQDDAR0ZXN0MIIBIjANBgkqhkiG
9w0BAQEFAAOCAQ8AMIIBCgKCAQEA0jW6bA//53YP3cqWmE42GGcJyZw1imzoIvDR
stTYosiu/8cju1NHBJE6xF84huTs4Q+f6ZCE931Kg4ORX6iQFvbMK6/n0kpBFchA
mZRqBElcIbjK8sNTbyJgjX2iRI5Mkm6mBgIaB0C/9iWN64WxSdk7Gs3ZTipn4SYW
Ejn6wP3B1BGpj3NMUm1xah6XhCmnlxXDNvpjBOEOSsgs9fM3Bvatpn4pRXQtzsMD
CkeicdSTnave3EQHskBCpw0f2ojG5LgGsibKRzijzt4LiMzt5jrMWxRgv/So9bAt
QmMZhyP3ZE+AySkh7df7WobsoGtFAv+8aiIBYtJl94yLq+kssQIDAQABo1MwUTAd
BgNVHQ4EFgQUjCKd8br99RMOcoMAuuHaOZJvskcwHwYDVR0jBBgwFoAUjCKd8br9
9RMOcoMAuuHaOZJvskcwDwYDVR0TAQH/BAUwAwEB/zANBgkqhkiG9w0BAQsFAAOC
AQEANWTC8AiQOsWQQEqErAbuemA9GrW94t0cxrAuu86P7RJSvsyC7OzIg0Exp8rI
AnEeRef8tHi19iepMtvSHTLwsPcAFA6NlDBX+kf2CI1XM0OrjLgmIgfdnCvAjaNm
kWiDpMtMq/PsRfGVFb15NGUdqv25mGofR2bluYvFyybmZoVcKXkoCZ5JvvTOEPO/
VPqRYnDMj5LVKefaBWp+xtGnTGx0m6ki2bk19OZAZz2GAzS+Kc27CiuO/hsjt0Bj
s1wJPdBdGvNNRJBIiwrf8wCpCrRQQl2uczatYJdoZK+3szmsWZJg3wGKLqp6Ua6y
URxUlN2SyT01lco4vat6Eh1t3A==
-----END CERTIFICATE-----

View File

@@ -0,0 +1,81 @@
Certificate:
Data:
Version: 3 (0x2)
Serial Number: 1 (0x1)
Signature Algorithm: sha256WithRSAEncryption
Issuer: C=CN, ST=Beijing, L=BJ, O=https://www.ruijie.com.cn
Validity
Not Before: Aug 12 09:41:13 2023 GMT
Not After : Nov 20 09:41:13 2023 GMT
Subject: C=CN, ST=Beijing, O=https://www.ruijie.com.cn, CN=test
Subject Public Key Info:
Public Key Algorithm: rsaEncryption
RSA Public-Key: (2048 bit)
Modulus:
00:a7:da:88:69:ee:bd:5c:11:8e:69:fc:7b:11:ae:
43:21:b9:1e:da:d2:6e:f5:bb:93:37:af:6e:8c:ae:
b3:7b:dd:b6:fd:af:48:e7:ac:a8:b5:7a:15:ab:0e:
b7:b5:27:b4:e3:83:92:3a:91:e6:f0:83:34:b8:74:
42:2c:a8:df:4e:14:5d:4e:a4:5f:4d:0c:79:b0:5c:
79:9a:ee:26:0f:76:82:67:48:0f:6a:3f:df:6d:a0:
c8:64:9a:2b:17:6a:c6:19:a5:c1:54:9b:f2:e4:6d:
b4:fe:5f:70:c9:ca:9b:47:ca:fe:50:f4:23:e1:fe:
94:d7:d1:ae:17:51:57:c7:78:da:b4:b2:b7:bb:e9:
1b:55:a1:f1:fd:17:63:9f:cf:3b:81:87:d8:80:7d:
1e:d6:ac:cc:b5:96:b1:78:df:d4:cb:0e:ec:42:da:
3d:f9:87:df:01:45:5f:3e:b6:93:24:18:b3:d1:d5:
c2:42:f8:2a:e8:c4:bd:48:f4:ec:c7:2c:1a:cf:bc:
a4:9c:df:f4:15:71:9d:ea:f4:4a:04:7f:54:64:f6:
79:3a:36:fb:10:1a:c3:18:2e:81:83:c2:62:47:a0:
88:70:13:1d:f9:9d:fb:ef:72:a8:3c:6d:9b:8e:69:
f8:c5:a0:92:32:87:19:21:dd:68:5c:0d:0c:fd:21:
28:69
Exponent: 65537 (0x10001)
X509v3 extensions:
X509v3 Basic Constraints:
CA:FALSE
Netscape Comment:
OpenSSL Generated Certificate
X509v3 Subject Key Identifier:
93:D4:BE:FF:27:3C:D0:91:A2:1E:36:1B:F1:A3:43:B3:70:CC:00:DA
X509v3 Authority Key Identifier:
keyid:8C:22:9D:F1:BA:FD:F5:13:0E:72:83:00:BA:E1:DA:39:92:6F:B2:47
Signature Algorithm: sha256WithRSAEncryption
61:f7:28:fb:02:42:57:0f:34:9b:e4:b6:8a:9b:8a:3b:b8:d1:
e0:4d:55:07:8d:7c:87:a3:88:3a:6f:4c:ab:cf:76:f8:76:17:
bc:76:32:69:3a:19:9b:50:f2:b2:97:7f:73:eb:7e:6f:05:b9:
ea:a3:88:c0:ab:96:bd:36:e4:36:59:e1:2c:44:08:78:da:4f:
5d:e3:87:e1:d5:ec:86:0e:08:27:e0:e9:ad:20:e0:6b:67:26:
9b:31:a9:17:ac:ee:e0:dc:d9:e6:50:69:fe:83:23:51:6b:51:
6b:c4:45:36:8a:48:a5:cd:61:99:cf:25:05:8a:94:5e:3c:29:
35:67:00:fa:77:2f:09:2c:a0:18:bb:35:ce:f0:45:43:b7:47:
d5:89:cb:aa:a1:6f:8d:ac:16:d1:8d:be:39:a9:54:3d:da:70:
43:ca:e1:a3:a2:13:83:9b:a8:3b:e8:80:60:21:26:af:f9:09:
8a:6a:b0:77:82:7b:76:a1:03:13:a4:e2:e0:5c:d1:83:bd:50:
43:b3:23:96:a7:c9:7d:e5:2f:e6:95:c9:ff:9b:3b:1f:a4:30:
df:4c:67:99:92:fc:b7:e7:25:fc:bd:d7:30:c3:3a:34:78:93:
87:ae:4e:61:5a:12:04:43:25:c8:7a:9e:c5:cd:31:12:48:22:
2d:4f:d9:ed
-----BEGIN CERTIFICATE-----
MIIDmDCCAoCgAwIBAgIBATANBgkqhkiG9w0BAQsFADBQMQswCQYDVQQGEwJDTjEQ
MA4GA1UECAwHQmVpamluZzELMAkGA1UEBwwCQkoxIjAgBgNVBAoMGWh0dHBzOi8v
d3d3LnJ1aWppZS5jb20uY24wHhcNMjMwODEyMDk0MTEzWhcNMjMxMTIwMDk0MTEz
WjBSMQswCQYDVQQGEwJDTjEQMA4GA1UECAwHQmVpamluZzEiMCAGA1UECgwZaHR0
cHM6Ly93d3cucnVpamllLmNvbS5jbjENMAsGA1UEAwwEdGVzdDCCASIwDQYJKoZI
hvcNAQEBBQADggEPADCCAQoCggEBAKfaiGnuvVwRjmn8exGuQyG5HtrSbvW7kzev
boyus3vdtv2vSOesqLV6FasOt7UntOODkjqR5vCDNLh0Qiyo304UXU6kX00MebBc
eZruJg92gmdID2o/322gyGSaKxdqxhmlwVSb8uRttP5fcMnKm0fK/lD0I+H+lNfR
rhdRV8d42rSyt7vpG1Wh8f0XY5/PO4GH2IB9HtaszLWWsXjf1MsO7ELaPfmH3wFF
Xz62kyQYs9HVwkL4KujEvUj07McsGs+8pJzf9BVxner0SgR/VGT2eTo2+xAawxgu
gYPCYkegiHATHfmd++9yqDxtm45p+MWgkjKHGSHdaFwNDP0hKGkCAwEAAaN7MHkw
CQYDVR0TBAIwADAsBglghkgBhvhCAQ0EHxYdT3BlblNTTCBHZW5lcmF0ZWQgQ2Vy
dGlmaWNhdGUwHQYDVR0OBBYEFJPUvv8nPNCRoh42G/GjQ7NwzADaMB8GA1UdIwQY
MBaAFIwinfG6/fUTDnKDALrh2jmSb7JHMA0GCSqGSIb3DQEBCwUAA4IBAQBh9yj7
AkJXDzSb5LaKm4o7uNHgTVUHjXyHo4g6b0yrz3b4dhe8djJpOhmbUPKyl39z635v
Bbnqo4jAq5a9NuQ2WeEsRAh42k9d44fh1eyGDggn4OmtIOBrZyabMakXrO7g3Nnm
UGn+gyNRa1FrxEU2ikilzWGZzyUFipRePCk1ZwD6dy8JLKAYuzXO8EVDt0fVicuq
oW+NrBbRjb45qVQ92nBDyuGjohODm6g76IBgISav+QmKarB3gnt2oQMTpOLgXNGD
vVBDsyOWp8l95S/mlcn/mzsfpDDfTGeZkvy35yX8vdcwwzo0eJOHrk5hWhIEQyXI
ep7FzTESSCItT9nt
-----END CERTIFICATE-----

View File

@@ -0,0 +1,27 @@
-----BEGIN RSA PRIVATE KEY-----
MIIEpQIBAAKCAQEAp9qIae69XBGOafx7Ea5DIbke2tJu9buTN69ujK6ze922/a9I
56yotXoVqw63tSe044OSOpHm8IM0uHRCLKjfThRdTqRfTQx5sFx5mu4mD3aCZ0gP
aj/fbaDIZJorF2rGGaXBVJvy5G20/l9wycqbR8r+UPQj4f6U19GuF1FXx3jatLK3
u+kbVaHx/Rdjn887gYfYgH0e1qzMtZaxeN/Uyw7sQto9+YffAUVfPraTJBiz0dXC
Qvgq6MS9SPTsxywaz7yknN/0FXGd6vRKBH9UZPZ5Ojb7EBrDGC6Bg8JiR6CIcBMd
+Z3773KoPG2bjmn4xaCSMocZId1oXA0M/SEoaQIDAQABAoIBAQCnLMfgeZ6vK+0j
MguAuIaz96P7XMqWg5NESr1X8EdifpfaYdHCq/v7gvRBwg7Fph5K2qexHc9ci9De
RSwDPs3o/e9Qe/VOz7YDKJcU70uI6wdFxkdUEvl8Pj5XtBRm5jkXIjdDBW8MgxdY
ocW7tMai4lIYXo++bcfgiz1Qi/tY9jAuloUaTnSnggayEx/4N6JDj8e8X+7ju6b7
A1lYt6jb10jU+8McxXfx/G2H+xTEvfDLGyeXnmkeYK5HmAl49xpaowSgk2siYJrd
M1a8Y7tb44tBNTymrJqjea32/S5U8qa0hywnRx9B9/GAsm1+bgyLdQBoxY5dUBU+
mu3x73fhAoGBANEKtywRjD4jOjp01Q7gxiBjBzjXAjm/DODB6jtWG16CEJ5LCMkE
MgKAsvac/z9gdWnGrRxNuO8CZExHW1XfwDcWbQ7jnpW4+JcXwG82djg91guzmOMV
bDdPhusUDFVtLJry+nf6kQ+JetZXQzDSoNrUHUWPRioSxZDmk0D9TIjrAoGBAM2P
OT+bGZDVsW1XpmHhPMXrce01S2jb17rKT3nikT/lZ3W8j8EbVHZXw/Q1PtrHDBiX
HQdG1V38vbSG9MvlEOKOXe0/7DLRxkE5n0Wke8qregLDxKnlPy+hiu9y1iCcs0Mm
QTcmShz29iSx6aG7pW4qvMQIm31O6zbhMLQSSj77AoGAFzbnbJ9uQaBL4R4EYyiX
GBWnQaqu9pa+6V7fkkNXusEa81lF2nz6yMheF4EL34/ouhx0MQZ4mSJc3RO3kuvM
PtHgvpyMifgGs1DR8AfOTSSg1p/VRLKmV+YfB5AsZng/Ud3V7ukGnwEXgSIjthJO
Br8zmPv2QMng4tyYUclPbI0CgYEAkp1NH+joWz2Px4V0zutwBVrhb2dL2gaz4C7c
cPsAzqo5GOjdP8bWf3Ip+czgf/rozcE6my4SkW7rgA+iGqvPV0hkBgxJ1BV7appG
181x3iRgaghoBSXV44s9JXyq7afW1FY8vbE5u18KQTIEia7lV6Zz7P6WqNHZQtNr
gYRqIHECgYEAgoMSfiaP+gtVwa24GajeoyaHrbsJmUAU4mMKVWFGwic8J4NfXmct
ebGGXpNAAzZFKSyYYr2IL1M1rbxy8pEnO4hB5eCbYyvnsmQgHtrixly/YCBKXBMK
Y/xp2u/QkpdL2ZkNuoeoXMLcrzM/24TG/RahFRMGi979/DUNkdm+i8M=
-----END RSA PRIVATE KEY-----

View File

@@ -0,0 +1,58 @@
package config
import (
"flag"
"fmt"
"os"
"gopkg.in/yaml.v3"
)
// Yaml struct of config
type YamlConfig struct {
//证书配置
CA struct {
RootCert string `yaml:"rootCert"` //root CA证书存放路径
Cert string `yaml:"cert"` // 服务端CA证书存放路径
PrivateKey string `yaml:"privateKey"` // 服务端私钥存放路径
Check bool `yaml:"check"` // 是否开启服务端证书检查功能
} `json:"ca"`
}
var CaConfig YamlConfig
func ReadConfig(configFile string) {
yamlFile, err := os.ReadFile(configFile)
if err != nil {
fmt.Println("Read yaml config file error:", err)
os.Exit(2)
}
err = yaml.Unmarshal(yamlFile, &CaConfig)
if err != nil {
fmt.Println("Unmarshal error:", err)
os.Exit(3)
}
}
var UserName *string
const defaultConfigFile = "./etc/cmca.yaml"
func init() {
cfile := flag.String("c", defaultConfigFile, "config file")
pv := flag.Bool("v", false, "print version")
ph := flag.Bool("h", false, "print help")
UserName = flag.String("u", "admin", "user name")
flag.Parse()
if *pv {
os.Exit(0)
}
if *ph {
flag.Usage()
os.Exit(0)
}
ReadConfig(*cfile)
}

4
tools/cmca/etc/cmca.yaml Normal file
View File

@@ -0,0 +1,4 @@
ca:
rootCert: ./certs/cacert.pem
cert: ./certs/nbi_agent.crt
privateKey: ./certs/nbi_agent.key

BIN
tools/cmsign/cmsign Normal file

Binary file not shown.

BIN
tools/cmsign/cmsign.exe Normal file

Binary file not shown.

114
tools/cmsign/cmsign.go Normal file
View File

@@ -0,0 +1,114 @@
package main
import (
"crypto"
"crypto/rand"
"crypto/rsa"
"crypto/sha256"
"crypto/x509"
"encoding/base64"
"encoding/pem"
"flag"
"fmt"
"os"
)
var UserName *string
func init() {
//cfile := flag.String("c", defaultConfigFile, "config file")
//pv := flag.Bool("v", false, "print version")
//ph := flag.Bool("h", false, "print help")
UserName = flag.String("u", "omc", "user name")
flag.Parse()
// if *pv {
// os.Exit(0)
// }
// if *ph {
// flag.Usage()
// os.Exit(0)
// }
//ReadConfig(*cfile)
}
func main() {
// 假设你已经有了CMCA证书私钥和userName登录用户名
privateKeyBytes, err := os.ReadFile("./private_key.pem")
if err != nil {
fmt.Println("Failed to read private key file:", err)
return
}
//userName := "omc"
// 解析私钥
privateKey, err := parsePrivateKey(privateKeyBytes)
if err != nil {
fmt.Println("Failed to parse private key:", err)
return
}
// 对用户名进行签名
signature, err := sign(privateKey, *UserName)
if err != nil {
fmt.Println("Failed to sign username:", err)
return
}
// 将签名按Base64编码格式化输出
signatureBase64 := base64.StdEncoding.EncodeToString(signature)
fmt.Println("Signature:", signatureBase64)
}
// 解析私钥
// func parsePrivateKey(privateKeyBytes []byte) (*rsa.PrivateKey, error) {
// privateKey, err := parsePrivateKey(privateKeyBytes)
// if err != nil {
// return nil, err
// }
// return privateKey, nil
// }
// 解析私钥
func parsePrivateKey(privateKeyBytes []byte) (*rsa.PrivateKey, error) {
block, _ := pem.Decode(privateKeyBytes)
if block == nil {
return nil, fmt.Errorf("failed to decode private key")
}
//privateKey, err := x509.ParsePKCS8PrivateKey(block.Bytes)
privateKey, err := x509.ParsePKCS1PrivateKey(block.Bytes)
if err != nil {
return nil, err
}
// rsaPrivateKey, ok := privateKey.(*rsa.PrivateKey)
// if !ok {
// return nil, fmt.Errorf("private key is not RSA")
// }
return privateKey, nil
}
// 对数据进行签名
func sign(privateKey *rsa.PrivateKey, data string) ([]byte, error) {
hashed := sha256.Sum256([]byte(data))
signature, err := rsa.SignPKCS1v15(rand.Reader, privateKey, crypto.SHA256, hashed[:])
if err != nil {
return nil, err
}
return signature, nil
}
func readPrivateKey() {
// 读取私钥文件
privateKeyBytes, err := os.ReadFile("./private_key.pem")
if err != nil {
fmt.Println("Failed to read private key file:", err)
return
}
// 输出私钥内容
fmt.Println(string(privateKeyBytes))
}

View File

@@ -0,0 +1,27 @@
-----BEGIN RSA PRIVATE KEY-----
MIIEpAIBAAKCAQEAlE3BYk9Rk2avUTik7lpuiHxbYTusrLYRCnr8JICRg0QsBfiu
q8d4+4s0w3y5F7puTj23Hf8ohAeNGK6vV9nJF9utMRvT4w5hlGqvKubM2vORoNoa
1usIixfcvMmCt/7++9endMurLY7e9aR+eeEffJtMx5G5JqxRGoFkeXBKFTOjD2ad
sHQ5zhQQUYgdQa2xzKQBYiierKKptcoVMAnnkfx7NPSRfCnzhYVeKgBFbxNXL4h7
nAhLywWhusQc2yr2Fdojj7urtqPNfMKYapkmWKI9/zuPxMlYL49VXUqppE0rnYoi
ISwGvP9iSq1tb+8BUI0ZMDcHX4elEeZYiFMJOwIDAQABAoIBAFVJVhIsXVRwdBg4
hBkS5ogVRBPp1obIeYpWadSwH36m4M5aUlE1eKzoRGK7wlIUA8V5FmroxysOkKUG
KI5UD6Jp0fLw9uyX46QPqkb4zgyIkFI5u7+nEJW1Flt3Y3Ze7dJ1FbdEPWAIzs3j
WFzNC2eEhCYs9pZ3+HhOuzJfUitYU6ts83tazSms+7E027e/v2ubtYOzluEoj4YK
MM+ocqJOlXUOhyTATDaLs4fM567bwwFeriODQqmMIhXLf3HiBPfPYhoAlwPUV51L
bAjIPwG2/jy0yXPenYOUqSMP1i+XkyTL4eVqOLLQUI+BsEaToS8M7Lf4KRQE0vQm
uAkEA9ECgYEAxCsKXtkYXrma8UziSJgQBj88TfACyuYZBPkpBFJhffPVOreYzqmn
gsE38oHlLhCrezsxvScivS/Cwt7kgBTE9r6xmH8y2f0P3PNmtazQCqovG1gsNZ1t
9PZQmxbVUfx/7KRJ1Q5zX3x5C0P2c6XYv/1h/SQQ8PYXDhRxWZFVSikCgYEAwYlt
AoP8j6yHDMk10vJd0fKT1lztcHcQLvH3HQn2kHci2GCxySvcac49hpXTDeNdUzcQ
I9UWo1MggNojME3WHUTiZD5DYUzuNUBTkc0kMHWy79/YNAzvF9312MSyJ0NlytBQ
ISh0z0sPSxDjW+XCi/8LGu1rrremBqvh0rNIrMMCgYEAt+C8VNHcZRZHpX3y8icP
hjuKFGgwxe3Pb/j5uKJb3ktMCUEFjFo8uXTSM5AMuhRIGTgQVIS1rG5zemSh/Wj6
g2uWXyKEEQ+D6hGBqjP1wrlpdJE+x3btFdw5DFbn2HT9mF0bFAn6nXu4npWzEw5X
UQd67WT8OFIEpF8HLPTs5JkCgYBQlL6dmITU8Vm9mh1d+mnT23NwgnqeJATJ9xcT
sS1HE0Of4grEHw4Dw8pcOg+JLcyStE91C+kEEb1ryOdz2kS3JRI5+K6nWZeo9mKV
R1u1DZx2QbZMXcJDJriRC7y9mlNMsZVbaPPRx4fTknGHts9c6NEf4hC+y1pGVtSM
nPc6bwKBgQCrtb6srow9o0acH7mMmieDuqvT8DQ6rHWoizgneZTuvIo6SPO6nRnR
jfgfQkqr9IiLh9awSblQEN9fnddog7a1yS4cUZueiP5dmtFvp4B9Scnt+BoHpOLk
rrU2i7grAye4Cd003+pqhSERGCKSzb3fTSYiMypKsxeH2bs8nrRu2A==
-----END RSA PRIVATE KEY-----

87
tools/genxml/genxml.go Normal file
View File

@@ -0,0 +1,87 @@
package main
import (
"flag"
"log"
"os/exec"
"strings"
xsd "github.com/metaleap/go-xsd"
)
var (
flagGoFmt = flag.Bool("gofmt", true, "Run 'gofmt' against the generated Go wrapper package?")
flagGoInst = flag.Bool("goinst", true, "Run 'go-buildrun' against the generated Go wrapper package?")
flagSchema = flag.String("uri", "", "The XML Schema Definition file URIs to generate a Go wrapper packages from, whitespace-separated. (For each, the protocol prefix can be omitted, it then defaults to http://. Only protocols understood by the net/http package are supported.)")
flagLocalCopy = flag.Bool("local", true, "Local copy: only downloads if file does not exist locally")
flagForceParse = flag.Bool("parse", false, "Not necessary unless the generated Go wrapper package won't compile.")
flagBasePath = flag.String("basepath", "", "Defaults to "+xsd.PkgGen.BasePath+". A $GOPATH/src/-relative path (always a slash-style path, even on Windows) where XSD files are downloaded to / loaded from and generated Go wrapper packages are created. Any XSD imports are also rewritten as Go imports from that path (but are not otherwise auto-magically processed in any way).")
// if no schemas are specified in *flagSchema, we run the pkg-maker through a default series of various XSDs...
schemas = []string{
"./nrm-schema.xsd",
"www.w3.org/2001/xml.xsd",
"www.w3.org/2001/03/xml.xsd",
"www.w3.org/TR/2002/WD-SVG11-20020108/xml.xsd",
"www.w3.org/TR/2002/WD-SVG11-20020108/xlink.xsd",
"www.w3.org/TR/2002/WD-SVG11-20020108/SVG.xsd",
"www.w3.org/2007/schema-for-xslt20.xsd",
"www.w3.org/Math/XMLSchema/mathml2/common/xlink-href.xsd",
"www.w3.org/Math/XMLSchema/mathml2/mathml2.xsd",
"docs.oasis-open.org/election/external/xAL.xsd",
"docbook.org/xml/5.0/xsd/xml.xsd",
"docbook.org/xml/5.0/xsd/xlink.xsd",
"docbook.org/xml/5.0/xsd/docbook.xsd",
"kbcafe.com/rss/atom.xsd.xml",
"thearchitect.co.uk/schemas/rss-2_0.xsd",
"schemas.opengis.net/kml/2.2.0/atom-author-link.xsd",
"schemas.opengis.net/kml/2.2.0/ogckml22.xsd",
"khronos.org/files/collada_schema_1_4",
"khronos.org/files/collada_schema_1_5",
}
)
func main() {
var (
sd *xsd.Schema
err error
raw []byte
outFilePath string
)
flag.Parse()
if len(*flagSchema) > 0 {
schemas = strings.Split(*flagSchema, " ")
}
if len(*flagBasePath) > 0 {
xsd.PkgGen.BasePath, xsd.PkgGen.BaseCodePath = *flagBasePath, udevgo.GopathSrc(strings.Split(*flagBasePath, "/")...)
}
for _, s := range schemas {
log.Printf("LOAD:\t%v\n", s)
if sd, err = xsd.LoadSchema(s, *flagLocalCopy); err != nil {
log.Printf("\tERROR: %v\n", err)
} else if sd != nil {
xsd.PkgGen.ForceParseForDefaults = *flagForceParse || (s == "schemas.opengis.net/kml/2.2.0/ogckml22.xsd") // KML schema uses 0 and 1 as defaults for booleans...
if outFilePath, err = sd.MakeGoPkgSrcFile(); err == nil {
log.Printf("MKPKG:\t%v\n", outFilePath)
if *flagGoFmt {
if raw, err = exec.Command("gofmt", "-w=true", "-s=true", "-e=true", outFilePath).CombinedOutput(); len(raw) > 0 {
log.Printf("GOFMT:\t%s\n", string(raw))
}
if err != nil {
log.Printf("GOFMT:\t%v\n", err)
}
}
if *flagGoInst {
if raw, err = exec.Command("go-buildrun", "-d=__doc.html", "-f="+outFilePath).CombinedOutput(); len(raw) > 0 {
println(string(raw))
}
if err != nil {
log.Printf("GOINST:\t%v\n", err)
}
}
} else {
log.Printf("\tERROR:\t%v\n", err)
}
}
}
}

View File

@@ -0,0 +1,76 @@
<?xml version="1.0" encoding="UTF-8"?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" elementFormDefault="qualified" attributeFormDefault="unqualified">
<xs:element name="DataFile">
<xs:complexType>
<xs:sequence>
<xs:element name="FileHeader">
<xs:complexType>
<xs:sequence>
<xs:element name="TimeStamp" type="xs:dateTime"/>
<xs:element name="TimeZone" type="xs:string"/>
<xs:element name="VendorName" type="xs:string" minOccurs="0"/>
<xs:element name="ElementType" type="xs:string" minOccurs="0"/>
<xs:element name="CmVersion" type="xs:string" minOccurs="0"/>
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:element name="Objects" maxOccurs="unbounded">
<xs:complexType>
<xs:sequence>
<xs:element name="ObjectType" type="xs:string"/>
<!--该字段必选-->
<xs:element name="FieldName">
<xs:complexType>
<xs:sequence minOccurs="0" maxOccurs="unbounded">
<xs:element name="N">
<xs:complexType>
<xs:simpleContent>
<xs:extension base="xs:string">
<xs:attribute name="i" type="xs:integer" use="required"/>
</xs:extension>
</xs:simpleContent>
</xs:complexType>
</xs:element>
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:element name="FieldValue">
<xs:complexType>
<xs:sequence minOccurs="0" maxOccurs="unbounded">
<xs:element name="Object">
<xs:complexType>
<xs:sequence minOccurs="0" maxOccurs="unbounded">
<xs:element name="V">
<xs:complexType>
<xs:simpleContent>
<xs:extension base="xs:string">
<xs:attribute name="i" type="xs:integer" use="required"/>
</xs:extension>
</xs:simpleContent>
</xs:complexType>
</xs:element>
</xs:sequence>
<xs:attribute name="rmUID" type="xs:string" use="required"/>
<xs:attribute name="Dn" type="xs:string"/>
<!-- //无线、核心网专业该字段必选传输、IP专业、业务系统无该字段-->
<xs:attribute name="UserLabel" type="xs:string"/>
<!-- //无线、核心网专业该字段必选传输、IP专业、业务系统无该字段-->
<xs:attribute name="PVFlag" type="xs:string" use="required"/>
<!-- //必须-->
<xs:attribute name="VMID" type="xs:string"/>
<!-- //VNF网络或VNF和PNF混合组网虚拟网元必选物理网元无该字段-->
<xs:attribute name="VNFInstanceID" type="xs:string"/>
<!-- //VNF网络或VNF和PNF混合组网虚拟网元必选物理网元无该字段-->
</xs:complexType>
</xs:element>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:schema>

View File

@@ -0,0 +1,80 @@
<?xml version="1.0" encoding="UTF-8"?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
elementFormDefault="qualified" attributeFormDefault="unqualified">
<xs:element name="PmFile">
<xs:complexType>
<xs:sequence>
<xs:element name="FileHeader">
<xs:complexType>
<xs:sequence>
<xs:element name="TimeStamp" type="xs:dateTime" />
<xs:element name="TimeZone" type="xs:string" />
<xs:element name="Period" type="xs:integer" />
<xs:element name="VendorName" type="xs:string" />
<xs:element name="ElementType" type="xs:string" />
<xs:element name="PmVersion" type="xs:string" />
<xs:element name="StartTime" type="xs:dateTime" />
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:element name="Measurements" minOccurs="0" maxOccurs="unbounded">
<xs:complexType>
<xs:sequence>
<xs:element name="ObjectType" type="xs:string" />
<xs:element name="PmName">
<xs:complexType>
<xs:sequence minOccurs="0" maxOccurs="unbounded">
<xs:element name="N">
<xs:complexType>
<xs:simpleContent>
<xs:extension base="xs:string">
<xs:attribute name="i" type="xs:integer" use="required" />
</xs:extension>
</xs:simpleContent>
</xs:complexType>
</xs:element>
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:element name="PmData">
<xs:complexType>
<xs:sequence minOccurs="0" maxOccurs="unbounded">
<xs:element name="Object">
<xs:complexType>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="V">
<xs:complexType>
<xs:simpleContent>
<xs:extension base="xs:string">
<xs:attribute name="i" type="xs:integer" use="required" />
</xs:extension>
</xs:simpleContent>
</xs:complexType>
</xs:element>
<xs:element name="CV">
<xs:complexType>
<xs:sequence minOccurs="0" maxOccurs="unbounded">
<xs:element name="SN" type="xs:string" />
<xs:element name="SV" type="xs:string" />
</xs:sequence>
<xs:attribute name="i" type="xs:integer"
use="required" />
</xs:complexType>
</xs:element>
</xs:choice>
<xs:attribute name="rmUID" type="xs:string" use="required" />
<xs:attribute name="Dn" type="xs:string" use="required" />
<xs:attribute name="UserLabel" type="xs:string" use="required" />
</xs:complexType>
</xs:element>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:schema>

BIN
tools/loadcmxls/1.txt Normal file

Binary file not shown.

53
tools/loadcmxls/db.go Normal file
View File

@@ -0,0 +1,53 @@
package main
import (
"fmt"
_ "github.com/go-sql-driver/mysql"
"xorm.io/xorm"
)
var xEngine *xorm.Engine
func XormConnectDatabaseWithUri(sql string) (*xorm.Engine, error) {
// sqlStr := fmt.Sprintf("%s:%s@tcp(%s:%s)/%s?charset=utf8&parseTime=true&loc=Local", db.User, db.Password, db.Host, db.Port, db.Name)
sqlStr := fmt.Sprintf("%s?charset=utf8&parseTime=true&loc=Local", sql)
// fmt.Printf("sqlStr:%s:******@tcp(%s:%s)/%s?charset=utf8&parseTime=true&loc=Local", db.User, db.Host, db.Port, db.Name)
var err error
xEngine, err = xorm.NewEngine("mysql", sqlStr) //1、Create xorm engine
if err != nil {
fmt.Println("Failed to connect database:", err)
return nil, err
}
// xEngine.ShowSQL(true)
return xEngine, nil
}
type CmTitle struct {
// Id int `json:"id" xorm:"pk 'id' autoincr"`
NeType string `json:"neType"`
Object string `json:"object" xorm:"object"`
Code string `json:"code"`
CmEn string `json:"cmEn" xorm:"cm_en"`
CmCn string `json:"cmCn" xorm:"cm_cn"`
Description string `json:"description"`
}
func XormInsertCmTitle(row *CmTitle) (int64, error) {
session := xEngine.NewSession()
defer session.Close()
_, err := session.
Table("cm_title").
Where("ne_type = ? and code = ? and cm_en = ?", row.NeType, row.Code, row.CmEn).
Delete()
if err != nil {
fmt.Println("Failed to delete cm_title:", err)
}
affected, err := session.Table("cm_title").Insert(row)
if err != nil {
fmt.Println("Failed to insert cm_title:", err)
}
return affected, err
}

109
tools/loadcmxls/load.go Normal file
View File

@@ -0,0 +1,109 @@
package main
import (
"flag"
"fmt"
"io/ioutil"
"os"
"gopkg.in/yaml.v3"
)
// Yaml struct of config
type YamlConfig struct {
Logger struct {
File string `yaml:"file"`
Level string `yaml:"level"`
} `yaml:"logger"`
Rest struct {
BindIP string `yaml:"bindip"`
Port uint16 `yaml:"port"`
} `yaml:"rest"`
Database struct {
Type string `yaml:"type"`
User string `yaml:"user"`
Password string `yaml:"password"`
Host string `yaml:"host"`
Port string `yaml:"port"`
Name string `yaml:"name"`
} `yaml:"database"`
CmFileDir string `yaml:"cmfiledir"`
}
var yamlConfig YamlConfig
func ReadConfig(configFile string) {
yamlFile, err := ioutil.ReadFile(configFile)
if err != nil {
fmt.Printf("ioutil.ReadFile %s err %v", configFile, err)
}
// fmt.Println("yamlfile:", string(yamlFile))
err = yaml.Unmarshal(yamlFile, &yamlConfig)
if err != nil {
fmt.Printf("Unmarshal: %v when to struct", err)
}
}
func GetYamlConfig() *YamlConfig {
return &yamlConfig
}
func GetAllFile(dir string, s []string) ([]string, error) {
fmt.Println("GetAllFile processing...", dir)
fmt.Println("dir:", dir)
rd, err := ioutil.ReadDir(dir)
if err != nil {
fmt.Println("read dir fail:", err)
return s, err
}
for _, fi := range rd {
if !fi.IsDir() {
fullName := dir + "/" + fi.Name()
s = append(s, fullName)
}
}
return s, nil
}
const defaultConfigFile = "./loadcmxls.yaml"
var (
version string
buildTime string
goVer string
)
var pfiles []string
func init() {
cfile := flag.String("c", defaultConfigFile, "config file")
pfile := flag.String("f", "", "cm file")
pv := flag.Bool("v", false, "print version")
ph := flag.Bool("h", false, "print help")
flag.Parse()
if *pv {
fmt.Printf("OMC loadpmxls version: %s\n%s\n%s\n\n", version, buildTime, goVer)
os.Exit(0)
}
if *ph {
flag.Usage()
os.Exit(0)
}
ReadConfig(*cfile)
fmt.Println("pfile:", *pfile)
if *pfile != "" {
pfiles = append(pfiles, *pfile)
} else {
pfiles, _ = GetAllFile(yamlConfig.CmFileDir, pfiles)
}
fmt.Println("pfiles:", pfiles)
}

BIN
tools/loadcmxls/loadcmxls Normal file

Binary file not shown.

View File

@@ -0,0 +1,77 @@
package main
import (
"fmt"
"strings"
"github.com/xuri/excelize/v2"
)
func main() {
fmt.Println("========================= OMC loadpmxls startup =========================")
fmt.Println("OMC loadpmxls version: %s %s %s", version, buildTime, goVer)
for _, f := range pfiles {
fmt.Println("f:", f)
db := yamlConfig.Database
sqlStr := fmt.Sprintf("%s:%s@tcp(%s:%s)/%s", db.User, db.Password, db.Host, db.Port, db.Name)
XormConnectDatabaseWithUri(sqlStr)
LoadCmIntoCmTitle(f)
}
}
func LoadCmIntoCmTitle(file string) {
fmt.Println("file len:", file, len(file))
f, err := excelize.OpenFile(file)
if err != nil {
fmt.Println(err.Error())
return
}
list := f.GetSheetList()
if err != nil {
fmt.Println(err.Error())
return
}
fmt.Println(list)
dl := len(yamlConfig.CmFileDir) + 1
neType := file[dl : dl+3]
fmt.Println("neType:", neType)
objectMap := make(map[string]string, 0)
for _, s := range list {
if s[0] == 'I' {
rows, _ := f.GetRows(s)
for _, row := range rows[1:] {
// fmt.Println("row:", row)
if len(row) > 1 {
fmt.Println("row[0]:", row[0], "row[1]", row[1])
objectMap[row[0]] = row[1]
}
}
fmt.Println("objectMap:", objectMap)
}
if s[0] == 'A' {
rows, _ := f.GetRows(s)
var code, desc, object string
object = objectMap[s]
fmt.Println("object:", object, "s:", s)
for _, row := range rows[1:] {
if row[0] != "" {
code = row[0]
}
if len(row) > 4 && row[4] != "" {
desc = row[4]
}
cmEn := strings.Replace(row[2], " ", "", -1)
cmEn = strings.Replace(cmEn, "\n", "", -1)
cmCn := strings.Replace(row[3], " ", "", -1)
cmCn = strings.Replace(cmCn, "\n", "", -1)
cmTitle := CmTitle{neType, object, code, cmEn, cmCn, desc}
fmt.Println("cmTitle:", cmTitle)
XormInsertCmTitle(&cmTitle)
}
}
}
}

View File

@@ -0,0 +1,17 @@
logger:
file: ./loadpmxls.log
level: debug
rest:
bindip: 0.0.0.0
port: 3040
database:
type: mysql
user: root
password: 1000omc@kp!
host: 127.0.0.1
port: 33066
name: omc_db
cmfiledir: ../../config/cm

22
tools/loadcmxls/makefile Normal file
View File

@@ -0,0 +1,22 @@
# Makefile for rest agent project
PROJECT = OMC
VERSION = 5GC16.1.1
PLATFORM = amd64
DEBDIR = ../../../deb
ETCDIR = ../../../etc
RELEASEDIR = ../../../release
LIBDIR = ../lib
BINNAME = loadcmxls
.PHONY: build $(BINNAME)
build $(BINNAME):
go build -o $(BINNAME) -v -ldflags "-X 'main.version=$(VERSION)' \
-X 'main.buildTime=`date`' \
-X 'main.goVer=`go version`'"
run: $(BINNAME)
./$(BINNAME)
clean:
rm ./$(BINNAME)

88
tools/loadmconf/db.go Normal file
View File

@@ -0,0 +1,88 @@
package main
import (
"encoding/json"
"fmt"
"strings"
_ "github.com/go-sql-driver/mysql"
"xorm.io/xorm"
)
var xEngine *xorm.Engine
func XormConnectDatabaseWithUri(sql string) (*xorm.Engine, error) {
// sqlStr := fmt.Sprintf("%s:%s@tcp(%s:%s)/%s?charset=utf8&parseTime=true&loc=Local", db.User, db.Password, db.Host, db.Port, db.Name)
sqlStr := fmt.Sprintf("%s?charset=utf8&parseTime=true&loc=Local", sql)
// fmt.Printf("sqlStr:%s:******@tcp(%s:%s)/%s?charset=utf8&parseTime=true&loc=Local", db.User, db.Host, db.Port, db.Name)
var err error
xEngine, err = xorm.NewEngine("mysql", sqlStr) //1、Create xorm engine
if err != nil {
fmt.Println("Failed to connect database:", err)
return nil, err
}
xEngine.ShowSQL(true)
return xEngine, nil
}
type MmlCommand struct {
// Id int `json:"id" xorm:"pk 'id' autoincr"`
NeType string `json:"neType"`
Category string `json:"category"`
CatDisplay string `json:"display" xorm:"cat_display"`
Operation string `json:"operation"`
Object string `json:"object"`
MmlDisplay string `json:"display" xorm:"mml_display"`
ParamJson string `json:"paramJson"`
}
func XormInsertMMLConfig(mapJson *map[string]interface{}, tableName string) (int64, error) {
var affected, a int64
var err error
mmlCommand := new(MmlCommand)
for n, d := range *mapJson {
if d == nil {
break
}
fmt.Println("n:", n)
mmlCommand.NeType = strings.ToUpper(n)
// for c, ma := range d.(map[string]interface{}) {
for c, ci := range d.(map[string]interface{}) {
fmt.Println("c:", c)
fmt.Println("ci:", ci)
mmlCommand.Category = c
mmlCommand.CatDisplay = fmt.Sprintf("%v", ci.(map[string]interface{})["display"])
mml := ci.(map[string]interface{})["mml"]
for m, mi := range mml.([]interface{}) {
fmt.Println("m:", m)
fmt.Println("mi:", mi)
mmlCommand.Operation = fmt.Sprintf("%v", mi.(map[string]interface{})["operation"])
mmlCommand.Object = fmt.Sprintf("%v", mi.(map[string]interface{})["object"])
mmlCommand.MmlDisplay = fmt.Sprintf("%v", mi.(map[string]interface{})["display"])
pj, _ := json.Marshal(mi.(map[string]interface{})["params"])
mmlCommand.ParamJson = string(pj)
fmt.Println("mmlCommand:", mmlCommand)
session := xEngine.NewSession()
defer session.Close()
_, err = session.
Table(tableName).
Where("ne_type = ? and category = ? and operation = ? and object = ?", mmlCommand.NeType, mmlCommand.Category, mmlCommand.Operation, mmlCommand.Object).
Delete()
if err != nil {
fmt.Printf("Failed to delete %s: %v\n", tableName, err)
}
a, err = session.Table(tableName).Insert(mmlCommand)
if err != nil {
fmt.Printf("Failed to insert %s: %v\n", tableName, err)
}
affected += a
}
}
}
return affected, err
}

131
tools/loadmconf/load.go Normal file
View File

@@ -0,0 +1,131 @@
package main
import (
"flag"
"fmt"
"io/ioutil"
"os"
"gopkg.in/yaml.v3"
)
// Yaml struct of config
type YamlConfig struct {
Logger struct {
File string `yaml:"file"`
Level string `yaml:"level"`
} `yaml:"logger"`
Rest struct {
BindIP string `yaml:"bindip"`
Port uint16 `yaml:"port"`
} `yaml:"rest"`
Database struct {
Type string `yaml:"type"`
User string `yaml:"user"`
Password string `yaml:"password"`
Host string `yaml:"host"`
Port string `yaml:"port"`
Name string `yaml:"name"`
} `yaml:"database"`
Mml struct {
FileDir string `yaml:"filedir"`
Table string `yaml:"table"`
} `yaml:"mml"`
}
var yamlConfig YamlConfig
func ReadConfig(configFile string) {
yamlFile, err := ioutil.ReadFile(configFile)
if err != nil {
fmt.Printf("ioutil.ReadFile %s err %v", configFile, err)
}
// fmt.Println("yamlfile:", string(yamlFile))
err = yaml.Unmarshal(yamlFile, &yamlConfig)
if err != nil {
fmt.Printf("Unmarshal: %v when to struct", err)
}
}
func GetYamlConfig() *YamlConfig {
return &yamlConfig
}
var mapYaml map[string]interface{}
func ReadMMLConfig(fileName string) *map[string]interface{} {
file, err := ioutil.ReadFile(fileName)
if err != nil {
fmt.Println("yamlFile.Get err", err)
}
mapYaml = make(map[string]interface{})
err = yaml.Unmarshal(file, &mapYaml)
if err != nil {
fmt.Println("yaml.Unmarshal: %v when to struct", err)
}
// fmt.Println("mapYaml:", mapYaml)
return &mapYaml
}
func GetAllFile(dir string, s []string) ([]string, error) {
fmt.Println("GetAllFile processing...", dir)
fmt.Println("dir:", dir)
rd, err := ioutil.ReadDir(dir)
if err != nil {
fmt.Println("read dir fail:", err)
return s, err
}
for _, fi := range rd {
if !fi.IsDir() {
fullName := dir + "/" + fi.Name()
s = append(s, fullName)
}
}
return s, nil
}
const defaultConfigFile = "./loadmconf.yaml"
var (
version string
buildTime string
goVer string
)
var pfiles []string
func init() {
cfile := flag.String("c", defaultConfigFile, "config file")
pfile := flag.String("m", "", "mmlconf file")
pv := flag.Bool("v", false, "print version")
ph := flag.Bool("h", false, "print help")
flag.Parse()
if *pv {
fmt.Printf("OMC loadmconf version: %s\n%s\n%s\n\n", version, buildTime, goVer)
os.Exit(0)
}
if *ph {
flag.Usage()
os.Exit(0)
}
ReadConfig(*cfile)
fmt.Println("pfile:", *pfile)
if *pfile != "" {
pfiles = append(pfiles, *pfile)
} else {
pfiles, _ = GetAllFile(yamlConfig.Mml.FileDir, pfiles)
}
fmt.Println("pfiles:", pfiles)
}

BIN
tools/loadmconf/loadmconf Normal file

Binary file not shown.

View File

@@ -0,0 +1,21 @@
package main
import (
"fmt"
)
func main() {
fmt.Println("========================= OMC loadmconf startup =========================")
fmt.Println("OMC loadmconf version: %s %s %s", version, buildTime, goVer)
for _, f := range pfiles {
fmt.Println("f:", f)
mmlMap := ReadMMLConfig(f)
fmt.Println("mmlMap:", mmlMap)
db := yamlConfig.Database
sqlStr := fmt.Sprintf("%s:%s@tcp(%s:%s)/%s", db.User, db.Password, db.Host, db.Port, db.Name)
XormConnectDatabaseWithUri(sqlStr)
XormInsertMMLConfig(mmlMap, yamlConfig.Mml.Table)
}
}

View File

@@ -0,0 +1,19 @@
logger:
file: ./loadmconf.log
level: trace
rest:
bindip: 0.0.0.0
port: 3040
database:
type: mysql
user: root
password: 1000omc@kp!
host: 127.0.0.1
port: 33066
name: omc_db
mml:
filedir: ../../config/mml/omc
table: mml_command

22
tools/loadmconf/makefile Normal file
View File

@@ -0,0 +1,22 @@
# Makefile for rest agent project
PROJECT = OMC
VERSION = 5GC16.1.1
PLATFORM = amd64
DEBDIR = ../../../deb
ETCDIR = ../../../etc
RELEASEDIR = ../../../release
LIBDIR = ../lib
BINNAME = loadmconf
.PHONY: build $(BINNAME)
build $(BINNAME):
go build -o $(BINNAME) -v -ldflags "-X 'main.version=$(VERSION)' \
-X 'main.buildTime=`date`' \
-X 'main.goVer=`go version`'"
run: $(BINNAME)
./$(BINNAME)
clean:
rm ./$(BINNAME)

88
tools/loadpconf/db.go Normal file
View File

@@ -0,0 +1,88 @@
package main
import (
"encoding/json"
"fmt"
"strings"
_ "github.com/go-sql-driver/mysql"
"xorm.io/xorm"
)
var xEngine *xorm.Engine
func XormConnectDatabaseWithUri(sql string) (*xorm.Engine, error) {
// sqlStr := fmt.Sprintf("%s:%s@tcp(%s:%s)/%s?charset=utf8&parseTime=true&loc=Local", db.User, db.Password, db.Host, db.Port, db.Name)
sqlStr := fmt.Sprintf("%s?charset=utf8&parseTime=true&loc=Local", sql)
// fmt.Printf("sqlStr:%s:******@tcp(%s:%s)/%s?charset=utf8&parseTime=true&loc=Local", db.User, db.Host, db.Port, db.Name)
var err error
xEngine, err = xorm.NewEngine("mysql", sqlStr) //1、Create xorm engine
if err != nil {
fmt.Println("Failed to connect database:", err)
return nil, err
}
xEngine.ShowSQL(true)
return xEngine, nil
}
type ParamConfig struct {
// Id int `json:"id" xorm:"pk 'id' autoincr"`
NeType string `json:"neType"`
NeId string `json:"neId"`
TopTag string `json:"topTag"`
TopDisplay string `json:"topDisplay"`
ParamJson string `json:"paramJson"`
}
func XormInsertParamConfig(mapJson *map[string]interface{}) (int64, error) {
var affected, a int64
var err error
paramConfig := new(ParamConfig)
for n, d := range *mapJson {
if d == nil {
break
}
fmt.Printf("n: %s", n)
for t, p := range d.(map[string]interface{}) {
if p == nil {
break
}
fmt.Println("t:", t)
fmt.Println("p:", p)
for k, v := range p.(map[string]interface{}) {
fmt.Println("k, v: ", k, v)
if k == "display" {
paramConfig.TopDisplay = fmt.Sprintf("%v", v)
} else {
pc, _ := json.Marshal(v)
paramConfig.ParamJson = fmt.Sprintf("{\"%v\":%v}", k, string(pc))
}
}
paramConfig.NeType = strings.ToUpper(n)
paramConfig.NeId = ""
paramConfig.TopTag = t
// paramConfig.TopDisplay = p["display"]
// paramConfig.ParamJson = p.(string)
fmt.Println("paramConfig:", paramConfig)
session := xEngine.NewSession()
defer session.Close()
_, err = session.Table("param_config").Where("ne_type = ? and top_tag = ?", paramConfig.NeType, paramConfig.TopTag).Delete()
if err != nil {
fmt.Println("Failed to delete param_config:", err)
}
a, err = session.Insert(paramConfig)
if err != nil {
fmt.Println("Failed to insert param_config:", err)
}
affected += a
}
}
return affected, err
}

124
tools/loadpconf/load.go Normal file
View File

@@ -0,0 +1,124 @@
package main
import (
"flag"
"fmt"
"io/ioutil"
"os"
"gopkg.in/yaml.v3"
)
// Yaml struct of config
type YamlConfig struct {
Logger struct {
File string `yaml:"file"`
Level string `yaml:"level"`
}
Rest struct {
Addr string `yaml:"addr"`
Port uint16 `yaml:"port"`
}
Database struct {
Type string `yaml:"type"`
User string `yaml:"user"`
Password string `yaml:"password"`
Host string `yaml:"host"`
Port string `yaml:"port"`
Name string `yaml:"name"`
}
ParamFileDir string `yaml:"paramfiledir"`
}
var yamlConfig YamlConfig
func ReadConfig(configFile string) {
yamlFile, err := ioutil.ReadFile(configFile)
if err != nil {
fmt.Printf("ioutil.ReadFile %s err %v", configFile, err)
}
// fmt.Println("yamlfile:", string(yamlFile))
err = yaml.Unmarshal(yamlFile, &yamlConfig)
if err != nil {
fmt.Printf("Unmarshal: %v when to struct", err)
}
}
func GetYamlConfig() *YamlConfig {
return &yamlConfig
}
var mapYaml map[string]interface{}
func ReadParamConfig(fileName string) *map[string]interface{} {
file, err := ioutil.ReadFile(fileName)
if err != nil {
fmt.Println("yamlFile.Get err", err)
}
mapYaml = make(map[string]interface{})
err = yaml.Unmarshal(file, &mapYaml)
if err != nil {
fmt.Println("yaml.Unmarshal: %v when to struct", err)
}
// fmt.Println("mapYaml:", mapYaml)
return &mapYaml
}
func GetAllFile(dir string, s []string) ([]string, error) {
rd, err := ioutil.ReadDir(dir)
if err != nil {
fmt.Println("read dir fail:", err)
return s, err
}
for _, fi := range rd {
if !fi.IsDir() {
fullName := dir + "/" + fi.Name()
s = append(s, fullName)
}
}
return s, nil
}
const defaultConfigFile = "./loadpconf.yaml"
var (
version string
buildTime string
goVer string
)
var pfiles []string
func init() {
cfile := flag.String("c", defaultConfigFile, "config file")
pfile := flag.String("p", "", "param file")
pv := flag.Bool("v", false, "print version")
ph := flag.Bool("h", false, "print help")
flag.Parse()
if *pv {
fmt.Printf("OMC initems version: %s\n%s\n%s\n\n", version, buildTime, goVer)
os.Exit(0)
}
if *ph {
flag.Usage()
os.Exit(0)
}
ReadConfig(*cfile)
fmt.Println("pfile:", *pfile)
if *pfile != "" {
pfiles = append(pfiles, *pfile)
} else {
pfiles, _ = GetAllFile(yamlConfig.ParamFileDir, pfiles)
}
fmt.Println("pfiles:", pfiles)
}

BIN
tools/loadpconf/loadpconf Normal file

Binary file not shown.

View File

@@ -0,0 +1,21 @@
package main
import (
"fmt"
)
func main() {
fmt.Println("========================= OMC loadpconf startup =========================")
fmt.Println("OMC loadpconf version: %s %s %s", version, buildTime, goVer)
for _, f := range pfiles {
fmt.Println("f:", f)
paramMap := ReadParamConfig(f)
fmt.Println("paramMap:", paramMap)
db := yamlConfig.Database
sqlStr := fmt.Sprintf("%s:%s@tcp(%s:%s)/%s", db.User, db.Password, db.Host, db.Port, db.Name)
XormConnectDatabaseWithUri(sqlStr)
XormInsertParamConfig(paramMap)
}
}

View File

@@ -0,0 +1,17 @@
logger:
file: ./initems.log
level: trace
rest:
addr: 0.0.0.0
port: 3040
database:
type: mysql
user: root
password: 1000omc@kp!
host: 127.0.0.1
port: 33066
name: omc_db
paramfiledir: ../../config/param

22
tools/loadpconf/makefile Normal file
View File

@@ -0,0 +1,22 @@
# Makefile for rest agent project
PROJECT = OMC
VERSION = 5GC16.1.1
PLATFORM = amd64
DEBDIR = ../../../deb
ETCDIR = ../../../etc
RELEASEDIR = ../../../release
LIBDIR = ../lib
BINNAME = loadpconf
.PHONY: build $(BINNAME)
build $(BINNAME):
go build -o $(BINNAME) -v -ldflags "-X 'main.version=$(VERSION)' \
-X 'main.buildTime=`date`' \
-X 'main.goVer=`go version`'"
run: $(BINNAME)
./$(BINNAME)
clean:
rm ./$(BINNAME)

BIN
tools/loadpmxls/1.txt Normal file

Binary file not shown.

55
tools/loadpmxls/db.go Normal file
View File

@@ -0,0 +1,55 @@
package main
import (
"fmt"
_ "github.com/go-sql-driver/mysql"
"xorm.io/xorm"
)
var xEngine *xorm.Engine
func XormConnectDatabaseWithUri(sql string) (*xorm.Engine, error) {
// sqlStr := fmt.Sprintf("%s:%s@tcp(%s:%s)/%s?charset=utf8&parseTime=true&loc=Local", db.User, db.Password, db.Host, db.Port, db.Name)
sqlStr := fmt.Sprintf("%s?charset=utf8&parseTime=true&loc=Local", sql)
// fmt.Printf("sqlStr:%s:******@tcp(%s:%s)/%s?charset=utf8&parseTime=true&loc=Local", db.User, db.Host, db.Port, db.Name)
var err error
xEngine, err = xorm.NewEngine("mysql", sqlStr) //1、Create xorm engine
if err != nil {
fmt.Println("Failed to connect database:", err)
return nil, err
}
xEngine.ShowSQL(true)
return xEngine, nil
}
type MeasureTitle struct {
// Id int `json:"id" xorm:"pk 'id' autoincr"`
NeType string `json:"neType"`
KpiCode string `json:"kpiCode"`
KpiId string `json:"kpiId" xorm:"kpi_id"`
Pseudo string `json:"pseudo" xorm:"pseudo"`
ObjectType string `json:"objectType" xorm:"object_type"`
Period string `json:"period" xorm:"period"`
TitleJson string `json:"titleJson" xorm:"title_json"`
Description string `json:"description"`
}
func XormInsertMeasureTitle(row *MeasureTitle) (int64, error) {
session := xEngine.NewSession()
defer session.Close()
_, err := session.
Table("measure_title").
Where("ne_type = ? and kpi_code = ? and kpi_id = ?", row.NeType, row.KpiCode, row.KpiId).
Delete()
if err != nil {
fmt.Println("Failed to delete measure_title:", err)
}
affected, err := session.Table("measure_title").Insert(row)
if err != nil {
fmt.Println("Failed to insert measure_title:", err)
}
return affected, err
}

109
tools/loadpmxls/load.go Normal file
View File

@@ -0,0 +1,109 @@
package main
import (
"flag"
"fmt"
"io/ioutil"
"os"
"gopkg.in/yaml.v3"
)
// Yaml struct of config
type YamlConfig struct {
Logger struct {
File string `yaml:"file"`
Level string `yaml:"level"`
} `yaml:"logger"`
Rest struct {
BindIP string `yaml:"bindip"`
Port uint16 `yaml:"port"`
} `yaml:"rest"`
Database struct {
Type string `yaml:"type"`
User string `yaml:"user"`
Password string `yaml:"password"`
Host string `yaml:"host"`
Port string `yaml:"port"`
Name string `yaml:"name"`
} `yaml:"database"`
PmFileDir string `yaml:"pmfiledir"`
}
var yamlConfig YamlConfig
func ReadConfig(configFile string) {
yamlFile, err := ioutil.ReadFile(configFile)
if err != nil {
fmt.Printf("ioutil.ReadFile %s err %v", configFile, err)
}
// fmt.Println("yamlfile:", string(yamlFile))
err = yaml.Unmarshal(yamlFile, &yamlConfig)
if err != nil {
fmt.Printf("Unmarshal: %v when to struct", err)
}
}
func GetYamlConfig() *YamlConfig {
return &yamlConfig
}
func GetAllFile(dir string, s []string) ([]string, error) {
fmt.Println("GetAllFile processing...", dir)
fmt.Println("dir:", dir)
rd, err := ioutil.ReadDir(dir)
if err != nil {
fmt.Println("read dir fail:", err)
return s, err
}
for _, fi := range rd {
if !fi.IsDir() {
fullName := dir + "/" + fi.Name()
s = append(s, fullName)
}
}
return s, nil
}
const defaultConfigFile = "./loadpmxls.yaml"
var (
version string
buildTime string
goVer string
)
var pfiles []string
func init() {
cfile := flag.String("c", defaultConfigFile, "config file")
pfile := flag.String("f", "", "pm file")
pv := flag.Bool("v", false, "print version")
ph := flag.Bool("h", false, "print help")
flag.Parse()
if *pv {
fmt.Printf("OMC loadpmxls version: %s\n%s\n%s\n\n", version, buildTime, goVer)
os.Exit(0)
}
if *ph {
flag.Usage()
os.Exit(0)
}
ReadConfig(*cfile)
fmt.Println("pfile:", *pfile)
if *pfile != "" {
pfiles = append(pfiles, *pfile)
} else {
pfiles, _ = GetAllFile(yamlConfig.PmFileDir, pfiles)
}
fmt.Println("pfiles:", pfiles)
}

BIN
tools/loadpmxls/loadpmxls Normal file

Binary file not shown.

View File

@@ -0,0 +1,73 @@
package main
import (
"encoding/json"
"fmt"
"strings"
"github.com/xuri/excelize/v2"
)
func main() {
fmt.Println("========================= OMC loadpmxls startup =========================")
fmt.Println("OMC loadpmxls version: %s %s %s", version, buildTime, goVer)
for _, f := range pfiles {
fmt.Println("f:", f)
db := yamlConfig.Database
sqlStr := fmt.Sprintf("%s:%s@tcp(%s:%s)/%s", db.User, db.Password, db.Host, db.Port, db.Name)
XormConnectDatabaseWithUri(sqlStr)
LoadPmIntoMeasureTitle(f)
}
}
func LoadPmIntoMeasureTitle(file string) {
fmt.Println("file len:", file, len(file))
f, err := excelize.OpenFile(file)
if err != nil {
fmt.Println(err.Error())
return
}
list := f.GetSheetList()
if err != nil {
fmt.Println(err.Error())
return
}
fmt.Println(list)
dl := len(yamlConfig.PmFileDir) + 1
neType := file[dl : dl+3]
fmt.Println("neType:", neType)
for _, s := range list {
if s[0] == 'H' {
rows, _ := f.GetRows(s)
var kpiCode, desc, objectType string
for _, row := range rows[1:] {
if row[0] != "" {
kpiCode = row[0]
}
if len(row) > 4 && row[4] != "" {
desc = row[4]
}
if len(row) > 9 && row[9] != "" {
objectType = row[9]
}
enKpiId := strings.Replace(row[2], " ", "", -1)
enKpiId = strings.Replace(enKpiId, "\n", "", -1)
isPseudo := "false"
if strings.Contains(enKpiId, "_") {
isPseudo = "true"
}
cnKpiId := strings.Replace(row[3], " ", "", -1)
cnKpiId = strings.Replace(cnKpiId, "\n", "", -1)
titleJson := map[string]string{"cn": cnKpiId, "en": enKpiId}
tj, _ := json.Marshal(titleJson)
measureTitle := MeasureTitle{neType, kpiCode, enKpiId, isPseudo, objectType, "15M", string(tj), desc}
fmt.Println("measureTitle:", measureTitle)
//fmt.Print(kpiCode, "\t", row[2], "\t", row[3], "\t", row[4], "\n")
XormInsertMeasureTitle(&measureTitle)
}
}
}
}

View File

@@ -0,0 +1,17 @@
logger:
file: ./loadpmxls.log
level: trace
rest:
bindip: 0.0.0.0
port: 3040
database:
type: mysql
user: root
password: 1000omc@kp!
host: 127.0.0.1
port: 33066
name: omc_db
pmfiledir: ../../config/pm

View File

@@ -0,0 +1,38 @@
package main
import (
"fmt"
"github.com/xuri/excelize/v2"
)
func main() {
file := "AMF-PM(V1.1.5)-Company-Version00.xlsx"
f, err := excelize.OpenFile(file)
if err != nil {
fmt.Println(err.Error())
return
}
list := f.GetSheetList()
if err != nil {
fmt.Println(err.Error())
return
}
fmt.Println(list)
neType := file[0:3]
fmt.Println("neType:", neType)
for _, s := range list {
if s[0] == 'H' {
rows, _ := f.GetRows(s)
var kpiCode string
for _, row := range rows[1:] {
if row[0] != "" {
kpiCode = row[0]
}
fmt.Print(kpiCode, "\t", row[2], "\t", row[3], "\t", row[4], "\n")
}
}
}
}

22
tools/loadpmxls/makefile Normal file
View File

@@ -0,0 +1,22 @@
# Makefile for rest agent project
PROJECT = OMC
VERSION = 5GC16.1.1
PLATFORM = amd64
DEBDIR = ../../../deb
ETCDIR = ../../../etc
RELEASEDIR = ../../../release
LIBDIR = ../lib
BINNAME = loadpmxls
.PHONY: build $(BINNAME)
build $(BINNAME):
go build -o $(BINNAME) -v -ldflags "-X 'main.version=$(VERSION)' \
-X 'main.buildTime=`date`' \
-X 'main.goVer=`go version`'"
run: $(BINNAME)
./$(BINNAME)
clean:
rm ./$(BINNAME)

33
tools/misc/dumpdb.sh Normal file
View File

@@ -0,0 +1,33 @@
#!/bin/bash
home="/home/simon"
project="goprojects"
user="root"
password="1000omc@kp!"
host="192.168.2.119"
port="33066"
dbname="omc_db"
dumpdbdir=${home}/${project}/ems.agt/tools/misc
insdir=${home}/${project}/ems.agt/database/install
upgdir=${home}/${project}/ems.agt/database/upgrade
tables_c=tables_c.lst
tables_s=tables_s.lst
#mysql -u ${user} -p${password} -D ${dbname} -e "show tables ; " > tables.lst
# dump table struct and data
while read line
do
table=`echo $line | cut -d " " -f 1`
echo "dump ${table} to install & upgrade directory"
mysqldump -h ${host} -P ${port} -u ${user} -p${password} ${dbname} ${table} > ${insdir}/${table}.sql
mysqldump -h ${host} -P ${port} -u ${user} -p${password} ${dbname} ${table} > ${upgdir}/${table}.sql
done < ${dumpdbdir}/${tables_c}
# dump table struct
while read line
do
table=`echo $line | cut -d " " -f 1`
echo "dump ${table} to install directory"
mysqldump -h ${host} -P ${port} -u ${user} -p${password} -d ${dbname} ${table} > ${insdir}/${table}.sql
done < ${dumpdbdir}/${tables_s}

10
tools/misc/rsyncsmb.sh Normal file
View File

@@ -0,0 +1,10 @@
#!/bin/bash
# 源目录Windows目录
SRC_DIR="192.168.2.119:/goprojects"
# 目标目录Samba目录
DST_DIR="/home/simon/goprojects"
# 同步目录
#rsync -avz --delete "$SRC_DIR/" "$DST_DIR/"
rsync -avz --delete --user=myuser --password-file=/path/to/password.txt "$SRC_DIR/" "$DST_DIR/"

15
tools/misc/tables_c.lst Normal file
View File

@@ -0,0 +1,15 @@
alarm_define
cm_title
config
group
kpi_title
measure_title
menu
mml_command
mml_http_map
mml_subscriber
mml_system
param_config
title_info
trace_info
user_menu

39
tools/misc/tables_s.lst Normal file
View File

@@ -0,0 +1,39 @@
4a_log
alarm
alarm_forward_log
alarm_log
alarm_relation
alarm_subscribe
event_log
gold_kpi
measure_data
measure_task
measure_threshold
mml_log
nbi_alarm_log
nbi_operation_log
nbi_secure_log
ne_backup
ne_info
ne_license
ne_link
ne_software
ne_state
ne_version
northbound_cm
northbound_pm
operation_log
param_value
pm_custom_data
pm_custom_title
rs_subscribe
security_log
session
system_log
trace_data
trace_task
permission
role_permission
role
user
user_role

94
tools/websocket/load.go Normal file
View File

@@ -0,0 +1,94 @@
package main
import (
"flag"
"fmt"
"io/ioutil"
"os"
"strings"
"ems.agt/lib/log"
"gopkg.in/yaml.v3"
)
// Yaml struct of config
type YamlConfig struct {
Logger struct {
File string `yaml:"file"`
Level string `yaml:"level"`
Duration int `yaml:"duration"`
}
Rest struct {
BindIP string `yaml:"bindip"`
Port uint16 `yaml:"port"`
}
}
var yamlConfig YamlConfig
func ReadConfig(configFile string) {
yamlFile, err := ioutil.ReadFile(configFile)
if err != nil {
fmt.Printf("ioutil.ReadFile %s err %v", configFile, err)
}
// fmt.Println("yamlfile:", string(yamlFile))
err = yaml.Unmarshal(yamlFile, &yamlConfig)
if err != nil {
fmt.Printf("Unmarshal: %v when to struct", err)
}
}
func GetYamlConfig() *YamlConfig {
return &yamlConfig
}
func GetLogLevel() log.LogLevel {
var logLevel log.LogLevel
switch strings.ToLower(yamlConfig.Logger.Level) {
case "trace":
logLevel = log.LOG_TRACE
case "info":
logLevel = log.LOG_INFO
case "debug":
logLevel = log.LOG_DEBUG
case "warn":
logLevel = log.LOG_WARN
case "error":
logLevel = log.LOG_ERROR
case "fatal":
logLevel = log.LOG_FATAL
case "off":
logLevel = log.LOG_OFF
default:
logLevel = log.LOG_DEBUG
}
return logLevel
}
const defaultConfigFile = "./tt.yaml"
var (
version string
buildTime string
goVer string
)
func init() {
cfile := flag.String("c", defaultConfigFile, "config file")
pv := flag.Bool("v", false, "print version")
ph := flag.Bool("h", false, "print help")
flag.Parse()
if *pv {
fmt.Printf("OMC version: %s\n%s\n%s\n\n", version, buildTime, goVer)
os.Exit(0)
}
if *ph {
flag.Usage()
os.Exit(0)
}
ReadConfig(*cfile)
}

87
tools/websocket/tt.go Normal file
View File

@@ -0,0 +1,87 @@
package main
import (
"fmt"
"net"
"os"
"time"
"ems.agt/lib/log"
)
const (
//经过测试linux下延时需要大于100ms
TIME_DELAY_AFTER_WRITE = 500 //500ms
)
func main() {
log.InitLogger(yamlConfig.Logger.File, yamlConfig.Logger.Duration, "omc:tt", GetLogLevel())
fmt.Printf("OMC tt version: %s\n", version)
log.Infof("========================= OMC tt startup =========================")
log.Infof("OMC tt version: %s %s %s", version, buildTime, goVer)
conn, err := net.Dial("tcp", "192.168.4.233:4100")
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
var buf [8192]byte
var n int
n, err = conn.Write([]byte("admin\nadmin\n"))
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
time.Sleep(time.Millisecond * TIME_DELAY_AFTER_WRITE)
n, err = conn.Read(buf[0:])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
log.Debug(string(buf[0:n]))
n, err = conn.Write([]byte("date\n"))
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
time.Sleep(time.Millisecond * TIME_DELAY_AFTER_WRITE)
n, err = conn.Read(buf[0:])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
log.Debug(string(buf[0 : n-5]))
/*
n, err = conn.Write([]byte("\n"))
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
time.Sleep(time.Millisecond * TIME_DELAY_AFTER_WRITE)
n, err = conn.Read(buf[0:])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
log.Debug(string(buf[0:n]))
log.Debug(string(buf[0:n]))
*/
/* n, err = conn.Write([]byte("\n"))
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
n, err = conn.Read(buf[0:])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
*/
}

15
tools/websocket/tt.yaml Normal file
View File

@@ -0,0 +1,15 @@
logger:
file: ./tt.log
level: trace
rest:
addr: 0.0.0.0
port: 3040
database:
type: mysql
user: root
password: 1000omc@kp!
host: 127.0.0.1
port: 33066
name: omc_db

11
tools/websocket/ttt.go Normal file
View File

@@ -0,0 +1,11 @@
package main
import (
"github.com/reiver/go-telnet"
)
func main() {
var caller telnet.Caller = telnet.StandardCaller
telnet.DialToAndCall("192.168.4.233:4100", caller)
}

View File

@@ -0,0 +1,301 @@
package main
import (
"fmt"
"io"
"net"
"net/http"
"os"
"time"
"github.com/gin-gonic/gin"
"github.com/go-admin-team/go-admin-core/sdk/api"
"github.com/gorilla/websocket"
"github.com/ziutek/telnet"
"golang.org/x/crypto/ssh"
"golang.org/x/crypto/ssh/terminal"
)
type TgWs struct {
api.Api
}
var upGrader = websocket.Upgrader{
ReadBufferSize: 1024,
WriteBufferSize: 1024 * 1024 * 10,
CheckOrigin: func(r *http.Request) bool {
return true
},
}
type ShellInfoStruct struct {
Proto string `json:"proto"`
IpAddr string `json:"ipaddr"`
Port string `json:"port"`
}
type wsWrapper struct {
*websocket.Conn
}
func main() {
telnetHandle(rw io.ReadWriter, ip, port string, errhandle func(string)) {
}
func init() {
routerCheckRole = append(routerCheckRole, registerTgWsRouter)
}
// 需认证的路由代码
func registerTgWsRouter(v1 *gin.RouterGroup, authMiddleware *jwt.GinJWTMiddleware) {
api := apis.TgWs{}
r := v1.Group("")
{
// 协议、IP、端口
r.GET("/tgws/:proto/:ipaddr/:port", api.TgWsWeb)
}
}
func (e TgWs) TgWsWeb(c *gin.Context) {
// 初始化返回信息
err := e.MakeContext(c).Errors
if err != nil {
e.Logger.Error(err)
e.Error(500, err, fmt.Sprintf(" %s ", err.Error()))
return
}
// 升级为websocket
wsConn, err := upGrader.Upgrade(c.Writer, c.Request, nil)
if err != nil {
e.Logger.Error(err)
e.Error(500, err, "websocket client connect error")
return
}
defer wsConn.Close()
proto := c.Param("proto")
ipaddr := c.Param("ipaddr")
port := c.Param("port")
shellinfo := ShellInfoStruct{
Proto: proto,
IpAddr: ipaddr,
Port: port,
}
quitChan := make(chan bool, 1)
go websocketHandle(wsConn, shellinfo, quitChan)
<-quitChan
}
func websocketHandle(con *websocket.Conn, shellinfo ShellInfoStruct, exitCh chan bool) {
defer setQuit(exitCh)
rw := io.ReadWriter(&wsWrapper{con})
webprintln := func(data string) {
rw.Write([]byte(data + "\r\n"))
}
con.SetCloseHandler(func(code int, text string) error {
con.Close()
return nil
})
switch shellinfo.Proto {
case "ssh":
sshHandle(rw, shellinfo.IpAddr, shellinfo.Port, "XXX", "XXX", webprintln)
case "telnet":
telnetHandle(rw, shellinfo.IpAddr, shellinfo.Port, webprintln)
case "bind_shell":
bindShellHandler(rw, shellinfo.IpAddr, shellinfo.Port, webprintln)
default:
webprintln("Not Support Protocol '" + shellinfo.Proto + "'")
}
return
}
func (wsw *wsWrapper) Write(p []byte) (n int, err error) {
writer, err := wsw.Conn.NextWriter(websocket.TextMessage)
if err != nil {
return 0, err
}
defer writer.Close()
return writer.Write(p)
}
func (wsw *wsWrapper) Read(p []byte) (n int, err error) {
for {
msgType, reader, err := wsw.Conn.NextReader()
if err != nil {
return 0, err
}
if msgType != websocket.TextMessage {
continue
}
return reader.Read(p)
}
}
// SSH连接
func sshHandle(rw io.ReadWriter, ip, port, user, passwd string, errhandle func(string)) {
sshConfig := &ssh.ClientConfig{
User: user,
Auth: []ssh.AuthMethod{ssh.Password(passwd)},
Timeout: 6 * time.Second,
}
sshConfig.HostKeyCallback = ssh.InsecureIgnoreHostKey()
if port == "" {
ip = ip + ":22"
} else {
ip = ip + ":" + port
}
client, err := ssh.Dial("tcp", ip, sshConfig)
if err != nil {
errhandle(err.Error())
return
}
defer client.Close()
session, err := client.NewSession()
if err != nil {
errhandle(err.Error())
return
}
defer session.Close()
fd := int(os.Stdin.Fd())
session.Stdout = rw
session.Stderr = rw
session.Stdin = rw
modes := ssh.TerminalModes{
ssh.ECHO: 1,
ssh.TTY_OP_ISPEED: 14400,
ssh.TTY_OP_OSPEED: 14400,
}
termWidth, termHeight, err := terminal.GetSize(fd)
err = session.RequestPty("xterm", termHeight, termWidth, modes)
if err != nil {
errhandle(err.Error())
}
err = session.Shell()
if err != nil {
errhandle(err.Error())
}
err = session.Wait()
if err != nil {
errhandle(err.Error())
}
return
}
// telnet连接
func telnetHandle(rw io.ReadWriter, ip, port string, errhandle func(string)) {
if port == "" {
ip = ip + ":23"
} else {
ip = ip + ":" + port
}
con, err := telnet.Dial("tcp", ip)
if err != nil {
errhandle(err.Error())
return
}
defer con.Close()
buf := make([]byte, 16*1024)
// 从远端读取返回结果并回显页面
go func() {
for {
n, err := con.Read(buf)
if err != nil {
errhandle(err.Error())
break
}
_, err = rw.Write(buf[:n])
if err != nil {
errhandle(err.Error())
break
}
}
}()
for {
// 从页面读取命令
n, err := rw.Read(buf)
if err != nil {
errhandle(err.Error())
break
}
if buf[0] == 13 { // 处理换行
data := []byte{telnet.CR, telnet.LF}
_, err = con.Write(data)
} else {
_, err = con.Write(buf[:n])
}
if err != nil {
errhandle(err.Error())
break
}
}
return
}
// 正向shell
func bindShellHandler(rw io.ReadWriter, ip, port string, errhandle func(string)) {
server := ip + ":" + port
//获取命令行参数 socket地址
addr, err := net.ResolveTCPAddr("tcp4", server)
if err != nil {
errhandle(err.Error())
return
}
//建立tcp连接
con, err := net.DialTCP("tcp4", nil, addr)
if err != nil {
errhandle(err.Error())
return
}
rw.Write([]byte("reverse shell connected " + "\r\n"))
defer con.Close()
buf := make([]byte, 16*1024)
go func() {
for {
n, err := con.Read(buf)
if err != nil {
errhandle(err.Error())
break
}
_, err = rw.Write(buf[:n])
if err != nil {
errhandle(err.Error())
break
}
}
}()
for {
n, err := rw.Read(buf)
if err != nil {
errhandle(err.Error())
break
}
_, err = rw.Write(buf[:n])
if err != nil {
errhandle(err.Error())
break
}
if buf[0] == 13 {
data := []byte{telnet.LF}
_, err = con.Write(data)
rw.Write([]byte("\r\n"))
} else {
_, err = con.Write(buf[:n])
}
if err != nil {
errhandle(err.Error())
break
}
}
return
}
func setQuit(ch chan bool) {
ch <- true
}

290
tools/websocket/webtel.go Normal file
View File

@@ -0,0 +1,290 @@
package main
import (
"fmt"
"net"
"os"
)
func main() {
conn, err := net.Dial("tcp", "192.168.4.233:4100")
if err != nil {
fmt.Sprint(os.Stderr, "Error: %s", err.Error())
return
}
var buf [16192]byte
/*
// for {
n, err := conn.Read(buf[0:])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
fmt.Println(string(buf[0:n]))
*/
n, err := conn.Write([]byte("admin\nadmin\n\ndate\n"))
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
/*
n, err = conn.Read(buf[0:])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
fmt.Println(string(buf[0:n]))
n, err = conn.Write([]byte("admin\n"))
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s\n", err.Error())
return
}
*/
n, err = conn.Read(buf[0:])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
fmt.Println((string(buf[0:n])))
fmt.Println(string(buf[0:n]))
n, err = conn.Write([]byte("date\n"))
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s\n", err.Error())
return
}
n, err = conn.Read(buf[0:])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
fmt.Println((string(buf[0:n])))
fmt.Println(string(buf[0:n]))
/*
buf[1] = 252
buf[4] = 252
buf[7] = 252
buf[10] = 252
fmt.Println((buf[0:n]))
n, err = conn.Write(buf[0:n])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s\n", err.Error())
return
}
n, err = conn.Read(buf[0:])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
fmt.Println(string(buf[0:n]))
fmt.Println((buf[0:n]))
*/
/*
buf[1] = 252
buf[4] = 251
buf[7] = 252
buf[10] = 254
buf[13] = 252
fmt.Println((buf[0:n]))
n, err = conn.Write(buf[0:n])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s\n", err.Error())
return
}
n, err = conn.Read(buf[0:])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
fmt.Println(string(buf[0:n]))
fmt.Println((buf[0:n]))
buf[1] = 252
buf[4] = 252
fmt.Println((buf[0:n]))
n, err = conn.Write(buf[0:n])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s\n", err.Error())
return
}
n, err = conn.Read(buf[0:])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
fmt.Println(string(buf[0:n]))
fmt.Println((buf[0:n]))
*/
/*
buf[0] = 255
buf[1] = 252
buf[2] = 1
buf[3] = 255
buf[4] = 253
buf[5] = 1
buf[6] = 255
buf[7] = 252
buf[8] = 1
buf[9] = 255
buf[10] = 253
buf[11] = 1
fmt.Println((buf[0:12]))
n, err = conn.Write(buf[0:12])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s\n", err.Error())
return
}
n, err = conn.Read(buf[0:])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
*/
/*
n, err = conn.Write([]byte("admin\n"))
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s\n", err.Error())
return
}
n, err = conn.Read(buf[0:])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
fmt.Println(string(buf[0:n]))
n, err = conn.Write([]byte("\n"))
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s\n", err.Error())
return
}
n, err = conn.Read(buf[0:])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
fmt.Println(string(buf[0:n]))
for {
n, err = conn.Read(buf[0:])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
fmt.Println(string(buf[0:n]))
if strings.HasSuffix(string(buf[0:n]), "> ") {
break
}
}
n, err = conn.Write([]byte("enable\n"))
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
n, err = conn.Read(buf[0:])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
fmt.Println(string(buf[0:n]))
n, err = conn.Write([]byte("terminal length 0\n"))
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
n, err = conn.Read(buf[0:])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
fmt.Println(string(buf[0:n]))
n, err = conn.Write([]byte("show port\n"))
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
for {
n, err = conn.Read(buf[0:])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
fmt.Println(string(buf[0:n]))
if strings.HasSuffix(string(buf[0:n]), "# ") {
break
}
}
n, err = conn.Write([]byte("show interface\n\n"))
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
for {
n, err = conn.Read(buf[0:])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
fmt.Println(string(buf[0:n]))
if strings.HasSuffix(string(buf[0:n]), "# ") {
break
}
}
n, err = conn.Write([]byte("show running-config\n"))
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
reader := bufio.NewReader(conn)
if reader == nil {
fmt.Fprintf(os.Stderr, "Create reader failed.")
}
for {
n, err := reader.Read(buf[0:])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
fmt.Println(string(buf[0:n]))
if strings.HasSuffix(string(buf[0:n]), "# ") {
break
}
}
*/
/*
for {
n, err = conn.Read(buf[0:])
if err != nil {
fmt.Fprintf(os.Stderr, "Error: %s", err.Error())
return
}
fmt.Println(string(buf[0:n]))
fmt.Println(n)
if strings.HasSuffix(string(buf[0:n]), "# ") {
break
}
}
*/
}

View File

@@ -0,0 +1,218 @@
package main
import (
"bufio"
"fmt"
"io"
"log"
"net"
"os"
"strings"
"time"
)
type TelnetClient struct {
IP string
Port string
IsAuthentication bool
UserName string
Password string
}
const (
//经过测试linux下延时需要大于100ms
TIME_DELAY_AFTER_WRITE = 500 //500ms
)
var g_WriteChan chan string
func main() {
g_WriteChan = make(chan string)
telnetClientObj := new(TelnetClient)
telnetClientObj.IP = "192.168.4.233"
telnetClientObj.Port = "4100"
telnetClientObj.IsAuthentication = true
telnetClientObj.UserName = "admin"
telnetClientObj.Password = "admin"
//fmt.Println(telnetClientObj.PortIsOpen(5))
go telnetClientObj.Telnet(20)
for {
line := readLine()
g_WriteChan <- string(line)
}
}
func readLine() string {
//fmt.Print("> ")
line, err := bufio.NewReader(os.Stdin).ReadString('\n')
if err != nil && err != io.EOF {
log.Fatal(err)
}
return strings.TrimSpace(line)
}
func (this *TelnetClient) PortIsOpen(timeout int) bool {
raddr := this.IP + ":" + this.Port
conn, err := net.DialTimeout("tcp", raddr, time.Duration(timeout)*time.Second)
if nil != err {
log.Println("pkg: model, func: PortIsOpen, method: net.DialTimeout, errInfo:", err)
return false
}
defer conn.Close()
return true
}
func (this *TelnetClient) Telnet(timeout int) (err error) {
raddr := this.IP + ":" + this.Port
conn, err := net.DialTimeout("tcp", raddr, time.Duration(timeout)*time.Second)
if nil != err {
log.Println("pkg: model, func: Telnet, method: net.DialTimeout, errInfo:", err)
return
}
defer conn.Close()
if false == this.telnetProtocolHandshake(conn) {
log.Println("pkg: model, func: Telnet, method: this.telnetProtocolHandshake, errInfo: telnet protocol handshake failed!!!")
return
}
go func() {
for {
data := make([]byte, 1024)
_, err := conn.Read(data)
if err != nil {
fmt.Println(err)
break
}
//strData := string(data)
fmt.Printf("%s", data)
}
}()
// conn.SetReadDeadline(time.Now().Add(time.Second * 30))
for {
select {
case cmd, _ := <-g_WriteChan:
_, err = conn.Write([]byte(cmd + "\n"))
if nil != err {
log.Println("pkg: model, func: Telnet, method: conn.Write, errInfo:", err)
return
}
break
default:
time.Sleep(100 * time.Millisecond)
continue
}
}
fmt.Println("Out telnet!!!!!!")
return
}
func (this *TelnetClient) telnetProtocolHandshake(conn net.Conn) bool {
var buf [4096]byte
n, err := conn.Read(buf[0:])
if nil != err {
log.Println("pkg: model, func: telnetProtocolHandshake, method: conn.Read, errInfo:", err)
return false
}
//fmt.Println(string(buf[0:n]))
//fmt.Println((buf[0:n]))
buf[1] = 252
buf[4] = 252
buf[7] = 252
buf[10] = 252
//fmt.Println((buf[0:n]))
n, err = conn.Write(buf[0:n])
if nil != err {
log.Println("pkg: model, func: telnetProtocolHandshake, method: conn.Write, errInfo:", err)
return false
}
n, err = conn.Read(buf[0:])
if nil != err {
log.Println("pkg: model, func: telnetProtocolHandshake, method: conn.Read, errInfo:", err)
return false
}
//fmt.Println(string(buf[0:n]))
//fmt.Println((buf[0:n]))
buf[1] = 252
buf[4] = 251
buf[7] = 252
buf[10] = 254
buf[13] = 252
fmt.Println((buf[0:n]))
n, err = conn.Write(buf[0:n])
if nil != err {
log.Println("pkg: model, func: telnetProtocolHandshake, method: conn.Write, errInfo:", err)
return false
}
n, err = conn.Read(buf[0:])
if nil != err {
log.Println("pkg: model, func: telnetProtocolHandshake, method: conn.Read, errInfo:", err)
return false
}
//fmt.Println(string(buf[0:n]))
//fmt.Println((buf[0:n]))
buf[1] = 252
buf[4] = 252
//fmt.Println((buf[0:n]))
n, err = conn.Write(buf[0:n])
if nil != err {
log.Println("pkg: model, func: telnetProtocolHandshake, method: conn.Write, errInfo:", err)
return false
}
n, err = conn.Read(buf[0:])
if nil != err {
log.Println("pkg: model, func: telnetProtocolHandshake, method: conn.Read, errInfo:", err)
return false
}
//fmt.Println(string(buf[0:n]))
//fmt.Println((buf[0:n]))
if false == this.IsAuthentication {
return true
}
n, err = conn.Write([]byte(this.UserName + "\n"))
if nil != err {
log.Println("pkg: model, func: telnetProtocolHandshake, method: conn.Write, errInfo:", err)
return false
}
time.Sleep(time.Millisecond * TIME_DELAY_AFTER_WRITE)
n, err = conn.Read(buf[0:])
if nil != err {
log.Println("pkg: model, func: telnetProtocolHandshake, method: conn.Read, errInfo:", err)
return false
}
//fmt.Println(string(buf[0:n]))
n, err = conn.Write([]byte(this.Password + "\n"))
if nil != err {
log.Println("pkg: model, func: telnetProtocolHandshake, method: conn.Write, errInfo:", err)
return false
}
n, err = conn.Read(buf[0:])
if nil != err {
log.Println("pkg: model, func: telnetProtocolHandshake, method: conn.Read, errInfo:", err)
return false
}
n, err = conn.Write([]byte("date" + "\n"))
if nil != err {
log.Println("pkg: model, func: telnetProtocolHandshake, method: conn.Write, errInfo:", err)
return false
}
time.Sleep(time.Millisecond * TIME_DELAY_AFTER_WRITE)
n, err = conn.Read(buf[0:])
if nil != err {
log.Println("pkg: model, func: telnetProtocolHandshake, method: conn.Read, errInfo:", err)
return false
}
fmt.Println(string(buf[0:n]))
return true
}

View File

@@ -0,0 +1,58 @@
// Code generated by xgen. DO NOT EDIT.
package schema
// FileHeader ...
type FileHeader struct {
TimeStamp string `xml:"TimeStamp"`
TimeZone string `xml:"TimeZone"`
VendorName string `xml:"VendorName"`
ElementType string `xml:"ElementType"`
CmVersion string `xml:"CmVersion"`
}
// N ...
type N struct {
IAttr int `xml:"i,attr"`
Value string `xml:",chardata"`
}
// FieldName ...
type FieldName struct {
N *N `xml:"N"`
}
// V ...
type V struct {
IAttr int `xml:"i,attr"`
Value string `xml:",chardata"`
}
// Object ...
type Object struct {
RmUIDAttr string `xml:"rmUID,attr"`
DnAttr string `xml:"Dn,attr,omitempty"`
UserLabelAttr string `xml:"UserLabel,attr,omitempty"`
PVFlagAttr string `xml:"PVFlag,attr"`
VMIDAttr string `xml:"VMID,attr,omitempty"`
VNFInstanceIDAttr string `xml:"VNFInstanceID,attr,omitempty"`
V *V `xml:"V"`
}
// FieldValue ...
type FieldValue struct {
Object *Object `xml:"Object"`
}
// Objects ...
type Objects struct {
ObjectType string `xml:"ObjectType"`
FieldName *FieldName `xml:"FieldName"`
FieldValue *FieldValue `xml:"FieldValue"`
}
// DataFile ...
type DataFile struct {
FileHeader *FileHeader `xml:"FileHeader"`
Objects []*Objects `xml:"Objects"`
}

View File

@@ -0,0 +1,65 @@
// Code generated by xgen. DO NOT EDIT.
package schema
// FileHeader ...
type FileHeader struct {
TimeStamp string `xml:"TimeStamp"`
TimeZone string `xml:"TimeZone"`
Period int `xml:"Period"`
VendorName string `xml:"VendorName"`
ElementType string `xml:"ElementType"`
PmVersion string `xml:"PmVersion"`
StartTime string `xml:"StartTime"`
}
// N ...
type N struct {
IAttr int `xml:"i,attr"`
Value string `xml:",chardata"`
}
// PmName ...
type PmName struct {
N *N `xml:"N"`
}
// V ...
type V struct {
IAttr int `xml:"i,attr"`
Value string `xml:",chardata"`
}
// CV ...
type CV struct {
IAttr int `xml:"i,attr"`
SN []string `xml:"SN"`
SV []string `xml:"SV"`
}
// Object ...
type Object struct {
RmUIDAttr string `xml:"rmUID,attr"`
DnAttr string `xml:"Dn,attr"`
UserLabelAttr string `xml:"UserLabel,attr"`
V []*V `xml:"V"`
CV []*CV `xml:"CV"`
}
// PmData ...
type PmData struct {
Object *Object `xml:"Object"`
}
// Measurements ...
type Measurements struct {
ObjectType string `xml:"ObjectType"`
PmName *PmName `xml:"PmName"`
PmData *PmData `xml:"PmData"`
}
// PmFile ...
type PmFile struct {
FileHeader *FileHeader `xml:"FileHeader"`
Measurements []*Measurements `xml:"Measurements"`
}

128
tools/xgen/xgen.go Normal file
View File

@@ -0,0 +1,128 @@
// Copyright 2020 - 2022 The xgen Authors. All rights reserved. Use of this
// source code is governed by a BSD-style license that can be found in the
// LICENSE file.
//
// xgen is a tool to automatically compiles XML schema files into the
// multi-language type or class declarations code.
//
// Usage:
//
// $ xgen [<flag> ...] <XSD file or directory> ...
// -i <path> Input file path or directory for the XML schema definition
// -o <path> Output file path or directory for the generated code
// -p Specify the package name
// -l Specify the language of generated code (Go/C/Java/Rust/TypeScript)
// -h Output this help and exit
// -v Output version and exit
//
// If the path specified by the -i flag is a directory, all files in the
// directory will be processed as XML schema definition.
//
// The default package name and output directory are "schema" and "xgen_out".
//
// Currently support language is Go.
package main
import (
"flag"
"fmt"
"os"
"github.com/xuri/xgen"
)
// Config holds user-defined overrides and filters that are used when
// generating source code from an XSD document.
type Config struct {
I string
O string
Pkg string
Lang string
Version string
}
// Cfg are the default config for xgen. The default package name and output
// directory are "schema" and "xgen_out".
var Cfg = Config{
Pkg: "schema",
Version: "0.1.0",
}
// SupportLang defines supported language types.
var SupportLang = map[string]bool{
"Go": true,
"C": true,
"Java": true,
"Rust": true,
"TypeScript": true,
}
// parseFlags parse flags of program.
func parseFlags() *Config {
iPtr := flag.String("i", "", "Input file path or directory for the XML schema definition")
oPtr := flag.String("o", "xgen_out", "Output file path or directory for the generated code")
pkgPtr := flag.String("p", "", "Specify the package name")
langPtr := flag.String("l", "", "Specify the language of generated code")
verPtr := flag.Bool("v", false, "Show version and exit")
helpPtr := flag.Bool("h", false, "Show this help and exit")
flag.Parse()
if *helpPtr {
fmt.Printf("xgen version: %s\r\nCopyright (c) 2020 - 2022 Ri Xu https://xuri.me All rights reserved.\r\n\r\nUsage:\r\n$ xgen [<flag> ...] <XSD file or directory> ...\n -i <path>\tInput file path or directory for the XML schema definition\r\n -o <path>\tOutput file path or directory for the generated code\r\n -p \tSpecify the package name\r\n -l \tSpecify the language of generated code (Go/C/Java/Rust/TypeScript)\r\n -h \tOutput this help and exit\r\n -v \tOutput version and exit\r\n", Cfg.Version)
os.Exit(0)
}
if *verPtr {
fmt.Printf("xgen version: %s\r\n", Cfg.Version)
os.Exit(0)
}
if *iPtr == "" {
fmt.Println("must specify input file path or directory for the XML schema definition")
os.Exit(1)
}
Cfg.I = *iPtr
if *langPtr == "" {
fmt.Println("must specify the language of generated code (Go/C/Java/Rust/TypeScript)")
os.Exit(1)
}
Cfg.Lang = *langPtr
if *oPtr != "" {
Cfg.O = *oPtr
}
if ok := SupportLang[Cfg.Lang]; !ok {
fmt.Println("unsupport language", Cfg.Lang)
os.Exit(1)
}
if *pkgPtr != "" {
Cfg.Pkg = *pkgPtr
}
return &Cfg
}
func main() {
cfg := parseFlags()
files, err := xgen.GetFileList(cfg.I)
if err != nil {
fmt.Println(err)
os.Exit(1)
}
for _, file := range files {
if err = xgen.NewParser(&xgen.Options{
FilePath: file,
InputDir: cfg.I,
OutputDir: cfg.O,
Lang: cfg.Lang,
Package: cfg.Pkg,
IncludeMap: make(map[string]bool),
LocalNameNSMap: make(map[string]string),
NSSchemaLocationMap: make(map[string]string),
ParseFileList: make(map[string]bool),
ParseFileMap: make(map[string][]interface{}),
ProtoTree: make([]interface{}, 0),
RemoteSchema: make(map[string][]byte),
}).Parse(); err != nil {
fmt.Printf("process error on %s: %s\r\n", file, err.Error())
os.Exit(1)
}
}
fmt.Println("done")
}

View File

@@ -0,0 +1,48 @@
<?xml version="1.0" encoding="UTF-8"?>
<DataFile xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="file:///./cm-schema.xsd">
<FileHeader>
<TimeStamp>2023-05-17 10:16:17</TimeStamp>
<TimeZone>UTC+8</TimeZone>
<VendorName>Ruijie Network</VendorName>
<ElementType>SMF</ElementType>
<CmVersion>16.1.1</CmVersion>
</FileHeader>
<Objects>
<ObjectType>ManagedElement</ObjectType>
<FieldName>
<N i="1">Id</N>
<N i="2">Id</N>
<N i="3">Id</N>
<N i="4">Id</N>
<N i="5">Id</N>
<N i="6">Id</N>
<N i="7">Id</N>
<N i="8">Id</N>
<N i="9">Id</N>
</FieldName>
<FieldValue>
<Object rmUID="1000HXSMF001" Dn="DC=www.ruijie.com.cn,SubNetwork=10001,SubNetwork=114214,ManagedElement=325" UserLabel="SMF_BJ_JC001" PVFlag="VNF" VMID="kylin10.0-001-SMF" VNFInstanceID="2bdd55b4-9018-41f4-af35-28b6828788">
<V i="1">SMF</V>
<V i="2">SMF</V>
<V i="3">SMF</V>
<V i="4">SMF</V>
<V i="5">SMF</V>
<V i="6">SMF</V>
<V i="7">SMF</V>
<V i="8">SMF</V>
<V i="9">SMF</V>
</Object>
<Object rmUID="1000HXSMF002" Dn="DC=www.ruijie.com.cn,SubNetwork=10001,SubNetwork=114214,ManagedElement=325" UserLabel="SMF_BJ_JC001" PVFlag="VNF" VMID="kylin10.0-002-SMF" VNFInstanceID="2bdd55b4-9018-41f4-af35-28b6828788">
<V i="1">SMF</V>
<V i="2">SMF</V>
<V i="3">SMF</V>
<V i="4">SMF</V>
<V i="5">SMF</V>
<V i="6">SMF</V>
<V i="7">SMF</V>
<V i="8">SMF</V>
<V i="9">SMF</V>
</Object>
</FieldValue>
</Objects>
</DataFile>

48
tools/xsdgen/cm-demo.xml Normal file
View File

@@ -0,0 +1,48 @@
<?xml version="1.0" encoding="UTF-8"?>
<DataFile xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="file:///./cm-schema.xsd">
<FileHeader>
<TimeStamp>2023-05-17 09:57:17</TimeStamp>
<TimeZone>UTC+8</TimeZone>
<VendorName>Ruijie Network</VendorName>
<ElementType>SMF</ElementType>
<CmVersion>16.1.1</CmVersion>
</FileHeader>
<Objects>
<ObjectType>ManagedElement</ObjectType>
<FieldName>
<N i="1">Id</N>
<N i="2">Id</N>
<N i="3">Id</N>
<N i="4">Id</N>
<N i="5">Id</N>
<N i="6">Id</N>
<N i="7">Id</N>
<N i="8">Id</N>
<N i="9">Id</N>
</FieldName>
<FieldValue>
<Object rmUID="1000HXSMF001" Dn="DC=www.ruijie.com.cn,SubNetwork=10001,SubNetwork=114214,ManagedElement=325" UserLabel="SMF_BJ_JC001" PVFlag="VNF" VMID="kylin10.0-001-SMF" VNFInstanceID="2bdd55b4-9018-41f4-af35-28b6828788">
<V i="1">SMF</V>
<V i="2">SMF</V>
<V i="3">SMF</V>
<V i="4">SMF</V>
<V i="5">SMF</V>
<V i="6">SMF</V>
<V i="7">SMF</V>
<V i="8">SMF</V>
<V i="9">SMF</V>
</Object>
<Object rmUID="1000HXSMF002" Dn="DC=www.ruijie.com.cn,SubNetwork=10001,SubNetwork=114214,ManagedElement=325" UserLabel="SMF_BJ_JC001" PVFlag="VNF" VMID="kylin10.0-002-SMF" VNFInstanceID="2bdd55b4-9018-41f4-af35-28b6828788">
<V i="1">SMF</V>
<V i="2">SMF</V>
<V i="3">SMF</V>
<V i="4">SMF</V>
<V i="5">SMF</V>
<V i="6">SMF</V>
<V i="7">SMF</V>
<V i="8">SMF</V>
<V i="9">SMF</V>
</Object>
</FieldValue>
</Objects>
</DataFile>

66
tools/xsdgen/cm-schema.go Normal file
View File

@@ -0,0 +1,66 @@
// Code generated by xgen. DO NOT EDIT.
package main
// FileHeader ...
type FileHeader struct {
TimeStamp string `xml:"TimeStamp"`
TimeZone string `xml:"TimeZone"`
VendorName string `xml:"VendorName"`
ElementType string `xml:"ElementType"`
CmVersion string `xml:"CmVersion"`
}
// N ...
type N struct {
IAttr int `xml:"i,attr"`
Value string `xml:",chardata"`
}
// FieldName ...
type FieldName struct {
N []N `xml:"N"`
}
// V ...
type V struct {
IAttr int `xml:"i,attr"`
Value string `xml:",chardata"`
}
// Object ...
type Object struct {
RmUIDAttr string `xml:"rmUID,attr"`
DnAttr string `xml:"Dn,attr,omitempty"`
UserLabelAttr string `xml:"UserLabel,attr,omitempty"`
PVFlagAttr string `xml:"PVFlag,attr"`
VMIDAttr string `xml:"VMID,attr,omitempty"`
VNFInstanceIDAttr string `xml:"VNFInstanceID,attr,omitempty"`
V []V `xml:"V"`
}
// FieldValue ...
type FieldValue struct {
Object []Object `xml:"Object"`
}
// Objects ...
type Objects struct {
ObjectType string `xml:"ObjectType"`
FieldName FieldName `xml:"FieldName"`
FieldValue FieldValue `xml:"FieldValue"`
}
// DataFile ...
type DataFile struct {
FileHeader FileHeader `xml:"FileHeader"`
Objects Objects `xml:"Objects"`
XsiAttr string `xml:"xmlns:xsi,attr"`
XsiLoc string `xml:"xsi:noNamespaceSchemaLocation,attr"`
}
// NRM xml file
type NRMXmlFile struct {
Header string `xml:"Header"`
DataFile DataFile `xml:"xmlns:xsi"`
}

View File

@@ -0,0 +1,76 @@
<?xml version="1.0" encoding="UTF-8"?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" elementFormDefault="qualified" attributeFormDefault="unqualified">
<xs:element name="DataFile">
<xs:complexType>
<xs:sequence>
<xs:element name="FileHeader">
<xs:complexType>
<xs:sequence>
<xs:element name="TimeStamp" type="xs:dateTime"/>
<xs:element name="TimeZone" type="xs:string"/>
<xs:element name="VendorName" type="xs:string" minOccurs="0"/>
<xs:element name="ElementType" type="xs:string" minOccurs="0"/>
<xs:element name="CmVersion" type="xs:string" minOccurs="0"/>
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:element name="Objects" maxOccurs="unbounded">
<xs:complexType>
<xs:sequence>
<xs:element name="ObjectType" type="xs:string"/>
<!--该字段必选-->
<xs:element name="FieldName">
<xs:complexType>
<xs:sequence minOccurs="0" maxOccurs="unbounded">
<xs:element name="N">
<xs:complexType>
<xs:simpleContent>
<xs:extension base="xs:string">
<xs:attribute name="i" type="xs:integer" use="required"/>
</xs:extension>
</xs:simpleContent>
</xs:complexType>
</xs:element>
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:element name="FieldValue">
<xs:complexType>
<xs:sequence minOccurs="0" maxOccurs="unbounded">
<xs:element name="Object">
<xs:complexType>
<xs:sequence minOccurs="0" maxOccurs="unbounded">
<xs:element name="V">
<xs:complexType>
<xs:simpleContent>
<xs:extension base="xs:string">
<xs:attribute name="i" type="xs:integer" use="required"/>
</xs:extension>
</xs:simpleContent>
</xs:complexType>
</xs:element>
</xs:sequence>
<xs:attribute name="rmUID" type="xs:string" use="required"/>
<xs:attribute name="Dn" type="xs:string"/>
<!-- //无线、核心网专业该字段必选传输、IP专业、业务系统无该字段-->
<xs:attribute name="UserLabel" type="xs:string"/>
<!-- //无线、核心网专业该字段必选传输、IP专业、业务系统无该字段-->
<xs:attribute name="PVFlag" type="xs:string" use="required"/>
<!-- //必须-->
<xs:attribute name="VMID" type="xs:string"/>
<!-- //VNF网络或VNF和PNF混合组网虚拟网元必选物理网元无该字段-->
<xs:attribute name="VNFInstanceID" type="xs:string"/>
<!-- //VNF网络或VNF和PNF混合组网虚拟网元必选物理网元无该字段-->
</xs:complexType>
</xs:element>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:schema>

66
tools/xsdgen/genxml.go Normal file
View File

@@ -0,0 +1,66 @@
package main
import (
"encoding/xml"
"fmt"
"io/ioutil"
"strconv"
"time"
)
const (
// Header is a generic XML header suitable for use with the output of Marshal.
// This is not automatically added to any output of this package,
// it is provided as a convenience.
Header = `<?xml version="1.0" encoding="UTF-8"?>` + "\n"
)
func main() {
t := time.Now()
timestamp := t.Format("2006-01-02 15:04:05")
timefile := t.Format("20060102150405")
_, offset := t.Zone()
var tzOffset string
if offset >= 0 {
tzOffset = "UTC+" + strconv.Itoa(offset/3600)
} else {
tzOffset = "UTC" + strconv.Itoa(offset/3600)
}
nrmFile := new(DataFile)
nrmFile.FileHeader = FileHeader{
TimeStamp: timestamp,
TimeZone: tzOffset,
VendorName: "Ruijie Network",
ElementType: "SMF",
CmVersion: "16.1.1",
}
nrmFile.XsiAttr = "http://www.w3.org/2001/XMLSchema-instance"
nrmFile.XsiLoc = "file:///usr/loal/omc/etc/schema/cm-schema.xsd"
nrmFile.Objects.ObjectType = "ManagedElement"
for i := 1; i < 10; i++ {
nrmFile.Objects.FieldName.N = append(nrmFile.Objects.FieldName.N, N{IAttr: i, Value: "Id"})
}
object := Object{RmUIDAttr: "1000HXSMF001",
DnAttr: "DC=www.ruijie.com.cn,SubNetwork=10001,SubNetwork=114214,ManagedElement=325",
UserLabelAttr: "SMF_BJ_JC001", PVFlagAttr: "VNF", VMIDAttr: "kylin10.0-001-SMF", VNFInstanceIDAttr: "2bdd55b4-9018-41f4-af35-28b6828788"}
for i := 1; i < 10; i++ {
object.V = append(object.V, V{IAttr: i, Value: "SMF"})
}
nrmFile.Objects.FieldValue.Object = append(nrmFile.Objects.FieldValue.Object, object)
object = Object{RmUIDAttr: "1000HXSMF002",
DnAttr: "DC=www.ruijie.com.cn,SubNetwork=10001,SubNetwork=114214,ManagedElement=325",
UserLabelAttr: "SMF_BJ_JC001", PVFlagAttr: "VNF", VMIDAttr: "kylin10.0-002-SMF", VNFInstanceIDAttr: "2bdd55b4-9018-41f4-af35-28b6828788"}
for i := 1; i < 10; i++ {
object.V = append(object.V, V{IAttr: i, Value: "SMF"})
}
nrmFile.Objects.FieldValue.Object = append(nrmFile.Objects.FieldValue.Object, object)
x, _ := xml.MarshalIndent(nrmFile, "", " ")
x = append([]byte(xml.Header), x...)
cmfile := fmt.Sprintf("./CM-HX-V%s-%s.xml", "16.1.1", timefile)
ioutil.WriteFile(cmfile, x, 0664)
}

View File

@@ -0,0 +1,80 @@
<?xml version="1.0" encoding="UTF-8"?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
elementFormDefault="qualified" attributeFormDefault="unqualified">
<xs:element name="PmFile">
<xs:complexType>
<xs:sequence>
<xs:element name="FileHeader">
<xs:complexType>
<xs:sequence>
<xs:element name="TimeStamp" type="xs:dateTime" />
<xs:element name="TimeZone" type="xs:string" />
<xs:element name="Period" type="xs:integer" />
<xs:element name="VendorName" type="xs:string" />
<xs:element name="ElementType" type="xs:string" />
<xs:element name="PmVersion" type="xs:string" />
<xs:element name="StartTime" type="xs:dateTime" />
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:element name="Measurements" minOccurs="0" maxOccurs="unbounded">
<xs:complexType>
<xs:sequence>
<xs:element name="ObjectType" type="xs:string" />
<xs:element name="PmName">
<xs:complexType>
<xs:sequence minOccurs="0" maxOccurs="unbounded">
<xs:element name="N">
<xs:complexType>
<xs:simpleContent>
<xs:extension base="xs:string">
<xs:attribute name="i" type="xs:integer" use="required" />
</xs:extension>
</xs:simpleContent>
</xs:complexType>
</xs:element>
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:element name="PmData">
<xs:complexType>
<xs:sequence minOccurs="0" maxOccurs="unbounded">
<xs:element name="Object">
<xs:complexType>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="V">
<xs:complexType>
<xs:simpleContent>
<xs:extension base="xs:string">
<xs:attribute name="i" type="xs:integer" use="required" />
</xs:extension>
</xs:simpleContent>
</xs:complexType>
</xs:element>
<xs:element name="CV">
<xs:complexType>
<xs:sequence minOccurs="0" maxOccurs="unbounded">
<xs:element name="SN" type="xs:string" />
<xs:element name="SV" type="xs:string" />
</xs:sequence>
<xs:attribute name="i" type="xs:integer"
use="required" />
</xs:complexType>
</xs:element>
</xs:choice>
<xs:attribute name="rmUID" type="xs:string" use="required" />
<xs:attribute name="Dn" type="xs:string" use="required" />
<xs:attribute name="UserLabel" type="xs:string" use="required" />
</xs:complexType>
</xs:element>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:schema>

3
tools/xsdgen/xsdgen.go Normal file
View File

@@ -0,0 +1,3 @@
// Code generated by xgen. DO NOT EDIT.
package schema