THRIFT-25. csharp: Various compiler and library improvements
Compiler:
- Thrift structures are serializable.
- The member fields of thrift structures are now private and only accessible
through Properties, which keep the appropriate __isset up to date.
Library
- Addition of TBufferedTransport, which can be used to wrap other Transports.
- Addition of TThreadedServer, which manually manages threads instead of
relying on .NET ThreadPool.
- Servers use a log delegate that defaults to System.Console but allows
servers to use log4net without introducing the dependency.
ThriftTest Visual Studio Project
- Test client and server that use ThriftTest.thrift. The project references
thrift.exe and Thrift.dll from the subversion tree and automatically builds
generated code. This makes it very easy to test changes in both the compiler
and library.
git-svn-id: https://svn.apache.org/repos/asf/incubator/thrift/trunk@732079 13f79535-47bb-0310-9956-ffa450edef68
diff --git a/test/csharp/ThriftTest/Program.cs b/test/csharp/ThriftTest/Program.cs
new file mode 100644
index 0000000..09bd84f
--- /dev/null
+++ b/test/csharp/ThriftTest/Program.cs
@@ -0,0 +1,44 @@
+// Distributed under the Thrift Software License
+//
+// See accompanying file LICENSE or visit the Thrift site at:
+// http://developers.facebook.com/thrift/
+
+using System;
+using System.Collections.Generic;
+using System.Text;
+using Thrift.Transport;
+using Thrift.Protocol;
+using Thrift.Test; //generated code
+
+namespace Test
+{
+ class Program
+ {
+ static void Main(string[] args)
+ {
+ if (args.Length == 0)
+ {
+ Console.WriteLine("must provide 'server' or 'client' arg");
+ return;
+ }
+
+ string[] subArgs = new string[args.Length - 1];
+ for(int i = 1; i < args.Length; i++)
+ {
+ subArgs[i-1] = args[i];
+ }
+ if (args[0] == "client")
+ {
+ TestClient.Execute(subArgs);
+ }
+ else if (args[0] == "server")
+ {
+ TestServer.Execute(subArgs);
+ }
+ else
+ {
+ Console.WriteLine("first argument must be 'server' or 'client'");
+ }
+ }
+ }
+}
diff --git a/test/csharp/ThriftTest/Properties/AssemblyInfo.cs b/test/csharp/ThriftTest/Properties/AssemblyInfo.cs
new file mode 100644
index 0000000..5b45949
--- /dev/null
+++ b/test/csharp/ThriftTest/Properties/AssemblyInfo.cs
@@ -0,0 +1,36 @@
+using System.Reflection;
+using System.Runtime.CompilerServices;
+using System.Runtime.InteropServices;
+
+// General Information about an assembly is controlled through the following
+// set of attributes. Change these attribute values to modify the information
+// associated with an assembly.
+[assembly: AssemblyTitle("ThriftTest")]
+[assembly: AssemblyDescription("")]
+[assembly: AssemblyConfiguration("")]
+[assembly: AssemblyCompany("")]
+[assembly: AssemblyProduct("ThriftTest")]
+[assembly: AssemblyCopyright("Copyright © 2009 The Apache Software Foundation")]
+[assembly: AssemblyTrademark("")]
+[assembly: AssemblyCulture("")]
+
+// Setting ComVisible to false makes the types in this assembly not visible
+// to COM components. If you need to access a type in this assembly from
+// COM, set the ComVisible attribute to true on that type.
+[assembly: ComVisible(false)]
+
+// The following GUID is for the ID of the typelib if this project is exposed to COM
+[assembly: Guid("f41b193b-f1ab-48ee-8843-f88e43084e26")]
+
+// Version information for an assembly consists of the following four values:
+//
+// Major Version
+// Minor Version
+// Build Number
+// Revision
+//
+// You can specify all the values or you can default the Build and Revision Numbers
+// by using the '*' as shown below:
+// [assembly: AssemblyVersion("1.0.*")]
+[assembly: AssemblyVersion("1.0.0.0")]
+[assembly: AssemblyFileVersion("1.0.0.0")]
diff --git a/test/csharp/ThriftTest/TestClient.cs b/test/csharp/ThriftTest/TestClient.cs
new file mode 100644
index 0000000..bcdb00e
--- /dev/null
+++ b/test/csharp/ThriftTest/TestClient.cs
@@ -0,0 +1,407 @@
+using System;
+using System.Collections.Generic;
+using System.Text;
+
+using Thrift.Protocol;
+using Thrift.Transport;
+using Thrift.Test;
+using System.Threading;
+
+namespace Test
+{
+ public class TestClient
+ {
+ private static int numIterations = 1;
+
+ public static void Execute(string[] args)
+ {
+ try
+ {
+ string host = "localhost";
+ int port = 9090;
+ string url = null;
+ int numThreads = 1;
+ bool buffered = false;
+
+ try
+ {
+ for (int i = 0; i < args.Length; i++)
+ {
+ if (args[i] == "-h")
+ {
+ string[] hostport = args[++i].Split(':');
+ host = hostport[0];
+ if (hostport.Length > 1)
+ {
+ port = Convert.ToInt32(hostport[1]);
+ }
+ }
+ else if (args[i] == "-u")
+ {
+ url = args[++i];
+ }
+ else if (args[i] == "-n")
+ {
+ numIterations = Convert.ToInt32(args[++i]);
+ }
+ else if (args[i] == "-b" || args[i] == "-buffered")
+ {
+ buffered = true;
+ Console.WriteLine("Using buffered sockets");
+ }
+ else if (args[i] == "-t")
+ {
+ numThreads = Convert.ToInt32(args[++i]);
+ }
+ }
+ }
+ catch (Exception e)
+ {
+ Console.WriteLine(e.StackTrace);
+ }
+
+
+
+ //issue tests on separate threads simultaneously
+ Thread[] threads = new Thread[numThreads];
+ DateTime start = DateTime.Now;
+ for (int test = 0; test < numThreads; test++)
+ {
+ Thread t = new Thread(new ParameterizedThreadStart(ClientThread));
+ threads[test] = t;
+ TSocket socket = new TSocket(host, port);
+ if (buffered)
+ {
+ TBufferedTransport buffer = new TBufferedTransport(socket);
+ t.Start(buffer);
+ }
+ else
+ {
+ t.Start(socket);
+ }
+ }
+
+ for (int test = 0; test < numThreads; test++)
+ {
+ threads[test].Join();
+ }
+ Console.Write("Total time: " + (DateTime.Now - start));
+ }
+ catch (Exception outerEx)
+ {
+ Console.WriteLine(outerEx.Message + " ST: " + outerEx.StackTrace);
+ }
+
+ Console.WriteLine();
+ Console.WriteLine();
+ }
+
+ public static void ClientThread(object obj)
+ {
+ TTransport transport = (TTransport)obj;
+ for (int i = 0; i < numIterations; i++)
+ {
+ ClientTest(transport);
+ }
+ transport.Close();
+ }
+
+ public static void ClientTest(TTransport transport)
+ {
+ TBinaryProtocol binaryProtocol = new TBinaryProtocol(transport);
+
+ ThriftTest.Client client = new ThriftTest.Client(binaryProtocol);
+ try
+ {
+ if (!transport.IsOpen)
+ {
+ transport.Open();
+ }
+ }
+ catch (TTransportException ttx)
+ {
+ Console.WriteLine("Connect failed: " + ttx.Message);
+ return;
+ }
+
+ long start = DateTime.Now.ToFileTime();
+
+ Console.Write("testVoid()");
+ client.testVoid();
+ Console.WriteLine(" = void");
+
+ Console.Write("testString(\"Test\")");
+ string s = client.testString("Test");
+ Console.WriteLine(" = \"" + s + "\"");
+
+ Console.Write("testByte(1)");
+ byte i8 = client.testByte((byte)1);
+ Console.WriteLine(" = " + i8);
+
+ Console.Write("testI32(-1)");
+ int i32 = client.testI32(-1);
+ Console.WriteLine(" = " + i32);
+
+ Console.Write("testI64(-34359738368)");
+ long i64 = client.testI64(-34359738368);
+ Console.WriteLine(" = " + i64);
+
+ Console.Write("testDouble(5.325098235)");
+ double dub = client.testDouble(5.325098235);
+ Console.WriteLine(" = " + dub);
+
+ Console.Write("testStruct({\"Zero\", 1, -3, -5})");
+ Xtruct o = new Xtruct();
+ o.String_thing = "Zero";
+ o.Byte_thing = (byte)1;
+ o.I32_thing = -3;
+ o.I64_thing = -5;
+ Xtruct i = client.testStruct(o);
+ Console.WriteLine(" = {\"" + i.String_thing + "\", " + i.Byte_thing + ", " + i.I32_thing + ", " + i.I64_thing + "}");
+
+ Console.Write("testNest({1, {\"Zero\", 1, -3, -5}, 5})");
+ Xtruct2 o2 = new Xtruct2();
+ o2.Byte_thing = (byte)1;
+ o2.Struct_thing = o;
+ o2.I32_thing = 5;
+ Xtruct2 i2 = client.testNest(o2);
+ i = i2.Struct_thing;
+ Console.WriteLine(" = {" + i2.Byte_thing + ", {\"" + i.String_thing + "\", " + i.Byte_thing + ", " + i.I32_thing + ", " + i.I64_thing + "}, " + i2.I32_thing + "}");
+
+ Dictionary<int, int> mapout = new Dictionary<int, int>();
+ for (int j = 0; j < 5; j++)
+ {
+ mapout[j] = j - 10;
+ }
+ Console.Write("testMap({");
+ bool first = true;
+ foreach (int key in mapout.Keys)
+ {
+ if (first)
+ {
+ first = false;
+ }
+ else
+ {
+ Console.Write(", ");
+ }
+ Console.Write(key + " => " + mapout[key]);
+ }
+ Console.Write("})");
+
+ Dictionary<int, int> mapin = client.testMap(mapout);
+
+ Console.Write(" = {");
+ first = true;
+ foreach (int key in mapin.Keys)
+ {
+ if (first)
+ {
+ first = false;
+ }
+ else
+ {
+ Console.Write(", ");
+ }
+ Console.Write(key + " => " + mapin[key]);
+ }
+ Console.WriteLine("}");
+
+ List<int> listout = new List<int>();
+ for (int j = -2; j < 3; j++)
+ {
+ listout.Add(j);
+ }
+ Console.Write("testList({");
+ first = true;
+ foreach (int j in listout)
+ {
+ if (first)
+ {
+ first = false;
+ }
+ else
+ {
+ Console.Write(", ");
+ }
+ Console.Write(j);
+ }
+ Console.Write("})");
+
+ List<int> listin = client.testList(listout);
+
+ Console.Write(" = {");
+ first = true;
+ foreach (int j in listin)
+ {
+ if (first)
+ {
+ first = false;
+ }
+ else
+ {
+ Console.Write(", ");
+ }
+ Console.Write(j);
+ }
+ Console.WriteLine("}");
+
+ //set
+ HashSet<int> setout = new HashSet<int>();
+ for (int j = -2; j < 3; j++)
+ {
+ setout.Add(j);
+ }
+ Console.Write("testSet({");
+ first = true;
+ foreach (int j in setout)
+ {
+ if (first)
+ {
+ first = false;
+ }
+ else
+ {
+ Console.Write(", ");
+ }
+ Console.Write(j);
+ }
+ Console.Write("})");
+
+ HashSet<int> setin = client.testSet(setout);
+
+ Console.Write(" = {");
+ first = true;
+ foreach (int j in setin)
+ {
+ if (first)
+ {
+ first = false;
+ }
+ else
+ {
+ Console.Write(", ");
+ }
+ Console.Write(j);
+ }
+ Console.WriteLine("}");
+
+
+ Console.Write("testEnum(ONE)");
+ Numberz ret = client.testEnum(Numberz.ONE);
+ Console.WriteLine(" = " + ret);
+
+ Console.Write("testEnum(TWO)");
+ ret = client.testEnum(Numberz.TWO);
+ Console.WriteLine(" = " + ret);
+
+ Console.Write("testEnum(THREE)");
+ ret = client.testEnum(Numberz.THREE);
+ Console.WriteLine(" = " + ret);
+
+ Console.Write("testEnum(FIVE)");
+ ret = client.testEnum(Numberz.FIVE);
+ Console.WriteLine(" = " + ret);
+
+ Console.Write("testEnum(EIGHT)");
+ ret = client.testEnum(Numberz.EIGHT);
+ Console.WriteLine(" = " + ret);
+
+ Console.Write("testTypedef(309858235082523)");
+ long uid = client.testTypedef(309858235082523L);
+ Console.WriteLine(" = " + uid);
+
+ Console.Write("testMapMap(1)");
+ Dictionary<int, Dictionary<int, int>> mm = client.testMapMap(1);
+ Console.Write(" = {");
+ foreach (int key in mm.Keys)
+ {
+ Console.Write(key + " => {");
+ Dictionary<int, int> m2 = mm[key];
+ foreach (int k2 in m2.Keys)
+ {
+ Console.Write(k2 + " => " + m2[k2] + ", ");
+ }
+ Console.Write("}, ");
+ }
+ Console.WriteLine("}");
+
+ Insanity insane = new Insanity();
+ insane.UserMap = new Dictionary<Numberz, long>();
+ insane.UserMap[Numberz.FIVE] = 5000L;
+ Xtruct truck = new Xtruct();
+ truck.String_thing = "Truck";
+ truck.Byte_thing = (byte)8;
+ truck.I32_thing = 8;
+ truck.I64_thing = 8;
+ insane.Xtructs = new List<Xtruct>();
+ insane.Xtructs.Add(truck);
+ Console.Write("testInsanity()");
+ Dictionary<long, Dictionary<Numberz, Insanity>> whoa = client.testInsanity(insane);
+ Console.Write(" = {");
+ foreach (long key in whoa.Keys)
+ {
+ Dictionary<Numberz, Insanity> val = whoa[key];
+ Console.Write(key + " => {");
+
+ foreach (Numberz k2 in val.Keys)
+ {
+ Insanity v2 = val[k2];
+
+ Console.Write(k2 + " => {");
+ Dictionary<Numberz, long> userMap = v2.UserMap;
+
+ Console.Write("{");
+ if (userMap != null)
+ {
+ foreach (Numberz k3 in userMap.Keys)
+ {
+ Console.Write(k3 + " => " + userMap[k3] + ", ");
+ }
+ }
+ else
+ {
+ Console.Write("null");
+ }
+ Console.Write("}, ");
+
+ List<Xtruct> xtructs = v2.Xtructs;
+
+ Console.Write("{");
+ if (xtructs != null)
+ {
+ foreach (Xtruct x in xtructs)
+ {
+ Console.Write("{\"" + x.String_thing + "\", " + x.Byte_thing + ", " + x.I32_thing + ", " + x.I32_thing + "}, ");
+ }
+ }
+ else
+ {
+ Console.Write("null");
+ }
+ Console.Write("}");
+
+ Console.Write("}, ");
+ }
+ Console.Write("}, ");
+ }
+ Console.WriteLine("}");
+
+
+ byte arg0 = 1;
+ int arg1 = 2;
+ long arg2 = long.MaxValue;
+ Dictionary<short, string> multiDict = new Dictionary<short, string>();
+ multiDict[1] = "one";
+ Numberz arg4 = Numberz.FIVE;
+ long arg5 = 5000000;
+ Console.Write("Test Multi(" + arg0 + "," + arg1 + "," + arg2 + "," + multiDict + "," + arg4 + "," + arg5 + ")");
+ Xtruct multiResponse = client.testMulti(arg0, arg1, arg2, multiDict, arg4, arg5);
+ Console.Write(" = Xtruct(byte_thing:" + multiResponse.Byte_thing + ",String_thing:" + multiResponse.String_thing
+ + ",i32_thing:" + multiResponse.I32_thing + ",i64_thing:" + multiResponse.I64_thing + ")\n");
+
+ Console.WriteLine("Test Async(1)");
+ client.testAsync(1);
+ }
+ }
+}
diff --git a/test/csharp/ThriftTest/TestServer.cs b/test/csharp/ThriftTest/TestServer.cs
new file mode 100644
index 0000000..4efe4b4
--- /dev/null
+++ b/test/csharp/ThriftTest/TestServer.cs
@@ -0,0 +1,327 @@
+// Distributed under the Thrift Software License
+//
+// See accompanying file LICENSE or visit the Thrift site at:
+// http://developers.facebook.com/thrift/
+using System;
+using System.Collections.Generic;
+using System.Text;
+using Thrift.Test; //generated code
+
+using Thrift.Transport;
+using Thrift.Protocol;
+using Thrift.Server;
+
+namespace Test
+{
+ public class TestServer
+ {
+ public class TestHandler : ThriftTest.Iface
+ {
+ public TServer server;
+
+ public TestHandler() { }
+
+ public void testVoid()
+ {
+ Console.WriteLine("testVoid()");
+ }
+
+ public string testString(string thing)
+ {
+ Console.WriteLine("teststring(\"" + thing + "\")");
+ return thing;
+ }
+
+ public byte testByte(byte thing)
+ {
+ Console.WriteLine("testByte(" + thing + ")");
+ return thing;
+ }
+
+ public int testI32(int thing)
+ {
+ Console.WriteLine("testI32(" + thing + ")");
+ return thing;
+ }
+
+ public long testI64(long thing)
+ {
+ Console.WriteLine("testI64(" + thing + ")");
+ return thing;
+ }
+
+ public double testDouble(double thing)
+ {
+ Console.WriteLine("testDouble(" + thing + ")");
+ return thing;
+ }
+
+ public Xtruct testStruct(Xtruct thing)
+ {
+ Console.WriteLine("testStruct({" +
+ "\"" + thing.String_thing + "\", " +
+ thing.Byte_thing + ", " +
+ thing.I32_thing + ", " +
+ thing.I64_thing + "})");
+ return thing;
+ }
+
+ public Xtruct2 testNest(Xtruct2 nest)
+ {
+ Xtruct thing = nest.Struct_thing;
+ Console.WriteLine("testNest({" +
+ nest.Byte_thing + ", {" +
+ "\"" + thing.String_thing + "\", " +
+ thing.Byte_thing + ", " +
+ thing.I32_thing + ", " +
+ thing.I64_thing + "}, " +
+ nest.I32_thing + "})");
+ return nest;
+ }
+
+ public Dictionary<int, int> testMap(Dictionary<int, int> thing)
+ {
+ Console.WriteLine("testMap({");
+ bool first = true;
+ foreach (int key in thing.Keys)
+ {
+ if (first)
+ {
+ first = false;
+ }
+ else
+ {
+ Console.WriteLine(", ");
+ }
+ Console.WriteLine(key + " => " + thing[key]);
+ }
+ Console.WriteLine("})");
+ return thing;
+ }
+
+ public HashSet<int> testSet(HashSet<int> thing)
+ {
+ Console.WriteLine("testSet({");
+ bool first = true;
+ foreach (int elem in thing)
+ {
+ if (first)
+ {
+ first = false;
+ }
+ else
+ {
+ Console.WriteLine(", ");
+ }
+ Console.WriteLine(elem);
+ }
+ Console.WriteLine("})");
+ return thing;
+ }
+
+ public List<int> testList(List<int> thing)
+ {
+ Console.WriteLine("testList({");
+ bool first = true;
+ foreach (int elem in thing)
+ {
+ if (first)
+ {
+ first = false;
+ }
+ else
+ {
+ Console.WriteLine(", ");
+ }
+ Console.WriteLine(elem);
+ }
+ Console.WriteLine("})");
+ return thing;
+ }
+
+ public Numberz testEnum(Numberz thing)
+ {
+ Console.WriteLine("testEnum(" + thing + ")");
+ return thing;
+ }
+
+ public long testTypedef(long thing)
+ {
+ Console.WriteLine("testTypedef(" + thing + ")");
+ return thing;
+ }
+
+ public Dictionary<int, Dictionary<int, int>> testMapMap(int hello)
+ {
+ Console.WriteLine("testMapMap(" + hello + ")");
+ Dictionary<int, Dictionary<int, int>> mapmap =
+ new Dictionary<int, Dictionary<int, int>>();
+
+ Dictionary<int, int> pos = new Dictionary<int, int>();
+ Dictionary<int, int> neg = new Dictionary<int, int>();
+ for (int i = 1; i < 5; i++)
+ {
+ pos[i] = i;
+ neg[-i] = -i;
+ }
+
+ mapmap[4] = pos;
+ mapmap[-4] = neg;
+
+ return mapmap;
+ }
+
+ public Dictionary<long, Dictionary<Numberz, Insanity>> testInsanity(Insanity argument)
+ {
+ Console.WriteLine("testInsanity()");
+
+ Xtruct hello = new Xtruct();
+ hello.String_thing = "Hello2";
+ hello.Byte_thing = 2;
+ hello.I32_thing = 2;
+ hello.I64_thing = 2;
+
+ Xtruct goodbye = new Xtruct();
+ goodbye.String_thing = "Goodbye4";
+ goodbye.Byte_thing = (byte)4;
+ goodbye.I32_thing = 4;
+ goodbye.I64_thing = (long)4;
+
+ Insanity crazy = new Insanity();
+ crazy.UserMap = new Dictionary<Numberz, long>();
+ crazy.UserMap[Numberz.EIGHT] = (long)8;
+ crazy.Xtructs = new List<Xtruct>();
+ crazy.Xtructs.Add(goodbye);
+
+ Insanity looney = new Insanity();
+ crazy.UserMap[Numberz.FIVE] = (long)5;
+ crazy.Xtructs.Add(hello);
+
+ Dictionary<Numberz, Insanity> first_map = new Dictionary<Numberz, Insanity>();
+ Dictionary<Numberz, Insanity> second_map = new Dictionary<Numberz, Insanity>(); ;
+
+ first_map[Numberz.TWO] = crazy;
+ first_map[Numberz.THREE] = crazy;
+
+ second_map[Numberz.SIX] = looney;
+
+ Dictionary<long, Dictionary<Numberz, Insanity>> insane =
+ new Dictionary<long, Dictionary<Numberz, Insanity>>();
+ insane[(long)1] = first_map;
+ insane[(long)2] = second_map;
+
+ return insane;
+ }
+
+ public Xtruct testMulti(byte arg0, int arg1, long arg2, Dictionary<short, string> arg3, Numberz arg4, long arg5)
+ {
+ Console.WriteLine("testMulti()");
+
+ Xtruct hello = new Xtruct(); ;
+ hello.String_thing = "Hello2";
+ hello.Byte_thing = arg0;
+ hello.I32_thing = arg1;
+ hello.I64_thing = arg2;
+ return hello;
+ }
+
+ public void testException(string arg)
+ {
+ Console.WriteLine("testException(" + arg + ")");
+ if (arg == "Xception")
+ {
+ Xception x = new Xception();
+ x.ErrorCode = 1001;
+ x.Message = "This is an Xception";
+ throw x;
+ }
+ return;
+ }
+
+ public Xtruct testMultiException(string arg0, string arg1)
+ {
+ Console.WriteLine("testMultiException(" + arg0 + ", " + arg1 + ")");
+ if (arg0 == "Xception")
+ {
+ Xception x = new Xception();
+ x.ErrorCode = 1001;
+ x.Message = "This is an Xception";
+ throw x;
+ }
+ else if (arg0 == "Xception2")
+ {
+ Xception2 x = new Xception2();
+ x.ErrorCode = 2002;
+ x.Struct_thing = new Xtruct();
+ x.Struct_thing.String_thing = "This is an Xception2";
+ throw x;
+ }
+
+ Xtruct result = new Xtruct();
+ result.String_thing = arg1;
+ return result;
+ }
+
+ public void testStop()
+ {
+ if (server != null)
+ {
+ server.Stop();
+ }
+ }
+
+ public void testAsync(int arg)
+ {
+ Console.WriteLine("testAsync(" + arg + "), sleeping...");
+ System.Threading.Thread.Sleep(arg * 1000);
+ Console.WriteLine("testAsync finished");
+ }
+
+ } // class TestHandler
+
+ public static void Execute(string[] args)
+ {
+ try
+ {
+ bool useBufferedSockets = false;
+ int port = 9090;
+ if (args.Length > 0)
+ {
+ port = int.Parse(args[0]);
+
+ if (args.Length > 1)
+ {
+ bool.TryParse(args[1], out useBufferedSockets);
+ }
+ }
+
+ // Processor
+ TestHandler testHandler = new TestHandler();
+ ThriftTest.Processor testProcessor = new ThriftTest.Processor(testHandler);
+
+ // Transport
+ TServerSocket tServerSocket = new TServerSocket(port, 0, useBufferedSockets);
+
+ TServer serverEngine;
+
+ // Simple Server
+ // serverEngine = new TSimpleServer(testProcessor, tServerSocket);
+
+ // ThreadPool Server
+ serverEngine = new TThreadPoolServer(testProcessor, tServerSocket);
+
+ testHandler.server = serverEngine;
+
+ // Run it
+ Console.WriteLine("Starting the server on port " + port + (useBufferedSockets ? " with buffered socket" : "") + "...");
+ serverEngine.Serve();
+
+ }
+ catch (Exception x)
+ {
+ Console.Error.Write(x);
+ }
+ Console.WriteLine("done.");
+ }
+ }
+}
diff --git a/test/csharp/ThriftTest/ThriftTest.csproj b/test/csharp/ThriftTest/ThriftTest.csproj
new file mode 100644
index 0000000..8e61173
--- /dev/null
+++ b/test/csharp/ThriftTest/ThriftTest.csproj
@@ -0,0 +1,122 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="3.5" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+ <PropertyGroup>
+ <Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
+ <Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
+ <ProductVersion>9.0.21022</ProductVersion>
+ <SchemaVersion>2.0</SchemaVersion>
+ <ProjectGuid>{48DD757F-CA95-4DD7-BDA4-58DB6F108C2C}</ProjectGuid>
+ <OutputType>Exe</OutputType>
+ <AppDesignerFolder>Properties</AppDesignerFolder>
+ <RootNamespace>ThriftTest</RootNamespace>
+ <AssemblyName>ThriftTest</AssemblyName>
+ <TargetFrameworkVersion>v3.5</TargetFrameworkVersion>
+ <FileAlignment>512</FileAlignment>
+ <PublishUrl>publish\</PublishUrl>
+ <Install>true</Install>
+ <InstallFrom>Disk</InstallFrom>
+ <UpdateEnabled>false</UpdateEnabled>
+ <UpdateMode>Foreground</UpdateMode>
+ <UpdateInterval>7</UpdateInterval>
+ <UpdateIntervalUnits>Days</UpdateIntervalUnits>
+ <UpdatePeriodically>false</UpdatePeriodically>
+ <UpdateRequired>false</UpdateRequired>
+ <MapFileExtensions>true</MapFileExtensions>
+ <ApplicationRevision>0</ApplicationRevision>
+ <ApplicationVersion>1.0.0.%2a</ApplicationVersion>
+ <IsWebBootstrapper>false</IsWebBootstrapper>
+ <UseApplicationTrust>false</UseApplicationTrust>
+ <BootstrapperEnabled>true</BootstrapperEnabled>
+ <SccProjectName>SAK</SccProjectName>
+ <SccLocalPath>SAK</SccLocalPath>
+ <SccAuxPath>SAK</SccAuxPath>
+ <SccProvider>SAK</SccProvider>
+ </PropertyGroup>
+ <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
+ <DebugSymbols>true</DebugSymbols>
+ <DebugType>full</DebugType>
+ <Optimize>false</Optimize>
+ <OutputPath>bin\Debug\</OutputPath>
+ <DefineConstants>DEBUG;TRACE</DefineConstants>
+ <ErrorReport>prompt</ErrorReport>
+ <WarningLevel>4</WarningLevel>
+ </PropertyGroup>
+ <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
+ <DebugType>pdbonly</DebugType>
+ <Optimize>true</Optimize>
+ <OutputPath>bin\Release\</OutputPath>
+ <DefineConstants>TRACE</DefineConstants>
+ <ErrorReport>prompt</ErrorReport>
+ <WarningLevel>4</WarningLevel>
+ </PropertyGroup>
+ <ItemGroup>
+ <Reference Include="System" />
+ <Reference Include="System.Core">
+ <RequiredTargetFramework>3.5</RequiredTargetFramework>
+ </Reference>
+ <Reference Include="System.Xml.Linq">
+ <RequiredTargetFramework>3.5</RequiredTargetFramework>
+ </Reference>
+ <Reference Include="System.Data.DataSetExtensions">
+ <RequiredTargetFramework>3.5</RequiredTargetFramework>
+ </Reference>
+ <Reference Include="System.Data" />
+ <Reference Include="System.Xml" />
+ <Reference Include="ThriftImpl, Version=0.0.0.0, Culture=neutral, processorArchitecture=MSIL">
+ <SpecificVersion>False</SpecificVersion>
+ <HintPath>.\ThriftImpl.dll</HintPath>
+ </Reference>
+ </ItemGroup>
+ <ItemGroup>
+ <Compile Include="Program.cs" />
+ <Compile Include="Properties\AssemblyInfo.cs" />
+ <Compile Include="TestClient.cs" />
+ <Compile Include="TestServer.cs" />
+ </ItemGroup>
+ <ItemGroup>
+ <BootstrapperPackage Include="Microsoft.Net.Framework.2.0">
+ <Visible>False</Visible>
+ <ProductName>.NET Framework 2.0 %28x86%29</ProductName>
+ <Install>false</Install>
+ </BootstrapperPackage>
+ <BootstrapperPackage Include="Microsoft.Net.Framework.3.0">
+ <Visible>False</Visible>
+ <ProductName>.NET Framework 3.0 %28x86%29</ProductName>
+ <Install>false</Install>
+ </BootstrapperPackage>
+ <BootstrapperPackage Include="Microsoft.Net.Framework.3.5">
+ <Visible>False</Visible>
+ <ProductName>.NET Framework 3.5</ProductName>
+ <Install>true</Install>
+ </BootstrapperPackage>
+ <BootstrapperPackage Include="Microsoft.Windows.Installer.3.1">
+ <Visible>False</Visible>
+ <ProductName>Windows Installer 3.1</ProductName>
+ <Install>true</Install>
+ </BootstrapperPackage>
+ </ItemGroup>
+ <ItemGroup>
+ <ProjectReference Include="..\..\..\lib\csharp\src\Thrift.csproj">
+ <Project>{499EB63C-D74C-47E8-AE48-A2FC94538E9D}</Project>
+ <Name>Thrift</Name>
+ </ProjectReference>
+ </ItemGroup>
+ <Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
+ <!-- To modify your build process, add your task inside one of the targets below and uncomment it.
+ Other similar extension points exist, see Microsoft.Common.targets.
+ <Target Name="BeforeBuild">
+ </Target>
+ <Target Name="AfterBuild">
+ </Target>
+ -->
+ <PropertyGroup>
+ <PreBuildEvent>rmdir /s /q $(ProjectDir)gen-csharp
+del /f /q $(ProjectDir)ThriftImpl.dll
+
+$(ProjectDir)\..\..\..\compiler\cpp\thrift.exe -csharp -o $(ProjectDir) $(ProjectDir)\..\..\ThriftTest.thrift
+
+cd $(ProjectDir)
+
+C:\Windows\Microsoft.NET\Framework\v3.5\Csc.exe /t:library /out:.\ThriftImpl.dll /recurse:.\gen-csharp\* /reference:$(ProjectDir)..\..\..\lib\csharp\src\bin\Debug\Thrift.dll</PreBuildEvent>
+ </PropertyGroup>
+</Project>