前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >基于API3.0开发C# Windows Forms应用

基于API3.0开发C# Windows Forms应用

原创
作者头像
zqfan
修改2020-04-22 16:28:07
11.1K14
修改2020-04-22 16:28:07
举报
文章被收录于专栏:腾讯云API腾讯云API

2020.04.22更新:根据用户的反馈,我们现在已支持同步调用。例如cvm 2017-03-12版本的DescribeRegions,如果想同步调用,直接DescribeRegionsSync即可。选用同步调用,请保持所有调用均为同步。同步异步混用,如果没处理好,容易造成问题。

==========原文=================

API 3.0 发布后,配套的多语言SDK将同步更新,其中 .NET SDK 3.0 由微软MVP张善友大大开发。

以下是当前的官网示例:https://cloud.tencent.com/document/sdk/.NET#.E7.A4.BA.E4.BE.8B

在这个例子中,创建的是控制台应用,使用的同步方式调用了异步的接口:

代码语言:txt
复制
DescribeInstancesResponse resp = client.DescribeInstances(req)
.ConfigureAwait(false).GetAwaiter().GetResult();

有一些朋友在开发ASP和Windows Forms应用时,发现按照官网的使用方式,不能按照预期返回结果,反而会导致界面卡死。

这是因为接口都做了异步化处理,而控制台应用不需要同步上下文,因此这种同步方式调用异步接口是没有问题的,会正常返回。

但是在ASP和Windows Forms应用中,通常不是主线程调用,需要同步上下文,当同步调用异步接口时,会发生UI线程被阻塞,从而界面卡死不动。

要解决这个问题,只需要让UI控件的响应方法异步化就可以了。例如从

代码语言:txt
复制
private void Button1_Click(object sender, EventArgs e)

改为

代码语言:txt
复制
private async void Button1_Click(object sender, EventArgs e)

具体的:

代码语言:txt
复制
        // SDK异步接口
        private async Task<string> GetZones()
        {
                // 处理一些初始化工作
                // 发起调用
                DescribeZonesResponse resp = await client.DescribeZones(req);
                // 输出json格式的字符串回包
                return AbstractModel.ToJsonString(resp);
        }
        // 注意:这里是一个异步接口
        private async void Button1_Click(object sender, EventArgs e)
        {
                textBox1.Text = await GetZones();
        }

这里按钮1(Button1)的点击响应方法(Button1_Click)里,异步的调用了.NET SDK接口,以获得可用区的信息,在请求结束后,将得到的返回显示在文本框中。最终的效果类似于:

image.png
image.png

另外一种方式其实也是用同步的方式,比异步的要差一点,因为UI线程要硬等,直到请求结束前界面都会卡住。具体的,就是将此请求放在一个线程中执行,并等待其结束,再操作UI控件。示例代码如下:

代码语言:txt
复制
        // SDK异步接口
        private async Task<string> GetZones()
        {
                // 处理一些初始化工作
                // 发起调用
                DescribeZonesResponse resp = await client.DescribeZones(req);
                // 输出json格式的字符串回包
                return AbstractModel.ToJsonString(resp);
        }
        // 注意:这里是一个同步接口
        private void Button1_Click(object sender, EventArgs e)
        {
            var result = "";
            var t = Task.Run(() =>
            {
                // 同步方式调用,会卡住直到请求返回
                result = GetZones().ConfigureAwait(false).GetAwaiter().GetResult();
            });
            // 同步等待,会卡住直到线程返回
            t.Wait();
            textBox1.Text = result;
        }

由于本人.NET编程水平有限,此方案未必是最优的。有需要的朋友可以借鉴下,或者留言探讨下。

附上源码,注意,源码中设置了对.NET SDK的依赖和其他的依赖,使用NuGet可以添加这个依赖。(把依赖一起打包的话包体积在8MB,上传失败了 。。)

另外需要从环境变量中读取一些信息,如果没有这些环境变量,执行会失败。

对此,你可以把自己的密钥写在代码中,或者设置所需要的对应的环境变量。如果是直连环境,可以不设置代理。

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档