微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

C#Swagger生成的客户端如何验证和使用自动生成的代码

如何解决C#Swagger生成的客户端如何验证和使用自动生成的代码

我已经使用nSwag Studio从Swagger DeFinition(Openapi 3.0.3)成功地生成了类,但是我不知道如何正确地将其用作客户端。

手动使用RestSharp代码可以正常工作,但是我想使用自动生成代码来使用Web服务方法并且无法正确完成

这工作正常:

string clientId = "dev";
string clientSecret = @"pass";

var client = new RestClient("http://192.168.1.10/xyz/apI/Oauth/token");
var request = new RestRequest(Method.POST);
request.AddHeader("cache-control","no-cache");
request.AddHeader("content-type","application/x-www-form-urlencoded");
request.AddHeader("grant_type","client_credentials");

var credentials = string.Format("{0}:{1}",clientId,clientSecret);
var headerValue = Convert.ToBase64String(Encoding.UTF8.GetBytes(credentials));
request.AddHeader("Authorization",$"Basic {headerValue}");
request.AddParameter($"application/x-www-form-urlencoded",$"grant_type=client_credentials&client_id={clientId}&client_secret{clientSecret}",ParameterType.RequestBody);
IRestResponse response = client.Execute(request,Method.POST);

我尝试使用自动生成代码。我错误地举报,但找不到任何例子。 例子很少,但看起来客户端是通过不同的方式生成的(使用基本url初始化客户端-但在这种情况下仍不了解基本授权) Googling大多返回“如何创建服务器端”或向asp / mvc / webapi项目添加招摇。

        string URL = @"http://192.168.1.10/xyz/api";
        string clientId = "dev";
        string clientSecret = @"pass";

        IO.Swagger.Client.apiclient client = new IO.Swagger.Client.apiclient(URL);
        IO.Swagger.Client.Configuration.Defaultapiclient = client; //<<this throws error
        IO.Swagger.Client.Configuration.Username = clientId;
        IO.Swagger.Client.Configuration.Password = clientSecret;
        client.AddDefaultHeader("Authorization","bearer TOKEN");

        IO.Swagger.Api.AuthApi authApi = new IO.Swagger.Api.AuthApi(client);

apiclient错误

public apiclient(String basePath="/xyz/api")
{
BasePath = basePath;
RestClient = new RestClient(BasePath); //System.UriFormatException: 'Invalid URI: The format of the URI Could not be determined.'
}

我尝试了许多字符串形式的url(类未明确接受Uri)

配置

using System;
using System.Reflection;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;

namespace IO.Swagger.Client
{
    public class Configuration
    {
        public const string Version = "1.0.0";
        public static apiclient Defaultapiclient = new apiclient();
        public static String Username { get; set; }
        public static String Password { get; set; }
        public static Dictionary<String,String> ApiKey = new Dictionary<String,String>();
        public static Dictionary<String,String> ApiKeyPrefix = new Dictionary<String,String>();
        private static string _tempFolderPath = Path.GetTempPath();
        public static String TempFolderPath
        {
            get { return _tempFolderPath; }
  
            set 
            {
                if (String.IsNullOrEmpty(value))
                {
                    _tempFolderPath = value;
                    return;
                }
      
                // create the directory if it does not exist
                if (!Directory.Exists(value)) 
                    Directory.CreateDirectory(value);
      
                // check if the path contains directory separator at the end
                if (value[value.Length - 1] == Path.DirectorySeparatorChar)
                    _tempFolderPath = value;
                else
                    _tempFolderPath = value  + Path.DirectorySeparatorChar;
            }
        }

        private const string ISO8601_DATETIME_FORMAT = "o";
        private static string _dateTimeFormat = ISO8601_DATETIME_FORMAT;

        public static String DateTimeFormat
        {
            get
            {
                return _dateTimeFormat;
            }
            set
            {
                if (string.IsNullOrEmpty(value))
                {
                    // Never allow a blank or null string,go back to the default
                    _dateTimeFormat = ISO8601_DATETIME_FORMAT;
                    return;
                }

                // Caution,no validation when you choose date time format other than ISO 8601
                // Take a look at the above links
                _dateTimeFormat = value;
            }
        }

        public static String ToDebugReport()
        {
            String report = "C# SDK (IO.Swagger) Debug Report:\n";
            report += "    OS: " + Environment.Osversion + "\n";
            report += "    .NET Framework Version: " + Assembly
                     .GetExecutingAssembly()
                     .GetReferencedAssemblies()
                     .Where(x => x.Name == "System.Core").First().Version.ToString()  + "\n";
            report += "    Version of the API: 2.0.1\n";
            report += "    SDK Package Version: 1.0.0\n";
  
            return report;
        }
    }
}

客户

using System;
using System.Collections.Generic;
using System.Globalization;
using System.Text.RegularExpressions;
using System.IO;
using System.Web;
using System.Linq;
using System.Net;
using System.Text;
using Newtonsoft.Json;
using RestSharp;
using RestSharp.Extensions;

namespace IO.Swagger.Client
{
    public class apiclient
    {
        private readonly Dictionary<String,String> _defaultHeaderMap = new Dictionary<String,String>();
  
        public apiclient(String basePath="/xyz/api")
        {
            BasePath = basePath;
            RestClient = new RestClient(BasePath);
        }
    
        public string BasePath { get; set; }
        public RestClient RestClient { get; set; }
        public Dictionary<String,String> DefaultHeader
        {
            get { return _defaultHeaderMap; }
        }
        public Object CallApi(String path,RestSharp.Method method,Dictionary<String,String> queryParams,String postBody,String> headerParams,String> formParams,FileParameter> fileParams,String[] authSettings)
        {

            var request = new RestRequest(path,method);
   
            UpdateParamsForAuth(queryParams,headerParams,authSettings);

            // add default header,if any
            foreach(var defaultHeader in _defaultHeaderMap)
                request.AddHeader(defaultHeader.Key,defaultHeader.Value);

            // add header parameter,if any
            foreach(var param in headerParams)
                request.AddHeader(param.Key,param.Value);

            // add query parameter,if any
            foreach(var param in queryParams)
                request.AddParameter(param.Key,param.Value,ParameterType.GetorPost);

            // add form parameter,if any
            foreach(var param in formParams)
                request.AddParameter(param.Key,ParameterType.GetorPost);

            // add file parameter,if any
            foreach(var param in fileParams)
                request.AddFile(param.Value.Name,param.Value.Writer,param.Value.FileName,param.Value.ContentType);

            if (postBody != null) // http body (model) parameter
                request.AddParameter("application/json",postBody,ParameterType.RequestBody);

            return (Object)RestClient.Execute(request);

        }
    
        public void AddDefaultHeader(string key,string value)
        {
            _defaultHeaderMap.Add(key,value);
        }
    
        public string Escapestring(string str)
        {
            return RestSharp.Contrib.HttpUtility.UrlEncode(str);
        }
    
        public FileParameter ParameterToFile(string name,Stream stream)
        {
            if (stream is FileStream)
                return FileParameter.Create(name,stream.ReadAsBytes(),Path.GetFileName(((FileStream)stream).Name));
            else
                return FileParameter.Create(name,"no_file_name_provided");
        }
    
        public string ParameterToString(object obj)
        {
            if (obj is DateTime)
                // Return a formatted date string - Can be customized with Configuration.DateTimeFormat
                // Defaults to an ISO 8601,using the kNown as a Round-trip date/time pattern ("o")
                // https://msdn.microsoft.com/en-us/library/az4se3k1(v=vs.110).aspx#Anchor_8
                // For example: 2009-06-15T13:45:30.0000000
                return ((DateTime)obj).ToString (Configuration.DateTimeFormat);
            else if (obj is List<string>)
                return String.Join(",",(obj as List<string>).ToArray());
            else
                return Convert.ToString (obj);
        }
    
        public object Deserialize(string content,Type type,IList<Parameter> headers=null)
        {
            if (type == typeof(Object)) // return an object
            {
                return content;
            }

            if (type == typeof(Stream))
            {
                var filePath = String.IsNullOrEmpty(Configuration.TempFolderPath)
                    ? Path.GetTempPath()
                    : Configuration.TempFolderPath;

                var fileName = filePath + Guid.NewGuid();
                if (headers != null)
                {
                    var regex = new Regex(@"Content-disposition:.*filename=['""]?([^'""\s]+)['""]?$");
                    var match = regex.Match(headers.ToString());
                    if (match.Success)
                        fileName = filePath + match.Value.Replace("\"","").Replace("'","");
                }
                File.WriteallText(fileName,content);
                return new FileStream(fileName,FileMode.Open);

            }

            if (type.Name.StartsWith("System.Nullable`1[[System.DateTime")) // return a datetime object
            {
                return DateTime.Parse(content,null,System.Globalization.DateTimeStyles.roundtripKind);
            }

            if (type == typeof(String) || type.Name.StartsWith("System.Nullable")) // return primitive type
            {
                return ConvertType(content,type); 
            }
    
            // at this point,it must be a model (json)
            try
            {
                return JsonConvert.DeserializeObject(content,type);
            }
            catch (IOException e)
            {
                throw new ApiException(500,e.Message);
            }
        }
    
        public string Serialize(object obj)
        {
            try
            {
                return obj != null ? JsonConvert.SerializeObject(obj) : null;
            }
            catch (Exception e)
            {
                throw new ApiException(500,e.Message);
            }
        }
    
        public string GetApiKeyWithPrefix (string apiKeyIdentifier)
        {
            var apikeyvalue = "";
            Configuration.ApiKey.TryGetValue (apiKeyIdentifier,out apikeyvalue);
            var apiKeyPrefix = "";
            if (Configuration.ApiKeyPrefix.TryGetValue (apiKeyIdentifier,out apiKeyPrefix))
                return apiKeyPrefix + " " + apikeyvalue;
            else
                return apikeyvalue;
        }
    
        public void UpdateParamsForAuth(Dictionary<String,string[] authSettings)
        {
            if (authSettings == null || authSettings.Length == 0)
                return;

            foreach (string auth in authSettings)
            {
                // determine which one to use
                switch(auth)
                {
                    case "BasicAuth":
                        headerParams["Authorization"] = "Basic " + Base64Encode(Configuration.Username + ":" + Configuration.Password);
                        
                        break;
                    case "BearerAuth":
                        
                        
                        break;
                    default:
                        //Todo show warning about security deFinition not found
                        break;
                }
            }
        }
 
        public static string Base64Encode(string text)
        {
            var textByte = System.Text.Encoding.UTF8.GetBytes(text);
            return System.Convert.ToBase64String(textByte);
        }
    
        public static Object ConvertType(Object fromObject,Type toObject) {
            return Convert.ChangeType(fromObject,toObject);
        }
    }
}

AuthApi

using System;
using System.Collections.Generic;
using RestSharp;
using IO.Swagger.Client;
using IO.Swagger.Model;

namespace IO.Swagger.Api
{
    public interface IAuthApi
    {
        InlineResponse200 OauthTokenPost (string grantType);
    }
  
    public class AuthApi : IAuthApi
    {
        public AuthApi(apiclient apiclient = null)
        {
            if (apiclient == null) // use the default one in Configuration
                this.apiclient = Configuration.Defaultapiclient; 
            else
                this.apiclient = apiclient;
        }
    
        public AuthApi(String basePath)
        {
            this.apiclient = new apiclient(basePath);
        }
    
        public void SetBasePath(String basePath)
        {
            this.apiclient.BasePath = basePath;
        }
    
        public String GetBasePath(String basePath)
        {
            return this.apiclient.BasePath;
        }
    
        public apiclient apiclient {get; set;}
    
        public InlineResponse200 OauthTokenPost (string grantType)
        {
    
            var path = "/oauth/token";
            path = path.Replace("{format}","json");
                
            var queryParams = new Dictionary<String,String>();
            var headerParams = new Dictionary<String,String>();
            var formParams = new Dictionary<String,String>();
            var fileParams = new Dictionary<String,FileParameter>();
            String postBody = null;
    
            if (grantType != null) formParams.Add("grant_type",apiclient.ParameterToString(grantType)); // form parameter
                
            // authentication setting,if any
            String[] authSettings = new String[] { "BasicAuth" };
    
            // make the HTTP request
            IRestResponse response = (IRestResponse) apiclient.CallApi(path,Method.POST,queryParams,formParams,fileParams,authSettings);
    
            if (((int)response.StatusCode) >= 400)
                throw new ApiException ((int)response.StatusCode,"Error calling OauthTokenPost: " + response.Content,response.Content);
            else if (((int)response.StatusCode) == 0)
                throw new ApiException ((int)response.StatusCode,"Error calling OauthTokenPost: " + response.ErrorMessage,response.ErrorMessage);
    
            return (InlineResponse200) apiclient.Deserialize(response.Content,typeof(InlineResponse200),response.Headers);
        }
    
    }
}

解决方法

给我的印象是,您的主要问题是Uri格式。我建议这样做可以找到确切的问题

    string URL = @"http://192.168.1.10/xyz/api";
    Uri baseAddress = new Uri(URL);
    string clientId = "dev";
    string clientSecret = @"pass";

    IO.Swagger.Client.ApiClient client = new IO.Swagger.Client.ApiClient(baseAddress.ToString());
    IO.Swagger.Client.Configuration.DefaultApiClient = client; //<<this throws error
    IO.Swagger.Client.Configuration.Username = clientId;
    IO.Swagger.Client.Configuration.Password = clientSecret;
    client.AddDefaultHeader("Authorization","bearer TOKEN");

    IO.Swagger.Api.AuthApi authApi = new IO.Swagger.Api.AuthApi(client);

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。