在上一篇文章,我们实现了SSH 私钥的“内容直接输入与文件上传双重输入方式”,那么我们在 console 上主动生成一个 SSH 私钥(非本地上传),当请求成功时,如何本地能同时得到生成的私钥文件呢?

生成秘钥1


实现

API 响应:

{
    "code": 0,
    "message": "ok",
    "data": {
        "name": "test",
        "key_material": "-----BEGIN RSA PRIVATE KEY-----\nMIIEogIBAAKCAQEA74RDDw+mCR4Z4N6S9VYiiKc487lhcRMYWyUi/rjlS5eBzEqh\nf61dzLs+lmBFfxFttq3lc0zUaseQWh+Ue6bcp2qEQUYvX+iXq1LV8Evhzn+hTnFQ\n/blpl8HUi+ykp0czacyBOeKmztJfrJgE2DHtiSIAXBHiBGF2R4/mR4DQvgNA2BtC\npzQIVt8/CghoVT1UpjNA6SxtxsKMCpn/R9bBh51Tfpu5KUgyJHUeEZYUdCAsAVFB\naruqljiA3FTzpGUbhDIPAFQJGCfpIs4oviHloPkbVzAJGSMUC9qKkuDH1GG0fQdC\nTPfcPooHzngOH60dgUGlmKLqNrNT8A03ntHehwIDAQABAoIBABUHbcPSwecnB2qg\n4BI+P8XzuKJdclq1LHxEJHBs12Ttpm3DV66YEBY7kmEtjqx7YUCav/yBkFzXrKrc\n/vJkUhc42OfKO7qV90sJeNMiNm8k8YqrlErSjpzOXdTzL/mn3LG7TNVCOxcJjXDf\n3/0DVTGnFJUA1PFBhVr/HV7Fxo4IG5gMq+hj0YtYlp4zRp/kDF22OGJaqudvVFI1\nBYtOsWDz7BaXxuNMTw0SjphYW+7+CWyXFh8799p1uptO05CL0Os//2k7WNLrHcNR\nh0YMXFJLwFURxxmPEsT9uKKFSjsyvEQjxJlV3x85GLPSc+pRedDYc9F42bN2c++E\ntHwzZoECgYEA8RiKBj7gqUNhrZerhh8bAtMGakNbe1OIr826nB2DDtgVAWsvO4fQ\n4kNGidqbPfNIS1SEtuaJAEa2DiJu2z7w8bl89YJq20iABFysDfdMBRsQuQN9O/Lx\nrQtVY5UKdTFq/xVKm8tJeMNPCQKXgRlXIvIDmUeWRQprvhOs/7iZ1OcCgYEA/lK7\nJe/bVpIxwegXFducH70rrWx3G9JtCRrpL7gnLTqkTbFfQW5tJxCJnzVV8VDLZtTR\nZ0Py/rwstiDJZ4diH7CBjMHb6xArjlp/PfF5Uds8433e7b73dfK0xis4nS5xnbJ6\n3DPNJ+dsHc9ikIy5odSi1a9t2ZG2N10ai6381WECgYB0scT02vBQ3R1lMXlDFME1\nL8D2JB4eZkNNnI1LTPmHcM1R/3hAHy/apGd7CAWGCcAfPgxynskHCjLKSp5Pnnpu\n9bHm/zYLZ18XPWfF5sGz4vLIKkkugBu7/zVYWuZR7RZ12u9e0xl/y0DxAoEkaoiD\nkJJvWXgBeNbHjKx6pfZHVwKBgDnONBt7WS9kK0sXpaeiMupD5RmV/bylJ4NaSoY+\nJSlymsXN+wi0QLsQVzeIt/ARnSnSVYZTO3gK7V64NQ8DBpqNU+Taa1ISatQAXcuG\nhzzDyCMtCO6g6T413EDusf+H/usJFkPWwlq/jyN3b7/LPKY73ocTSLSbGf+bed0l\nvsIBAoGAHEWmPgrXMwj5aN2OJwSY3JHt7rkqihhbIE3s7sR4g3H6xBlkdiKkacg4\nFgXmITIiEQUwM0eIuzrLfcxtM0aTUjClg+GE1+T4qw1efnhNYlhsJVRc3pMzjta5\npxOHfLyTvv0lcv/1AqAhKzu7r64f5lyUMFNcF33LWifZBhcI+5s=\n-----END RSA PRIVATE KEY-----\n"
    }
}


实现方案:

  1. 用户点击生成密钥对按钮
  2. amis 请求后台,拿到密钥对
  3. amis 自动弹出下载/保存对话或直接下载(JS动作,生成blob并自动触发下载) ***
  4. reload 当前界面

生成秘钥2

          {
            "type": "container",
            "align": "right",
            "behavior": [
              "FuzzyQuery"
            ],
            "body": [
              {
                "type": "button",
                "label": "创建秘钥对",
                "onEvent": {
                  "click": {
                    "actions": [
                      {
                        "ignoreError": false,
                        "actionType": "dialog",
                        "dialog": {
                          "type": "dialog",
                          "title": "创建密钥对",
                          "body": [
                            {
                              "type": "input-text",
                              "label": "name",
                              "name": "name",
                              "id": "u:d3997761dafc"
                            },
                            {
                              "type": "input-text",
                              "label": "描述",
                              "name": "description",
                              "id": "u:b5d890050cb4"
                            }
                          ],
                          "id": "u:4abcbfd87011",
                          "actions": [
                            {
                              "type": "button",
                              "actionType": "cancel",
                              "label": "取消",
                              "id": "u:51a7d5debfc8"
                            },
                            {
                              "type": "button",
                              "actionType": "confirm",
                              "label": "确定",
                              "primary": true,
                              "id": "u:4fefcac5d5a5",
                              "onEvent": {
                                "click": {
                                  "weight": 0,
                                  "actions": [
                                    {
                                      "ignoreError": false,
                                      "outputVar": "responseResult",
                                      "actionType": "ajax",
                                      "options": {},
                                      "api": {
                                        "url": "/admin/cloud/v1/rsa_create",
                                        "method": "post",
                                        "requestAdaptor": "",
                                        "adaptor": "",
                                        "messages": {},
                                        "dataType": "json",
                                        "data": {
                                          "name": "${name}",
                                          "description": "${description}"
                                        }
                                      }
                                    },
                                    {
                                      "ignoreError": false,
                                      "actionType": "custom",
                                      "script": "const data = event.data.responseResult;\nconst content = data.key_material;\nconst name = (data && data.name ? data.name : 'private_key') + '.pem';\nconst blob = new Blob([content], { type: 'application/octet-stream' });\nconst url = URL.createObjectURL(blob);\nconst a = document.createElement('a');\na.href = url;\na.download = name;\ndocument.body.appendChild(a);\na.click();\ndocument.body.removeChild(a);\nURL.revokeObjectURL(url);",
                                      "args": {}
                                    },
                                    {
                                      "ignoreError": true,
                                      "actionType": "reload",
                                      "componentId": "u:86eeb4c2dc51"
                                    }
                                  ]
                                }
                              }
                            }
                          ],
                          "showCloseButton": true,
                          "closeOnOutside": false,
                          "closeOnEsc": false,
                          "showErrorMsg": true,
                          "showLoading": true,
                          "draggable": false,
                          "actionType": "dialog"
                        }
                      }
                    ]
                  }
                },
                "id": "u:4412592e3b6c"
              }
            ],
            "wrapperBody": false,
            "style": {
              "flexGrow": 1,
              "flex": "1 1 auto",
              "position": "static",
              "display": "flex",
              "flexBasis": "auto",
              "flexDirection": "row",
              "flexWrap": "nowrap",
              "alignItems": "stretch",
              "justifyContent": "flex-end"
            },
            "id": "u:60494c7d425d"
          }


实现细节

自定义JS代码将后端返回的密钥内容,生成Blob文件,并自动下载

const data = event.data.responseResult;
const content = data.key_material;
const name = (data && data.name ? data.name : 'private_key') + '.pem';
const blob = new Blob([content], { type: 'application/octet-stream' });
const url = URL.createObjectURL(blob);
const a = document.createElement('a');
a.href = url;
a.download = name;
document.body.appendChild(a);
a.click();
document.body.removeChild(a);
URL.revokeObjectURL(url);

在 AMis 的「事件联动」链条中,后面的 custom 脚本可以拿到前面 ajax 的返回结果,即 event.data.responseResult

Last modified: May 26, 2025

Comments

Write a Reply or Comment

Your email address will not be published.