吐血原创,转载请注明出处!
目录
假如我们有个Winform程序,这个程序有个表格,用户如何通过简单的http请求来增删改查这个表格,而不用手动去操作这个Winform程序呢?Winform+Owin正是其中一个挺不错的方案!表格操作代码量相对多一点,这里我就用简单的TextBox作为案例,简单的写一下这个方案!
解决方案目录:
1.界面(控件自己拽一下):
2.安装OwinSelfHost插件
3.Startup类
using Owin;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Net.Http.Headers;
using System.Text;
using System.Threading.Tasks;
using System.Web.Http;
namespace WindowsFormsApp3 {
class Startup {
// This code configures Web API. The Startup class is specified as a type
// parameter in the WebApp.Start method.
public void Configuration(Owin.IAppBuilder appBuilder) {
// Configure Web API for self-host.
HttpConfiguration config = new HttpConfiguration();
config.Routes.MapHttpRoute(
name: "DefaultApi",
routeTemplate: "api/{controller}/{action}/{id}",
defaults: new { id = RouteParameter.Optional }
);
config.Formatters.XmlFormatter.SupportedMediaTypes.Clear();
config.Formatters.JsonFormatter.SupportedMediaTypes.Add(new MediaTypeHeaderValue("text/html"));
//将默认xml返回数据格式改为json
//config.Formatters.XmlFormatter.SupportedMediaTypes.Clear();
//config.Formatters.JsonFormatter.MediaTypeMappings.Add(new QueryStringMapping("datatype", "json", "application/json"));
//json 序列化设置
//config.Formatters.JsonFormatter.SerializerSettings = new Newtonsoft.Json.JsonSerializerSettings() {
// NullValueHandling = Newtonsoft.Json.NullValueHandling.Ignore //设置忽略值为 null 的属性
// };
appBuilder.UseWebApi(config);
}
}
}
4.LogController控制类
using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Net.Http;
using System.Text;
using System.Threading.Tasks;
using System.Web.Http;
namespace WindowsFormsApp3 {
public class LogController : ApiController {
//这里用户请求的时候,如果不提交msg参数,那么将会404,建议将参数改成这种方式[FromUri] Obj obj
[HttpGet]
public string Get([FromUri] Obj obj) {
if (obj == null) {
return "msg参数不能为空!";
}
UI.GetF1().AppendText("用户发起了Get请求(http://xxx.xxx.x.xxx:9000/api/log/Get),msg参数:" + obj.msg);
return "msg:" + obj.msg;
}
[HttpPost]
public string Post ([FromBody]Obj obj) {
if (obj==null) {
return "msg参数不能为空!";
}
UI.GetF1().AppendText("用户发起了Post请求(http://xxx.xxx.x.xxx:9000/api/log/Post),msg参数:"+ obj.msg);
return "msg:"+ obj.msg;
}
[HttpPost]
public HttpResponseMessage log([FromBody] Obj obj) {
HttpResponseMessage result;
string response = "";
if (obj == null) {
response = "参数不能为空!";
} else {
if (obj.msg == null || obj.msg.Length == 0) {
response += "msg参数不能为空";
}
if (obj.log == null || obj.log.Length == 0) {
response += " log参数不能为空";
}
}
if (response.Length>0) {
result = new HttpResponseMessage(HttpStatusCode.OK) {
Content = new StringContent(response, System.Text.Encoding.UTF8)
};
return result;
}
UI.GetF1().AppendText("用户发起了Post请求(http://xxx.xxx.x.xxx:9000/api/log/log),msg=" + obj.msg+",log="+obj.log);
result = new HttpResponseMessage(HttpStatusCode.OK) {
Content = new StringContent("这是post log:msg=" + obj.msg + ",log=" + obj.log)
};
return result;
}
public class Obj {
public string msg { get; set; }
public string log { get; set; }
}
}
}
5.界面事件绑定
using Microsoft.Owin.Hosting;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Net;
using System.Net.Http;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
namespace WindowsFormsApp3 {
public partial class Form1 : Form {
public Form1() {
InitializeComponent();
//非主线程亦可操作界面
CheckForIllegalCrossThreadCalls = false;
}
private void button1_Click(object sender, EventArgs e) {
//获取本机IP
string IP = "";
IPHostEntry here = Dns.GetHostEntry(Dns.GetHostName());
foreach (IPAddress _ip in here.AddressList) {
if (_ip.AddressFamily.ToString().ToUpper() == "INTERNETWORK") {
IP = _ip.ToString();
break;
}
}
string baseAddress = "http://"+ IP+":9000/";
WebApp.Start<Startup>(url: baseAddress);
AppendText("服务器IP及端口:"+ baseAddress);
AppendText("开始监听...");
}
private void button2_Click(object sender, EventArgs e) {
//测试API(这里就没写测试的了,自己用Http工具自己试一下)
//http://192.168.1.3:9000/api/log/Get?msg=234234
//URL:http://192.168.1.3:9000/api/log/Post 请求体:msg=testMsg&log=testLog
//URL:http://192.168.1.3:9000/api/log/log 请求体:msg=testMsg&log=testLog
}
public void AppendText(string msg) {
textBox1.AppendText(msg+"\r\n");
}
}
}
6.UI类(方便其他调用界面空间)
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace WindowsFormsApp3 {
class UI {
private static Form1 f1;
public static Form1 GetF1() {
if (f1==null) {
f1 = new Form1();
}
return f1;
}
}
}
7.Main启动类(包含全局异常捕获弹窗显示)
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using System.Windows.Forms;
namespace WindowsFormsApp3 {
static class Program {
/// <summary>
/// 应用程序的主入口点。
/// </summary>
[STAThread]
static void Main() {
try {
//处理未捕获的异常
Application.SetUnhandledExceptionMode(UnhandledExceptionMode.CatchException);
//处理UI线程异常
Application.ThreadException += Application_ThreadException;
//处理非UI线程异常
AppDomain.CurrentDomain.UnhandledException += CurrentDomain_UnhandledException;
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
//Application.Run(new Form1());
Application.Run(UI.GetF1());
} catch (Exception ex) {
var strDateInfo = "出现应用程序未处理的异常:" + DateTime.Now + "\r\n";
var str = string.Format(strDateInfo + "异常类型:{0}\r\n异常消息:{1}\r\n异常信息:{2}\r\n",
ex.GetType().Name, ex.Message, ex.StackTrace);
MessageBox.Show(str, "系统错误", MessageBoxButtons.OK, MessageBoxIcon.Error);//进行弹窗提示
//Environment.Exit(0);
}
}
/// <summary>
///错误弹窗
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
static void Application_ThreadException(object sender, System.Threading.ThreadExceptionEventArgs e) {
string str;
var strDateInfo = "出现应用程序未处理的异常:" + DateTime.Now + "\r\n";
var error = e.Exception;
if (error != null) {
str = string.Format(strDateInfo + "异常类型:{0}\r\n异常消息:{1}\r\n异常信息:{2}\r\n",
error.GetType().Name, error.Message, error.StackTrace);
} else {
str = string.Format("应用程序线程错误:{0}", e);
}
MessageBox.Show(str, "系统错误", MessageBoxButtons.OK, MessageBoxIcon.Error);
//Environment.Exit(0);
}
static void CurrentDomain_UnhandledException(object sender, UnhandledExceptionEventArgs e) {
var error = e.ExceptionObject as Exception;
var strDateInfo = "出现应用程序未处理的异常:" + DateTime.Now + "\r\n";
var str = error != null ? string.Format(strDateInfo + "Application UnhandledException:{0};\n\r堆栈信息:{1}", error.Message, error.StackTrace) : string.Format("Application UnhandledError:{0}", e);
MessageBox.Show(str, "系统错误", MessageBoxButtons.OK, MessageBoxIcon.Error);
//Environment.Exit(0);
}
}
}
TestController类是我自己瞎写测试的,这里没什么关联就不放上来了....
有什么不对的欢迎指出批评,写博不易,转载请注明出处