Skip to main content
Glama

yeepay_yop_gen_key_pair

Generate asymmetric encryption key pairs (public and private keys) for YOP platform integration, supporting RSA and SM2 algorithms with configurable formats and storage options.

Instructions

根据密钥算法生成非对称加密的密钥对(公钥和私钥),并保存到本地路径

参数: algorithm: 密钥算法,可选值为 "RSA" 或 "SM2",默认为 "RSA" key_format: 密钥格式,可选值为 "pkcs8"或"pkcs1",默认为 "pkcs8" storage_type: 密钥存储类型,"file"或"string",默认为 "file"

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
algorithmNoRSA
key_formatNopkcs8
storage_typeNofile

Output Schema

TableJSON Schema
NameRequiredDescriptionDefault
resultYes

Implementation Reference

  • The MCP tool handler function for 'yeepay_yop_gen_key_pair', decorated with @mcp.tool(). It calls the gen_key_pair helper from tools.cert_utils.
    @mcp.tool()
    def yeepay_yop_gen_key_pair(
        algorithm: str = "RSA", key_format: str = "pkcs8", storage_type: str = "file"
    ) -> Dict[str, Any]:
        """
        根据密钥算法生成非对称加密的密钥对(公钥和私钥),并保存到本地路径
    
        参数:
            algorithm: 密钥算法,可选值为 "RSA" 或 "SM2",默认为 "RSA"
            key_format: 密钥格式,可选值为 "pkcs8"或"pkcs1",默认为 "pkcs8"
            storage_type: 密钥存储类型,"file"或"string",默认为 "file"
        """
        return gen_key_pair(
            algorithm=algorithm, format=key_format, storage_type=storage_type
        )
  • The primary helper function implementing the key pair generation for both RSA and SM2 algorithms using the cryptography library. Handles formatting, Base64 encoding, and optional file storage.
    def gen_key_pair(  # pylint: disable=too-many-arguments,too-many-positional-arguments,redefined-builtin
        algorithm: str = "RSA", format: str = "pkcs8", storage_type: str = "file"
    ) -> Dict[str, Any]:
        try:
            private_key_str = None
            public_key_str = None
    
            if algorithm.upper() == "RSA":
                # 生成RSA密钥对,使用2048位密钥长度
                private_key = rsa.generate_private_key(
                    public_exponent=65537, key_size=2048, backend=default_backend()
                )
                public_key = private_key.public_key()
    
                # 处理私钥格式
                if format.lower() == "pkcs8":
                    private_key_bytes = private_key.private_bytes(
                        encoding=serialization.Encoding.PEM,
                        format=serialization.PrivateFormat.PKCS8,
                        encryption_algorithm=serialization.NoEncryption(),
                    )
                else:  # pkcs1
                    private_key_bytes = private_key.private_bytes(
                        encoding=serialization.Encoding.PEM,
                        format=serialization.PrivateFormat.TraditionalOpenSSL,
                        encryption_algorithm=serialization.NoEncryption(),
                    )
    
                # 处理公钥格式
                public_key_bytes = public_key.public_bytes(
                    encoding=serialization.Encoding.PEM,
                    format=serialization.PublicFormat.SubjectPublicKeyInfo,
                )
    
                # 去除PEM头尾并转为Base64字符串
                private_key_str = private_key_bytes.decode("utf-8")
                private_key_str = private_key_str.replace(
                    "-----BEGIN PRIVATE KEY-----\n", ""
                )
                private_key_str = private_key_str.replace("-----END PRIVATE KEY-----\n", "")
                private_key_str = private_key_str.replace(
                    "-----BEGIN RSA PRIVATE KEY-----\n", ""
                )
                private_key_str = private_key_str.replace(
                    "-----END RSA PRIVATE KEY-----\n", ""
                )
                private_key_str = private_key_str.replace("\n", "")
    
                public_key_str = public_key_bytes.decode("utf-8")
                public_key_str = public_key_str.replace("-----BEGIN PUBLIC KEY-----\n", "")
                public_key_str = public_key_str.replace("-----END PUBLIC KEY-----\n", "")
                public_key_str = public_key_str.replace("\n", "")
    
            elif algorithm.upper() == "SM2":
                if format.lower() != "pkcs8":
                    return {
                        "message": "SM2密钥只支持生成PKCS8格式",
                        "privateKey": None,
                        "publicKey": None,
                        "privateCert": None,
                        "publicCert": None,
                    }
                private_key_str, public_key_str = CertUtils.generate_sm2_key_pair()
            else:
                return {
                    "message": f"不支持的密钥算法: {algorithm}",
                    "privateKey": None,
                    "publicKey": None,
                    "privateCert": None,
                    "publicCert": None,
                }
    
            # 如果需要保存到文件
            private_cert_path = None
            public_cert_path = None
    
            if storage_type.lower() == "file":
                # 创建目录
                key_dir = "./keys/"
                os.makedirs(key_dir, exist_ok=True)
    
                algorithm_name = "RSA2048" if algorithm.upper() == "RSA" else "SM2"
    
                # 保存私钥
                private_cert_path = os.path.join(key_dir, f"应用私钥{algorithm_name}.txt")
                with open(private_cert_path, "w", encoding="utf-8") as f:
                    f.write(private_key_str)
    
                # 保存公钥
                public_cert_path = os.path.join(key_dir, f"应用公钥{algorithm_name}.txt")
                with open(public_cert_path, "w", encoding="utf-8") as f:
                    f.write(public_key_str)
    
            return {
                "message": "密钥对生成成功"
                + (",并已保存到文件" if storage_type.lower() == "file" else ""),
                "privateKey": private_key_str,
                "publicKey": public_key_str,
                "privateCert": private_cert_path,
                "publicCert": public_cert_path,
            }
    
        except Exception as e:
            return {
                "message": f"生成密钥对失败: {str(e)}",
                "privateKey": None,
                "publicKey": None,
                "privateCert": None,
                "publicCert": None,
            }
  • Supporting method for generating SM2 key pairs using elliptic curve cryptography (SECP256K1 curve).
    def generate_sm2_key_pair() -> List[str]:
        # 使用SM2曲线创建私钥
        private_key = ec.generate_private_key(ec.SECP256K1(), default_backend())
    
        # 从私钥获取公钥
        public_key = private_key.public_key()
    
        # 导出私钥,DER格式
        private_key_der = private_key.private_bytes(
            encoding=serialization.Encoding.DER,
            format=serialization.PrivateFormat.PKCS8,
            encryption_algorithm=serialization.NoEncryption(),
        )
    
        # 导出公钥,DER格式
        public_key_der = public_key.public_bytes(
            encoding=serialization.Encoding.DER,
            format=serialization.PublicFormat.SubjectPublicKeyInfo,
        )
    
        # Base64编码
        private_key_b64 = base64.b64encode(private_key_der).decode("utf-8")
        public_key_b64 = base64.b64encode(public_key_der).decode("utf-8")
    
        return [private_key_b64, public_key_b64]
Behavior2/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

No annotations are provided, so the description carries the full burden. It mentions saving to a local path but doesn't disclose critical behaviors: where files are saved (default path?), file naming conventions, whether existing files are overwritten, security implications of storing private keys, or error handling. For a tool generating sensitive cryptographic keys, this lack of detail is a significant gap.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness3/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is appropriately sized (two sentences) and front-loaded with the purpose. However, the parameter details are listed in a separate section without integration into the flow, making it slightly less structured. Every sentence adds value, but it could be more cohesive.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness3/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given 3 parameters with 0% schema coverage and no annotations, the description compensates well for parameters but lacks behavioral context. An output schema exists, so return values needn't be explained. However, for a tool handling cryptographic keys, more details on security, file handling, and error cases would improve completeness.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 0%, so the description must compensate. It adds meaningful semantics for all 3 parameters: 'algorithm' (RSA or SM2), 'key_format' (pkcs8 or pkcs1), and 'storage_type' (file or string), including default values. This goes beyond the schema's basic titles, providing essential context for parameter selection. However, it doesn't explain the implications of choices (e.g., SM2 vs. RSA security).

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the tool's purpose: '生成非对称加密的密钥对(公钥和私钥),并保存到本地路径' (generate asymmetric encryption key pairs and save to local path). It specifies the verb (generate), resource (key pairs), and outcome (save locally). However, it doesn't explicitly differentiate from sibling tools like 'yeepay_yop_download_cert' or 'yeepay_yop_parse_certificates', which also handle cryptographic operations.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description provides no guidance on when to use this tool versus alternatives. It doesn't mention prerequisites (e.g., needing local file permissions), use cases (e.g., for secure payments), or comparisons to sibling tools (e.g., 'yeepay_yop_download_cert' for downloading vs. generating keys). Usage is implied only by the tool's name and description.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

Install Server

Other Tools

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/yop-platform/yop-mcp'

If you have feedback or need assistance with the MCP directory API, please join our Discord server