泛化调用

更新时间:

阿里云V1.0 SDK支持以一种通用的方式调用OpenAPI,此方式被称为泛化调用。本文将为您详细介绍如何使用泛化调用访问OpenAPI。

特点

  • 轻量:只需Core包即可发起调用,无需下载安装各产品的SDK。

  • 兼容性高:当云产品尚未提供相应的SDK,或当新API发布但SDK未能及时更新时,可以使用泛化调用。这样,无需等待SDK的更新,即可及时调用最新发布的API接口。

更多介绍,请参见泛化调用与特化调用

使用说明

在使用泛化调用之前,必须手动获取并配置OpenAPI的版本号、请求路径、参数类型等元数据信息。可以通过查看OpenAPI元数据来获取有关OpenAPIAPI风格、请求参数、资源路径等相关信息。

安装核心SDK

Terminal中执行以下命令安装核心SDK,最新版本请参见aliyun-net-sdk-core

dotnet add package aliyun-net-sdk-core

调用OpenAPI

初始化请求客户端

通过创建DefaultAcsClient初始化请求客户端,示例中以使用AccessKey初始化客户端方式为例,更多初始化方式请参见管理访问凭据

说明

为了避免凭据泄露,常见的方案是将其写入到环境变量中,具体操作请参见Linux、macOSWindows系统配置环境变量

using Aliyun.Acs.Core;
using Aliyun.Acs.Core.Profile;

namespace AlibabaCloud.SDK.Sample
{
    public class Sample
    {
        public static void Main(string[] args)
        {
            IClientProfile profile = DefaultProfile.GetProfile(
                // 地域ID
                "<REGION_ID>",
                // 从环境变量获取RAM用户的AccessKey ID
                Environment.GetEnvironmentVariable("ALIBABA_CLOUD_ACCESS_KEY_ID"),
                // 从环境变量获取RAM用户的AccessKey SECRET
                Environment.GetEnvironmentVariable("ALIBABA_CLOUD_ACCESS_KEY_SECRET"));
            DefaultAcsClient client = new DefaultAcsClient(profile);
        }
    }
}

配置OpenAPI信息及请求参数

通过CommonRequest来配置OpenAPI所需的公共请求参数及接口请求参数。关于更多公共请求参数的介绍及使用请参见进阶配置

接口请求参数说明

请求参数应该如何传参需要查看接口对应的OpenAPI元数据,例如DescribeInstanceStatus的请求参数RegionId元数据中信息为{"name":"RegionId","in":"query",...}},其中"in":"query"表示RegionId通过AddQueryParameters传递。

描述

传参方式

请求参数显示"in":"query"时。

AddQueryParameters(string key,string value)

说明

如果请求参数的类型是集合,那么参数应该按照AddQueryParameters("key.1","value1")、AddQueryParameters("key.2","value2")...格式传参。

请求参数显示"in":"body""in": "formData"时。

AddBodyParameters(string key,string value)

说明

如果请求参数的类型不是字符串类型,则需要将参数值转换为JSON字符串,并赋值给变量value。

上传文件时。

SetContent(byte[] content,string charset,FormatType formatType)

说明

其中参数formatType固定为FormatType.RAW。

       // 2. 创建API请求,并设置参数
        CommonRequest request = new CommonRequest();
        // 2.1  设置公共请求参数
        request.Domain = "ecs-cn-hangzhou.aliyuncs.com"; // 对应云产品支持的endpoint
        request.Version = "2014-05-26"; // 对应云产品的API版本
        request.Action = "DescribeInstanceStatus"; // 接口名称,RPC必传,ROA非必传
        request.Method = MethodType.POST; // 设置请求方式,MethodType.POST、MethodType.GET、MethodType.PUT、MethodType.DELETE、MethodType.HEAD、MethodType.OPTIONS
        request.Protocol = ProtocolType.HTTPS; // 设置请求协议,ProtocolType.HTTPS、ProtocolType.HTTP
        request.TimeoutInMilliSeconds = 1000; // 超时时间
        // request.UriPattern = "/";  // 资源路径,ROA接口必传。RPC接口禁止设置该参数。

        // 2.2 设置接口请求参数
        // 场景一:Query参数通过AddQueryParameters(string key,string value)设置
        request.AddQueryParameters("RegionId", "cn-hangzhou");
        List<string> instanceIds = new List<string> { "i-bp124uve8zq7XXXXXXXX", "i-bp1axhql4dqaXXXXXXXX" };
        for (int i = 0; i < instanceIds.Count; i++) {
		request.AddQueryParameters($"InstanceId.{i + 1}" , instanceIds[i]);
	    }
        request.AddQueryParameters("PageNumber", "1");
        request.AddQueryParameters("PageSize", "30");

        // 场景二:body参数通过AddBodyParameters(string key,string value)设置
        // request.AddBodyParameters("key1", "value1");
        // request.AddBodyParameters("key2", "value2");

        // 场景三:文件上传SetContent(byte[] content,string charset,FormatType formatType),其中formatType固定为FormatType.RAW。
        // byte[] content = File.ReadAllBytes(@"<FILE_PATH>");
        // request.SetContent(content, "UTF-8",FormatType.RAW); 
        

发起请求

通过前面步骤创建的client调用GetCommonResponse发起请求。

CommonResponse response = client.GetCommonResponse(request);
System.Console.WriteLine(response.Data);

示例:调用RPC风格的API

以下代码展示了如何使用CommonRequest的方式调用ECSDescribeInstanceStatus接口:

using Aliyun.Acs.Core;
using Aliyun.Acs.Core.Exceptions;
using Aliyun.Acs.Core.Profile;
class Sample
{
    static void Main(string[] args)
    {
        // 构建一个客户端实例,用于发起请求
        IClientProfile profile = DefaultProfile.GetProfile(
            // 地域ID
            "cn-hangzhou",
            // 从环境变量获取RAM账号的AccessKey ID
            Environment.GetEnvironmentVariable("ALIBABA_CLOUD_ACCESS_KEY_ID"),
            // 从环境变量获取RAM账号的AccessKey SECRET
            Environment.GetEnvironmentVariable("ALIBABA_CLOUD_ACCESS_KEY_SECRET"));
        DefaultAcsClient client = new DefaultAcsClient(profile);
        try
        {
            // 构造请求
            CommonRequest request = new CommonRequest();
            request.Domain = "ecs.aliyuncs.com";
            request.Version = "2014-05-26";
            // 因为是 RPC 风格接口,需指定 ApiName(Action)
            request.Action = "DescribeInstanceStatus";
            request.AddQueryParameters("RegionId", "cn-hangzhou");
            List<string> instanceIds = new List<string> { "i-bp124uve8zq7XXXXXXXX", "i-bp1axhql4dqaXXXXXXXX" };
            for (int i = 0; i < instanceIds.Count; i++) {
                    request.AddQueryParameters($"InstanceId.{i + 1}" , instanceIds[i]);
                }
            request.AddQueryParameters("PageNumber", "1");
            request.AddQueryParameters("PageSize", "30");
            // 发起请求,并得到 Response
            CommonResponse response = client.GetCommonResponse(request);
            System.Console.WriteLine(response.Data);
        }
        catch (ServerException ex)
        {
            System.Console.WriteLine(ex.ToString());
        }
        catch (ClientException ex)
        {
            System.Console.WriteLine(ex.ToString());
        }
    }
}

示例:调用RESTful(ROA)风格的API

以下代码展示了如何使用CommonRequest的方式调用容器服务的查看所有集群实例接口:

using Aliyun.Acs.Core;
using Aliyun.Acs.Core.Exceptions;
using Aliyun.Acs.Core.Profile;
class Sample
{
    static void Main(string[] args)
    {
        // 构建一个 Client,用于发起请求
        IClientProfile profile = DefaultProfile.GetProfile(
            // 地域ID
            "<REGION-ID>",
            // 从环境变量获取RAM账号的AccessKey ID
            Environment.GetEnvironmentVariable("ALIBABA_CLOUD_ACCESS_KEY_ID"),
            // 从环境变量获取RAM账号的AccessKey SECRET
            Environment.GetEnvironmentVariable("ALIBABA_CLOUD_ACCESS_KEY_SECRET"));
        DefaultAcsClient client = new DefaultAcsClient(profile);
        try
        {
            // 构造请求
            CommonRequest request = new CommonRequest();
            request.Domain = "cs.aliyuncs.com";
            request.Version = "2015-12-15";
            // 因为是Restful风格接口,需指定 UriPattern
            request.UriPattern = "/clusters";
            // 发起请求,并得到 Response
            CommonResponse response = client.GetCommonResponse(request);
            System.Console.WriteLine(response.Data);
        }
        catch (ServerException ex)
        {
            System.Console.WriteLine(ex.ToString());
        }
        catch (ClientException ex)
        {
            System.Console.WriteLine(ex.ToString());
        }
    }
}

常见问题

  1. 报错提示“The input parameter \"AccessKeyId\" that is mandatory for processing this request is not supplied.”。

    问题原因:AK未正确配置。

    解决方案:

    1. 执行以下命令,检查您的环境变量中是否配置有ALIBABA_CLOUD_ACCESS_KEY_IDALIBABA_CLOUD_ACCESS_KEY_SECRET:

      Linux/macOS

      echo $ALIBABA_CLOUD_ACCESS_KEY_ID
      echo $ALIBABA_CLOUD_ACCESS_KEY_SECRET

      Windows

      echo %ALIBABA_CLOUD_ACCESS_KEY_ID%
      echo %ALIBABA_CLOUD_ACCESS_KEY_SECRET%

      若返回正确的AccessKey,则说明配置成功。如果返回为空或错误,请尝试重新设置,具体操作请参见Linux、macOSWindows系统配置环境变量

    2. 检查代码中AK相关内容是否存在错误。

      常见错误示例:

      AccessKeyId = Environment.GetEnvironmentVariable("yourAccessKeyID"),
      AccessKeySecret = Environment.GetEnvironmentVariable("yourAccessKeySecret"),

      正确示例

      Environment.GetEnvironmentVariable("ALIBABA_CLOUD_ACCESS_KEY_ID"), 
      Environment.GetEnvironmentVariable("ALIBABA_CLOUD_ACCESS_KEY_SECRET")
  2. 报错提示“Unhandled exception. Aliyun.Acs.Core.Exceptions.ClientException: SDK.WebException : HttpWebRequest WebException occured, the request url is XXX.cn-hangzhou.aliyuncs.com System.Net.WebException: An eile sending the request.”

    问题原因:RPC接口公共请求参数设置了UriPattern参数。

    解决方案:在公共请求参数中去掉UriPattern参数。