aboutsummaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
-rw-r--r--examples/csharp/HelloworldXamarin/.gitignore41
-rw-r--r--examples/csharp/HelloworldXamarin/Droid/Assets/AboutAssets.txt19
-rw-r--r--examples/csharp/HelloworldXamarin/Droid/HelloworldXamarin.Droid.csproj83
-rw-r--r--examples/csharp/HelloworldXamarin/Droid/MainActivity.cs84
-rw-r--r--examples/csharp/HelloworldXamarin/Droid/Properties/AndroidManifest.xml6
-rw-r--r--examples/csharp/HelloworldXamarin/Droid/Properties/AssemblyInfo.cs45
-rw-r--r--examples/csharp/HelloworldXamarin/Droid/Resources/AboutResources.txt44
-rw-r--r--examples/csharp/HelloworldXamarin/Droid/Resources/Resource.designer.cs112
-rw-r--r--examples/csharp/HelloworldXamarin/Droid/Resources/layout/Main.axml4
-rw-r--r--examples/csharp/HelloworldXamarin/Droid/Resources/mipmap-hdpi/Icon.pngbin0 -> 2201 bytes
-rw-r--r--examples/csharp/HelloworldXamarin/Droid/Resources/mipmap-mdpi/Icon.pngbin0 -> 1410 bytes
-rw-r--r--examples/csharp/HelloworldXamarin/Droid/Resources/mipmap-xhdpi/Icon.pngbin0 -> 3237 bytes
-rw-r--r--examples/csharp/HelloworldXamarin/Droid/Resources/mipmap-xxhdpi/Icon.pngbin0 -> 5414 bytes
-rw-r--r--examples/csharp/HelloworldXamarin/Droid/Resources/mipmap-xxxhdpi/Icon.pngbin0 -> 7825 bytes
-rw-r--r--examples/csharp/HelloworldXamarin/Droid/Resources/values/Strings.xml5
-rw-r--r--examples/csharp/HelloworldXamarin/Droid/packages.config54
-rw-r--r--examples/csharp/HelloworldXamarin/HelloworldXamarin.sln45
-rw-r--r--examples/csharp/HelloworldXamarin/HelloworldXamarin/Helloworld.cs286
-rw-r--r--examples/csharp/HelloworldXamarin/HelloworldXamarin/HelloworldGrpc.cs150
-rw-r--r--examples/csharp/HelloworldXamarin/HelloworldXamarin/HelloworldXamarin.projitems15
-rw-r--r--examples/csharp/HelloworldXamarin/HelloworldXamarin/HelloworldXamarin.shproj11
-rw-r--r--examples/csharp/HelloworldXamarin/README.md35
-rw-r--r--examples/csharp/HelloworldXamarin/iOS/AppDelegate.cs77
-rw-r--r--examples/csharp/HelloworldXamarin/iOS/Assets.xcassets/AppIcon.appiconset/Contents.json202
-rw-r--r--examples/csharp/HelloworldXamarin/iOS/Assets.xcassets/Contents.json6
-rw-r--r--examples/csharp/HelloworldXamarin/iOS/Entitlements.plist6
-rw-r--r--examples/csharp/HelloworldXamarin/iOS/HelloworldXamarin.iOS.csproj126
-rw-r--r--examples/csharp/HelloworldXamarin/iOS/Info.plist48
-rw-r--r--examples/csharp/HelloworldXamarin/iOS/LaunchScreen.storyboard27
-rw-r--r--examples/csharp/HelloworldXamarin/iOS/Main.cs38
-rw-r--r--examples/csharp/HelloworldXamarin/iOS/Main.storyboard40
-rw-r--r--examples/csharp/HelloworldXamarin/iOS/ViewController.cs91
-rw-r--r--examples/csharp/HelloworldXamarin/iOS/ViewController.designer.cs25
-rw-r--r--examples/csharp/HelloworldXamarin/iOS/packages.config54
-rw-r--r--src/csharp/README.md8
-rw-r--r--src/csharp/experimental/README.md26
-rwxr-xr-xtools/distrib/check_copyright.py4
37 files changed, 1807 insertions, 10 deletions
diff --git a/examples/csharp/HelloworldXamarin/.gitignore b/examples/csharp/HelloworldXamarin/.gitignore
new file mode 100644
index 0000000000..bf793edcc6
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/.gitignore
@@ -0,0 +1,41 @@
+# Autosave files
+*~
+
+# build
+[Oo]bj/
+[Bb]in/
+packages/
+TestResults/
+
+# globs
+Makefile.in
+*.DS_Store
+*.sln.cache
+*.suo
+*.cache
+*.pidb
+*.userprefs
+*.usertasks
+config.log
+config.make
+config.status
+aclocal.m4
+install-sh
+autom4te.cache/
+*.user
+*.tar.gz
+tarballs/
+test-results/
+Thumbs.db
+.vs/
+
+# Mac bundle stuff
+*.dmg
+*.app
+
+# resharper
+*_Resharper.*
+*.Resharper
+
+# dotCover
+*.dotCover
diff --git a/examples/csharp/HelloworldXamarin/Droid/Assets/AboutAssets.txt b/examples/csharp/HelloworldXamarin/Droid/Assets/AboutAssets.txt
new file mode 100644
index 0000000000..a9b0638eb1
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/Droid/Assets/AboutAssets.txt
@@ -0,0 +1,19 @@
+Any raw assets you want to be deployed with your application can be placed in
+this directory (and child directories) and given a Build Action of "AndroidAsset".
+
+These files will be deployed with your package and will be accessible using Android's
+AssetManager, like this:
+
+public class ReadAsset : Activity
+{
+ protected override void OnCreate (Bundle bundle)
+ {
+ base.OnCreate (bundle);
+
+ InputStream input = Assets.Open ("my_asset.txt");
+ }
+}
+
+Additionally, some Android functions will automatically load asset files:
+
+Typeface tf = Typeface.CreateFromAsset (Context.Assets, "fonts/samplefont.ttf");
diff --git a/examples/csharp/HelloworldXamarin/Droid/HelloworldXamarin.Droid.csproj b/examples/csharp/HelloworldXamarin/Droid/HelloworldXamarin.Droid.csproj
new file mode 100644
index 0000000000..b5ca8490a4
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/Droid/HelloworldXamarin.Droid.csproj
@@ -0,0 +1,83 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+ <PropertyGroup>
+ <Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
+ <Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
+ <ProjectGuid>{B9B0D41C-1C07-4590-A919-5865E741B2EA}</ProjectGuid>
+ <ProjectTypeGuids>{EFBA0AD7-5A72-4C68-AF49-83D382785DCF};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}</ProjectTypeGuids>
+ <OutputType>Library</OutputType>
+ <RootNamespace>HelloworldXamarin.Droid</RootNamespace>
+ <AssemblyName>HelloworldXamarin.Droid</AssemblyName>
+ <TargetFrameworkVersion>v8.1</TargetFrameworkVersion>
+ <AndroidApplication>True</AndroidApplication>
+ <AndroidResgenFile>Resources\Resource.designer.cs</AndroidResgenFile>
+ <AndroidResgenClass>Resource</AndroidResgenClass>
+ <AndroidManifest>Properties\AndroidManifest.xml</AndroidManifest>
+ <MonoAndroidResourcePrefix>Resources</MonoAndroidResourcePrefix>
+ <MonoAndroidAssetsPrefix>Assets</MonoAndroidAssetsPrefix>
+ <AndroidUseLatestPlatformSdk>true</AndroidUseLatestPlatformSdk>
+ </PropertyGroup>
+ <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
+ <DebugSymbols>true</DebugSymbols>
+ <DebugType>full</DebugType>
+ <Optimize>false</Optimize>
+ <OutputPath>bin\Debug</OutputPath>
+ <DefineConstants>DEBUG;</DefineConstants>
+ <ErrorReport>prompt</ErrorReport>
+ <WarningLevel>4</WarningLevel>
+ <AndroidLinkMode>None</AndroidLinkMode>
+ </PropertyGroup>
+ <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
+ <DebugSymbols>true</DebugSymbols>
+ <DebugType>pdbonly</DebugType>
+ <Optimize>true</Optimize>
+ <OutputPath>bin\Release</OutputPath>
+ <ErrorReport>prompt</ErrorReport>
+ <WarningLevel>4</WarningLevel>
+ <AndroidManagedSymbols>true</AndroidManagedSymbols>
+ <AndroidUseSharedRuntime>false</AndroidUseSharedRuntime>
+ </PropertyGroup>
+ <ItemGroup>
+ <Reference Include="System" />
+ <Reference Include="System.Xml" />
+ <Reference Include="System.Core" />
+ <Reference Include="Mono.Android" />
+ <Reference Include="System.IO.Compression" />
+ <Reference Include="System.Net.Http" />
+ <Reference Include="System.Runtime.Loader">
+ <HintPath>..\packages\System.Runtime.Loader.4.0.0\lib\netstandard1.5\System.Runtime.Loader.dll</HintPath>
+ </Reference>
+ <Reference Include="System.Interactive.Async">
+ <HintPath>..\packages\System.Interactive.Async.3.1.1\lib\netstandard1.3\System.Interactive.Async.dll</HintPath>
+ </Reference>
+ <Reference Include="Grpc.Core">
+ <HintPath>..\packages\Grpc.Core.1.15.0-dev\lib\netstandard1.5\Grpc.Core.dll</HintPath>
+ </Reference>
+ <Reference Include="Google.Protobuf">
+ <HintPath>..\packages\Google.Protobuf.3.6.0\lib\netstandard1.0\Google.Protobuf.dll</HintPath>
+ </Reference>
+ </ItemGroup>
+ <ItemGroup>
+ <Compile Include="MainActivity.cs" />
+ <Compile Include="Resources\Resource.designer.cs" />
+ <Compile Include="Properties\AssemblyInfo.cs" />
+ </ItemGroup>
+ <ItemGroup>
+ <None Include="Resources\AboutResources.txt" />
+ <None Include="Properties\AndroidManifest.xml" />
+ <None Include="Assets\AboutAssets.txt" />
+ <None Include="packages.config" />
+ </ItemGroup>
+ <ItemGroup>
+ <AndroidResource Include="Resources\layout\Main.axml" />
+ <AndroidResource Include="Resources\values\Strings.xml" />
+ <AndroidResource Include="Resources\mipmap-hdpi\Icon.png" />
+ <AndroidResource Include="Resources\mipmap-mdpi\Icon.png" />
+ <AndroidResource Include="Resources\mipmap-xhdpi\Icon.png" />
+ <AndroidResource Include="Resources\mipmap-xxhdpi\Icon.png" />
+ <AndroidResource Include="Resources\mipmap-xxxhdpi\Icon.png" />
+ </ItemGroup>
+ <Import Project="..\HelloworldXamarin\HelloworldXamarin.projitems" Label="Shared" Condition="Exists('..\HelloworldXamarin\HelloworldXamarin.projitems')" />
+ <Import Project="$(MSBuildExtensionsPath)\Xamarin\Android\Xamarin.Android.CSharp.targets" />
+ <Import Project="..\packages\Grpc.Core.1.15.0-dev\build\MonoAndroid\Grpc.Core.targets" Condition="Exists('..\packages\Grpc.Core.1.15.0-dev\build\MonoAndroid\Grpc.Core.targets')" />
+</Project> \ No newline at end of file
diff --git a/examples/csharp/HelloworldXamarin/Droid/MainActivity.cs b/examples/csharp/HelloworldXamarin/Droid/MainActivity.cs
new file mode 100644
index 0000000000..353943ced6
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/Droid/MainActivity.cs
@@ -0,0 +1,84 @@
+#region Copyright notice and license
+
+// Copyright 2018 The gRPC Authors
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#endregion
+
+using Android.App;
+using Android.Widget;
+using Android.OS;
+using System.Threading.Tasks;
+using Grpc.Core;
+using Helloworld;
+
+namespace HelloworldXamarin.Droid
+{
+ [Activity(Label = "HelloworldXamarin", MainLauncher = true, Icon = "@mipmap/icon")]
+ public class MainActivity : Activity
+ {
+ const int Port = 50051;
+ int count = 1;
+
+ protected override void OnCreate(Bundle savedInstanceState)
+ {
+ base.OnCreate(savedInstanceState);
+
+ // Set our view from the "main" layout resource
+ SetContentView(Resource.Layout.Main);
+
+ // Get our button from the layout resource,
+ // and attach an event to it
+ Button button = FindViewById<Button>(Resource.Id.myButton);
+
+ button.Click += delegate { SayHello(button); };
+ }
+
+ private void SayHello(Button button)
+ {
+ Server server = new Server
+ {
+ Services = { Greeter.BindService(new GreeterImpl()) },
+ Ports = { new ServerPort("localhost", Port, ServerCredentials.Insecure) }
+ };
+ server.Start();
+
+ // use loopback on host machine: https://developer.android.com/studio/run/emulator-networking
+ //10.0.2.2:50051
+ Channel channel = new Channel("localhost:50051", ChannelCredentials.Insecure);
+
+ var client = new Greeter.GreeterClient(channel);
+ string user = "Xamarin " + count;
+
+ var reply = client.SayHello(new HelloRequest { Name = user });
+
+ button.Text = "Greeting: " + reply.Message;
+
+ channel.ShutdownAsync().Wait();
+ server.ShutdownAsync().Wait();
+
+ count++;
+ }
+
+ class GreeterImpl : Greeter.GreeterBase
+ {
+ // Server side handler of the SayHello RPC
+ public override Task<HelloReply> SayHello(HelloRequest request, ServerCallContext context)
+ {
+ return Task.FromResult(new HelloReply { Message = "Hello " + request.Name });
+ }
+ }
+ }
+}
+
diff --git a/examples/csharp/HelloworldXamarin/Droid/Properties/AndroidManifest.xml b/examples/csharp/HelloworldXamarin/Droid/Properties/AndroidManifest.xml
new file mode 100644
index 0000000000..4f2167a1a0
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/Droid/Properties/AndroidManifest.xml
@@ -0,0 +1,6 @@
+<?xml version="1.0" encoding="utf-8"?>
+<manifest xmlns:android="http://schemas.android.com/apk/res/android" android:versionCode="1" android:versionName="1.0" package="io.grpc.examples.HelloworldXamarin">
+ <uses-sdk android:minSdkVersion="15" />
+ <application android:label="HelloworldXamarin">
+ </application>
+</manifest>
diff --git a/examples/csharp/HelloworldXamarin/Droid/Properties/AssemblyInfo.cs b/examples/csharp/HelloworldXamarin/Droid/Properties/AssemblyInfo.cs
new file mode 100644
index 0000000000..5a479659da
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/Droid/Properties/AssemblyInfo.cs
@@ -0,0 +1,45 @@
+#region Copyright notice and license
+
+// Copyright 2018 The gRPC Authors
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#endregion
+
+using System.Reflection;
+using System.Runtime.CompilerServices;
+using Android.App;
+
+// Information about this assembly is defined by the following attributes.
+// Change them to the values specific to your project.
+
+[assembly: AssemblyTitle("HelloworldXamarin.Droid")]
+[assembly: AssemblyDescription("")]
+[assembly: AssemblyConfiguration("")]
+[assembly: AssemblyCompany("")]
+[assembly: AssemblyProduct("")]
+[assembly: AssemblyCopyright("${AuthorCopyright}")]
+[assembly: AssemblyTrademark("")]
+[assembly: AssemblyCulture("")]
+
+// The assembly version has the format "{Major}.{Minor}.{Build}.{Revision}".
+// The form "{Major}.{Minor}.*" will automatically update the build and revision,
+// and "{Major}.{Minor}.{Build}.*" will update just the revision.
+
+[assembly: AssemblyVersion("1.0.0")]
+
+// The following attributes are used to specify the signing key for the assembly,
+// if desired. See the Mono documentation for more information about signing.
+
+//[assembly: AssemblyDelaySign(false)]
+//[assembly: AssemblyKeyFile("")]
diff --git a/examples/csharp/HelloworldXamarin/Droid/Resources/AboutResources.txt b/examples/csharp/HelloworldXamarin/Droid/Resources/AboutResources.txt
new file mode 100644
index 0000000000..10f52d4602
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/Droid/Resources/AboutResources.txt
@@ -0,0 +1,44 @@
+Images, layout descriptions, binary blobs and string dictionaries can be included
+in your application as resource files. Various Android APIs are designed to
+operate on the resource IDs instead of dealing with images, strings or binary blobs
+directly.
+
+For example, a sample Android app that contains a user interface layout (main.axml),
+an internationalization string table (strings.xml) and some icons (drawable-XXX/icon.png)
+would keep its resources in the "Resources" directory of the application:
+
+Resources/
+ drawable/
+ icon.png
+
+ layout/
+ main.axml
+
+ values/
+ strings.xml
+
+In order to get the build system to recognize Android resources, set the build action to
+"AndroidResource". The native Android APIs do not operate directly with filenames, but
+instead operate on resource IDs. When you compile an Android application that uses resources,
+the build system will package the resources for distribution and generate a class called "R"
+(this is an Android convention) that contains the tokens for each one of the resources
+included. For example, for the above Resources layout, this is what the R class would expose:
+
+public class R {
+ public class drawable {
+ public const int icon = 0x123;
+ }
+
+ public class layout {
+ public const int main = 0x456;
+ }
+
+ public class strings {
+ public const int first_string = 0xabc;
+ public const int second_string = 0xbcd;
+ }
+}
+
+You would then use R.drawable.icon to reference the drawable/icon.png file, or R.layout.main
+to reference the layout/main.axml file, or R.strings.first_string to reference the first
+string in the dictionary file values/strings.xml.
diff --git a/examples/csharp/HelloworldXamarin/Droid/Resources/Resource.designer.cs b/examples/csharp/HelloworldXamarin/Droid/Resources/Resource.designer.cs
new file mode 100644
index 0000000000..0b8a27d3dd
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/Droid/Resources/Resource.designer.cs
@@ -0,0 +1,112 @@
+#pragma warning disable 1591
+//------------------------------------------------------------------------------
+// <auto-generated>
+// This code was generated by a tool.
+// Runtime Version:4.0.30319.42000
+//
+// Changes to this file may cause incorrect behavior and will be lost if
+// the code is regenerated.
+// </auto-generated>
+//------------------------------------------------------------------------------
+
+[assembly: global::Android.Runtime.ResourceDesignerAttribute("HelloworldXamarin.Droid.Resource", IsApplication=true)]
+
+namespace HelloworldXamarin.Droid
+{
+
+
+ [System.CodeDom.Compiler.GeneratedCodeAttribute("Xamarin.Android.Build.Tasks", "1.0.0.0")]
+ public partial class Resource
+ {
+
+ static Resource()
+ {
+ global::Android.Runtime.ResourceIdManager.UpdateIdValues();
+ }
+
+ public static void UpdateIdValues()
+ {
+ }
+
+ public partial class Attribute
+ {
+
+ static Attribute()
+ {
+ global::Android.Runtime.ResourceIdManager.UpdateIdValues();
+ }
+
+ private Attribute()
+ {
+ }
+ }
+
+ public partial class Id
+ {
+
+ // aapt resource value: 0x7f050000
+ public const int myButton = 2131034112;
+
+ static Id()
+ {
+ global::Android.Runtime.ResourceIdManager.UpdateIdValues();
+ }
+
+ private Id()
+ {
+ }
+ }
+
+ public partial class Layout
+ {
+
+ // aapt resource value: 0x7f030000
+ public const int Main = 2130903040;
+
+ static Layout()
+ {
+ global::Android.Runtime.ResourceIdManager.UpdateIdValues();
+ }
+
+ private Layout()
+ {
+ }
+ }
+
+ public partial class Mipmap
+ {
+
+ // aapt resource value: 0x7f020000
+ public const int Icon = 2130837504;
+
+ static Mipmap()
+ {
+ global::Android.Runtime.ResourceIdManager.UpdateIdValues();
+ }
+
+ private Mipmap()
+ {
+ }
+ }
+
+ public partial class String
+ {
+
+ // aapt resource value: 0x7f040001
+ public const int app_name = 2130968577;
+
+ // aapt resource value: 0x7f040000
+ public const int hello = 2130968576;
+
+ static String()
+ {
+ global::Android.Runtime.ResourceIdManager.UpdateIdValues();
+ }
+
+ private String()
+ {
+ }
+ }
+ }
+}
+#pragma warning restore 1591
diff --git a/examples/csharp/HelloworldXamarin/Droid/Resources/layout/Main.axml b/examples/csharp/HelloworldXamarin/Droid/Resources/layout/Main.axml
new file mode 100644
index 0000000000..8cb72282b9
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/Droid/Resources/layout/Main.axml
@@ -0,0 +1,4 @@
+<?xml version="1.0" encoding="utf-8"?>
+<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:orientation="vertical" android:layout_width="match_parent" android:layout_height="match_parent">
+ <Button android:id="@+id/myButton" android:layout_width="match_parent" android:layout_height="wrap_content" android:text="@string/hello" />
+</LinearLayout>
diff --git a/examples/csharp/HelloworldXamarin/Droid/Resources/mipmap-hdpi/Icon.png b/examples/csharp/HelloworldXamarin/Droid/Resources/mipmap-hdpi/Icon.png
new file mode 100644
index 0000000000..f4c804644c
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/Droid/Resources/mipmap-hdpi/Icon.png
Binary files differ
diff --git a/examples/csharp/HelloworldXamarin/Droid/Resources/mipmap-mdpi/Icon.png b/examples/csharp/HelloworldXamarin/Droid/Resources/mipmap-mdpi/Icon.png
new file mode 100644
index 0000000000..ef1e1ee7dc
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/Droid/Resources/mipmap-mdpi/Icon.png
Binary files differ
diff --git a/examples/csharp/HelloworldXamarin/Droid/Resources/mipmap-xhdpi/Icon.png b/examples/csharp/HelloworldXamarin/Droid/Resources/mipmap-xhdpi/Icon.png
new file mode 100644
index 0000000000..b7e2e57aa9
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/Droid/Resources/mipmap-xhdpi/Icon.png
Binary files differ
diff --git a/examples/csharp/HelloworldXamarin/Droid/Resources/mipmap-xxhdpi/Icon.png b/examples/csharp/HelloworldXamarin/Droid/Resources/mipmap-xxhdpi/Icon.png
new file mode 100644
index 0000000000..8d20a38d17
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/Droid/Resources/mipmap-xxhdpi/Icon.png
Binary files differ
diff --git a/examples/csharp/HelloworldXamarin/Droid/Resources/mipmap-xxxhdpi/Icon.png b/examples/csharp/HelloworldXamarin/Droid/Resources/mipmap-xxxhdpi/Icon.png
new file mode 100644
index 0000000000..6d9919c41a
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/Droid/Resources/mipmap-xxxhdpi/Icon.png
Binary files differ
diff --git a/examples/csharp/HelloworldXamarin/Droid/Resources/values/Strings.xml b/examples/csharp/HelloworldXamarin/Droid/Resources/values/Strings.xml
new file mode 100644
index 0000000000..0a47c047e2
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/Droid/Resources/values/Strings.xml
@@ -0,0 +1,5 @@
+<?xml version="1.0" encoding="utf-8"?>
+<resources>
+ <string name="hello">Hello World, Click Me!</string>
+ <string name="app_name">HelloworldXamarin.Droid</string>
+</resources>
diff --git a/examples/csharp/HelloworldXamarin/Droid/packages.config b/examples/csharp/HelloworldXamarin/Droid/packages.config
new file mode 100644
index 0000000000..3574b6782b
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/Droid/packages.config
@@ -0,0 +1,54 @@
+<?xml version="1.0" encoding="utf-8"?>
+<packages>
+ <package id="Google.Protobuf" version="3.6.0" targetFramework="monoandroid81" />
+ <package id="Grpc.Core" version="1.15.0-dev" targetFramework="monoandroid81" />
+ <package id="Microsoft.NETCore.Platforms" version="1.1.0" targetFramework="monoandroid81" />
+ <package id="Microsoft.Win32.Primitives" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="NETStandard.Library" version="1.6.1" targetFramework="monoandroid81" />
+ <package id="System.AppContext" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Collections" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Collections.Concurrent" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Console" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Diagnostics.Debug" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Diagnostics.Tools" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Diagnostics.Tracing" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Globalization" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Globalization.Calendars" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Interactive.Async" version="3.1.1" targetFramework="monoandroid81" />
+ <package id="System.IO" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.IO.Compression" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.IO.Compression.ZipFile" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.IO.FileSystem" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.IO.FileSystem.Primitives" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Linq" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Linq.Expressions" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Net.Http" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Net.Primitives" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Net.Sockets" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.ObjectModel" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Reflection" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Reflection.Extensions" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Reflection.Primitives" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Resources.ResourceManager" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Runtime" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Runtime.Extensions" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Runtime.Handles" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Runtime.InteropServices" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Runtime.InteropServices.RuntimeInformation" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Runtime.Loader" version="4.0.0" targetFramework="monoandroid81" />
+ <package id="System.Runtime.Numerics" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Security.Cryptography.Algorithms" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Security.Cryptography.Encoding" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Security.Cryptography.Primitives" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Security.Cryptography.X509Certificates" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Text.Encoding" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Text.Encoding.Extensions" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Text.RegularExpressions" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Threading" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Threading.Tasks" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Threading.Thread" version="4.0.0" targetFramework="monoandroid81" />
+ <package id="System.Threading.ThreadPool" version="4.0.10" targetFramework="monoandroid81" />
+ <package id="System.Threading.Timer" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Xml.ReaderWriter" version="4.3.0" targetFramework="monoandroid81" />
+ <package id="System.Xml.XDocument" version="4.3.0" targetFramework="monoandroid81" />
+</packages> \ No newline at end of file
diff --git a/examples/csharp/HelloworldXamarin/HelloworldXamarin.sln b/examples/csharp/HelloworldXamarin/HelloworldXamarin.sln
new file mode 100644
index 0000000000..e2a738f157
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/HelloworldXamarin.sln
@@ -0,0 +1,45 @@
+
+Microsoft Visual Studio Solution File, Format Version 12.00
+# Visual Studio 2012
+Project("{D954291E-2A0B-460D-934E-DC6B0785DB48}") = "HelloworldXamarin", "HelloworldXamarin\HelloworldXamarin.shproj", "{42FFF3D8-934F-4475-8E68-08DA340BF6E8}"
+EndProject
+Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "HelloworldXamarin.Droid", "Droid\HelloworldXamarin.Droid.csproj", "{B9B0D41C-1C07-4590-A919-5865E741B2EA}"
+EndProject
+Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "HelloworldXamarin.iOS", "iOS\HelloworldXamarin.iOS.csproj", "{62336DF0-60D8-478F-8140-B3CB089B417E}"
+EndProject
+Global
+ GlobalSection(SolutionConfigurationPlatforms) = preSolution
+ Debug|Any CPU = Debug|Any CPU
+ Release|Any CPU = Release|Any CPU
+ Debug|iPhoneSimulator = Debug|iPhoneSimulator
+ Release|iPhone = Release|iPhone
+ Release|iPhoneSimulator = Release|iPhoneSimulator
+ Debug|iPhone = Debug|iPhone
+ EndGlobalSection
+ GlobalSection(ProjectConfigurationPlatforms) = postSolution
+ {B9B0D41C-1C07-4590-A919-5865E741B2EA}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {B9B0D41C-1C07-4590-A919-5865E741B2EA}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {B9B0D41C-1C07-4590-A919-5865E741B2EA}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {B9B0D41C-1C07-4590-A919-5865E741B2EA}.Release|Any CPU.Build.0 = Release|Any CPU
+ {B9B0D41C-1C07-4590-A919-5865E741B2EA}.Debug|iPhoneSimulator.ActiveCfg = Debug|Any CPU
+ {B9B0D41C-1C07-4590-A919-5865E741B2EA}.Debug|iPhoneSimulator.Build.0 = Debug|Any CPU
+ {B9B0D41C-1C07-4590-A919-5865E741B2EA}.Release|iPhone.ActiveCfg = Release|Any CPU
+ {B9B0D41C-1C07-4590-A919-5865E741B2EA}.Release|iPhone.Build.0 = Release|Any CPU
+ {B9B0D41C-1C07-4590-A919-5865E741B2EA}.Release|iPhoneSimulator.ActiveCfg = Release|Any CPU
+ {B9B0D41C-1C07-4590-A919-5865E741B2EA}.Release|iPhoneSimulator.Build.0 = Release|Any CPU
+ {B9B0D41C-1C07-4590-A919-5865E741B2EA}.Debug|iPhone.ActiveCfg = Debug|Any CPU
+ {B9B0D41C-1C07-4590-A919-5865E741B2EA}.Debug|iPhone.Build.0 = Debug|Any CPU
+ {62336DF0-60D8-478F-8140-B3CB089B417E}.Debug|Any CPU.ActiveCfg = Debug|iPhoneSimulator
+ {62336DF0-60D8-478F-8140-B3CB089B417E}.Debug|Any CPU.Build.0 = Debug|iPhoneSimulator
+ {62336DF0-60D8-478F-8140-B3CB089B417E}.Release|Any CPU.ActiveCfg = Release|iPhone
+ {62336DF0-60D8-478F-8140-B3CB089B417E}.Release|Any CPU.Build.0 = Release|iPhone
+ {62336DF0-60D8-478F-8140-B3CB089B417E}.Debug|iPhoneSimulator.ActiveCfg = Debug|iPhoneSimulator
+ {62336DF0-60D8-478F-8140-B3CB089B417E}.Debug|iPhoneSimulator.Build.0 = Debug|iPhoneSimulator
+ {62336DF0-60D8-478F-8140-B3CB089B417E}.Release|iPhone.ActiveCfg = Release|iPhone
+ {62336DF0-60D8-478F-8140-B3CB089B417E}.Release|iPhone.Build.0 = Release|iPhone
+ {62336DF0-60D8-478F-8140-B3CB089B417E}.Release|iPhoneSimulator.ActiveCfg = Release|iPhoneSimulator
+ {62336DF0-60D8-478F-8140-B3CB089B417E}.Release|iPhoneSimulator.Build.0 = Release|iPhoneSimulator
+ {62336DF0-60D8-478F-8140-B3CB089B417E}.Debug|iPhone.ActiveCfg = Debug|iPhone
+ {62336DF0-60D8-478F-8140-B3CB089B417E}.Debug|iPhone.Build.0 = Debug|iPhone
+ EndGlobalSection
+EndGlobal
diff --git a/examples/csharp/HelloworldXamarin/HelloworldXamarin/Helloworld.cs b/examples/csharp/HelloworldXamarin/HelloworldXamarin/Helloworld.cs
new file mode 100644
index 0000000000..ecfc8e131c
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/HelloworldXamarin/Helloworld.cs
@@ -0,0 +1,286 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: helloworld.proto
+#pragma warning disable 1591, 0612, 3021
+#region Designer generated code
+
+using pb = global::Google.Protobuf;
+using pbc = global::Google.Protobuf.Collections;
+using pbr = global::Google.Protobuf.Reflection;
+using scg = global::System.Collections.Generic;
+namespace Helloworld {
+
+ /// <summary>Holder for reflection information generated from helloworld.proto</summary>
+ public static partial class HelloworldReflection {
+
+ #region Descriptor
+ /// <summary>File descriptor for helloworld.proto</summary>
+ public static pbr::FileDescriptor Descriptor {
+ get { return descriptor; }
+ }
+ private static pbr::FileDescriptor descriptor;
+
+ static HelloworldReflection() {
+ byte[] descriptorData = global::System.Convert.FromBase64String(
+ string.Concat(
+ "ChBoZWxsb3dvcmxkLnByb3RvEgpoZWxsb3dvcmxkIhwKDEhlbGxvUmVxdWVz",
+ "dBIMCgRuYW1lGAEgASgJIh0KCkhlbGxvUmVwbHkSDwoHbWVzc2FnZRgBIAEo",
+ "CTJJCgdHcmVldGVyEj4KCFNheUhlbGxvEhguaGVsbG93b3JsZC5IZWxsb1Jl",
+ "cXVlc3QaFi5oZWxsb3dvcmxkLkhlbGxvUmVwbHkiAEI2Chtpby5ncnBjLmV4",
+ "YW1wbGVzLmhlbGxvd29ybGRCD0hlbGxvV29ybGRQcm90b1ABogIDSExXYgZw",
+ "cm90bzM="));
+ descriptor = pbr::FileDescriptor.FromGeneratedCode(descriptorData,
+ new pbr::FileDescriptor[] { },
+ new pbr::GeneratedClrTypeInfo(null, new pbr::GeneratedClrTypeInfo[] {
+ new pbr::GeneratedClrTypeInfo(typeof(global::Helloworld.HelloRequest), global::Helloworld.HelloRequest.Parser, new[]{ "Name" }, null, null, null),
+ new pbr::GeneratedClrTypeInfo(typeof(global::Helloworld.HelloReply), global::Helloworld.HelloReply.Parser, new[]{ "Message" }, null, null, null)
+ }));
+ }
+ #endregion
+
+ }
+ #region Messages
+ /// <summary>
+ /// The request message containing the user's name.
+ /// </summary>
+ public sealed partial class HelloRequest : pb::IMessage<HelloRequest> {
+ private static readonly pb::MessageParser<HelloRequest> _parser = new pb::MessageParser<HelloRequest>(() => new HelloRequest());
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public static pb::MessageParser<HelloRequest> Parser { get { return _parser; } }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public static pbr::MessageDescriptor Descriptor {
+ get { return global::Helloworld.HelloworldReflection.Descriptor.MessageTypes[0]; }
+ }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ pbr::MessageDescriptor pb::IMessage.Descriptor {
+ get { return Descriptor; }
+ }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public HelloRequest() {
+ OnConstruction();
+ }
+
+ partial void OnConstruction();
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public HelloRequest(HelloRequest other) : this() {
+ name_ = other.name_;
+ }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public HelloRequest Clone() {
+ return new HelloRequest(this);
+ }
+
+ /// <summary>Field number for the "name" field.</summary>
+ public const int NameFieldNumber = 1;
+ private string name_ = "";
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public string Name {
+ get { return name_; }
+ set {
+ name_ = pb::ProtoPreconditions.CheckNotNull(value, "value");
+ }
+ }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public override bool Equals(object other) {
+ return Equals(other as HelloRequest);
+ }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public bool Equals(HelloRequest other) {
+ if (ReferenceEquals(other, null)) {
+ return false;
+ }
+ if (ReferenceEquals(other, this)) {
+ return true;
+ }
+ if (Name != other.Name) return false;
+ return true;
+ }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public override int GetHashCode() {
+ int hash = 1;
+ if (Name.Length != 0) hash ^= Name.GetHashCode();
+ return hash;
+ }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public override string ToString() {
+ return pb::JsonFormatter.ToDiagnosticString(this);
+ }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public void WriteTo(pb::CodedOutputStream output) {
+ if (Name.Length != 0) {
+ output.WriteRawTag(10);
+ output.WriteString(Name);
+ }
+ }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public int CalculateSize() {
+ int size = 0;
+ if (Name.Length != 0) {
+ size += 1 + pb::CodedOutputStream.ComputeStringSize(Name);
+ }
+ return size;
+ }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public void MergeFrom(HelloRequest other) {
+ if (other == null) {
+ return;
+ }
+ if (other.Name.Length != 0) {
+ Name = other.Name;
+ }
+ }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public void MergeFrom(pb::CodedInputStream input) {
+ uint tag;
+ while ((tag = input.ReadTag()) != 0) {
+ switch(tag) {
+ default:
+ input.SkipLastField();
+ break;
+ case 10: {
+ Name = input.ReadString();
+ break;
+ }
+ }
+ }
+ }
+
+ }
+
+ /// <summary>
+ /// The response message containing the greetings
+ /// </summary>
+ public sealed partial class HelloReply : pb::IMessage<HelloReply> {
+ private static readonly pb::MessageParser<HelloReply> _parser = new pb::MessageParser<HelloReply>(() => new HelloReply());
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public static pb::MessageParser<HelloReply> Parser { get { return _parser; } }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public static pbr::MessageDescriptor Descriptor {
+ get { return global::Helloworld.HelloworldReflection.Descriptor.MessageTypes[1]; }
+ }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ pbr::MessageDescriptor pb::IMessage.Descriptor {
+ get { return Descriptor; }
+ }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public HelloReply() {
+ OnConstruction();
+ }
+
+ partial void OnConstruction();
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public HelloReply(HelloReply other) : this() {
+ message_ = other.message_;
+ }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public HelloReply Clone() {
+ return new HelloReply(this);
+ }
+
+ /// <summary>Field number for the "message" field.</summary>
+ public const int MessageFieldNumber = 1;
+ private string message_ = "";
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public string Message {
+ get { return message_; }
+ set {
+ message_ = pb::ProtoPreconditions.CheckNotNull(value, "value");
+ }
+ }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public override bool Equals(object other) {
+ return Equals(other as HelloReply);
+ }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public bool Equals(HelloReply other) {
+ if (ReferenceEquals(other, null)) {
+ return false;
+ }
+ if (ReferenceEquals(other, this)) {
+ return true;
+ }
+ if (Message != other.Message) return false;
+ return true;
+ }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public override int GetHashCode() {
+ int hash = 1;
+ if (Message.Length != 0) hash ^= Message.GetHashCode();
+ return hash;
+ }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public override string ToString() {
+ return pb::JsonFormatter.ToDiagnosticString(this);
+ }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public void WriteTo(pb::CodedOutputStream output) {
+ if (Message.Length != 0) {
+ output.WriteRawTag(10);
+ output.WriteString(Message);
+ }
+ }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public int CalculateSize() {
+ int size = 0;
+ if (Message.Length != 0) {
+ size += 1 + pb::CodedOutputStream.ComputeStringSize(Message);
+ }
+ return size;
+ }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public void MergeFrom(HelloReply other) {
+ if (other == null) {
+ return;
+ }
+ if (other.Message.Length != 0) {
+ Message = other.Message;
+ }
+ }
+
+ [global::System.Diagnostics.DebuggerNonUserCodeAttribute]
+ public void MergeFrom(pb::CodedInputStream input) {
+ uint tag;
+ while ((tag = input.ReadTag()) != 0) {
+ switch(tag) {
+ default:
+ input.SkipLastField();
+ break;
+ case 10: {
+ Message = input.ReadString();
+ break;
+ }
+ }
+ }
+ }
+
+ }
+
+ #endregion
+
+}
+
+#endregion Designer generated code
diff --git a/examples/csharp/HelloworldXamarin/HelloworldXamarin/HelloworldGrpc.cs b/examples/csharp/HelloworldXamarin/HelloworldXamarin/HelloworldGrpc.cs
new file mode 100644
index 0000000000..c808884e57
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/HelloworldXamarin/HelloworldGrpc.cs
@@ -0,0 +1,150 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: helloworld.proto
+// Original file comments:
+// Copyright 2015 gRPC authors.
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+#pragma warning disable 1591
+#region Designer generated code
+
+using System;
+using System.Threading;
+using System.Threading.Tasks;
+using grpc = global::Grpc.Core;
+
+namespace Helloworld {
+ /// <summary>
+ /// The greeting service definition.
+ /// </summary>
+ public static partial class Greeter
+ {
+ static readonly string __ServiceName = "helloworld.Greeter";
+
+ static readonly grpc::Marshaller<global::Helloworld.HelloRequest> __Marshaller_HelloRequest = grpc::Marshallers.Create((arg) => global::Google.Protobuf.MessageExtensions.ToByteArray(arg), global::Helloworld.HelloRequest.Parser.ParseFrom);
+ static readonly grpc::Marshaller<global::Helloworld.HelloReply> __Marshaller_HelloReply = grpc::Marshallers.Create((arg) => global::Google.Protobuf.MessageExtensions.ToByteArray(arg), global::Helloworld.HelloReply.Parser.ParseFrom);
+
+ static readonly grpc::Method<global::Helloworld.HelloRequest, global::Helloworld.HelloReply> __Method_SayHello = new grpc::Method<global::Helloworld.HelloRequest, global::Helloworld.HelloReply>(
+ grpc::MethodType.Unary,
+ __ServiceName,
+ "SayHello",
+ __Marshaller_HelloRequest,
+ __Marshaller_HelloReply);
+
+ /// <summary>Service descriptor</summary>
+ public static global::Google.Protobuf.Reflection.ServiceDescriptor Descriptor
+ {
+ get { return global::Helloworld.HelloworldReflection.Descriptor.Services[0]; }
+ }
+
+ /// <summary>Base class for server-side implementations of Greeter</summary>
+ public abstract partial class GreeterBase
+ {
+ /// <summary>
+ /// Sends a greeting
+ /// </summary>
+ /// <param name="request">The request received from the client.</param>
+ /// <param name="context">The context of the server-side call handler being invoked.</param>
+ /// <returns>The response to send back to the client (wrapped by a task).</returns>
+ public virtual global::System.Threading.Tasks.Task<global::Helloworld.HelloReply> SayHello(global::Helloworld.HelloRequest request, grpc::ServerCallContext context)
+ {
+ throw new grpc::RpcException(new grpc::Status(grpc::StatusCode.Unimplemented, ""));
+ }
+
+ }
+
+ /// <summary>Client for Greeter</summary>
+ public partial class GreeterClient : grpc::ClientBase<GreeterClient>
+ {
+ /// <summary>Creates a new client for Greeter</summary>
+ /// <param name="channel">The channel to use to make remote calls.</param>
+ public GreeterClient(grpc::Channel channel) : base(channel)
+ {
+ }
+ /// <summary>Creates a new client for Greeter that uses a custom <c>CallInvoker</c>.</summary>
+ /// <param name="callInvoker">The callInvoker to use to make remote calls.</param>
+ public GreeterClient(grpc::CallInvoker callInvoker) : base(callInvoker)
+ {
+ }
+ /// <summary>Protected parameterless constructor to allow creation of test doubles.</summary>
+ protected GreeterClient() : base()
+ {
+ }
+ /// <summary>Protected constructor to allow creation of configured clients.</summary>
+ /// <param name="configuration">The client configuration.</param>
+ protected GreeterClient(ClientBaseConfiguration configuration) : base(configuration)
+ {
+ }
+
+ /// <summary>
+ /// Sends a greeting
+ /// </summary>
+ /// <param name="request">The request to send to the server.</param>
+ /// <param name="headers">The initial metadata to send with the call. This parameter is optional.</param>
+ /// <param name="deadline">An optional deadline for the call. The call will be cancelled if deadline is hit.</param>
+ /// <param name="cancellationToken">An optional token for canceling the call.</param>
+ /// <returns>The response received from the server.</returns>
+ public virtual global::Helloworld.HelloReply SayHello(global::Helloworld.HelloRequest request, grpc::Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken))
+ {
+ return SayHello(request, new grpc::CallOptions(headers, deadline, cancellationToken));
+ }
+ /// <summary>
+ /// Sends a greeting
+ /// </summary>
+ /// <param name="request">The request to send to the server.</param>
+ /// <param name="options">The options for the call.</param>
+ /// <returns>The response received from the server.</returns>
+ public virtual global::Helloworld.HelloReply SayHello(global::Helloworld.HelloRequest request, grpc::CallOptions options)
+ {
+ return CallInvoker.BlockingUnaryCall(__Method_SayHello, null, options, request);
+ }
+ /// <summary>
+ /// Sends a greeting
+ /// </summary>
+ /// <param name="request">The request to send to the server.</param>
+ /// <param name="headers">The initial metadata to send with the call. This parameter is optional.</param>
+ /// <param name="deadline">An optional deadline for the call. The call will be cancelled if deadline is hit.</param>
+ /// <param name="cancellationToken">An optional token for canceling the call.</param>
+ /// <returns>The call object.</returns>
+ public virtual grpc::AsyncUnaryCall<global::Helloworld.HelloReply> SayHelloAsync(global::Helloworld.HelloRequest request, grpc::Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken))
+ {
+ return SayHelloAsync(request, new grpc::CallOptions(headers, deadline, cancellationToken));
+ }
+ /// <summary>
+ /// Sends a greeting
+ /// </summary>
+ /// <param name="request">The request to send to the server.</param>
+ /// <param name="options">The options for the call.</param>
+ /// <returns>The call object.</returns>
+ public virtual grpc::AsyncUnaryCall<global::Helloworld.HelloReply> SayHelloAsync(global::Helloworld.HelloRequest request, grpc::CallOptions options)
+ {
+ return CallInvoker.AsyncUnaryCall(__Method_SayHello, null, options, request);
+ }
+ /// <summary>Creates a new instance of client from given <c>ClientBaseConfiguration</c>.</summary>
+ protected override GreeterClient NewInstance(ClientBaseConfiguration configuration)
+ {
+ return new GreeterClient(configuration);
+ }
+ }
+
+ /// <summary>Creates service definition that can be registered with a server</summary>
+ /// <param name="serviceImpl">An object implementing the server-side handling logic.</param>
+ public static grpc::ServerServiceDefinition BindService(GreeterBase serviceImpl)
+ {
+ return grpc::ServerServiceDefinition.CreateBuilder()
+ .AddMethod(__Method_SayHello, serviceImpl.SayHello).Build();
+ }
+
+ }
+}
+#endregion
diff --git a/examples/csharp/HelloworldXamarin/HelloworldXamarin/HelloworldXamarin.projitems b/examples/csharp/HelloworldXamarin/HelloworldXamarin/HelloworldXamarin.projitems
new file mode 100644
index 0000000000..25f5478c53
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/HelloworldXamarin/HelloworldXamarin.projitems
@@ -0,0 +1,15 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+ <PropertyGroup>
+ <MSBuildAllProjects>$(MSBuildAllProjects);$(MSBuildThisFileFullPath)</MSBuildAllProjects>
+ <HasSharedItems>true</HasSharedItems>
+ <SharedGUID>{42FFF3D8-934F-4475-8E68-08DA340BF6E8}</SharedGUID>
+ </PropertyGroup>
+ <PropertyGroup Label="Configuration">
+ <Import_RootNamespace>HelloworldXamarin</Import_RootNamespace>
+ </PropertyGroup>
+ <ItemGroup>
+ <Compile Include="$(MSBuildThisFileDirectory)Helloworld.cs" />
+ <Compile Include="$(MSBuildThisFileDirectory)HelloworldGrpc.cs" />
+ </ItemGroup>
+</Project> \ No newline at end of file
diff --git a/examples/csharp/HelloworldXamarin/HelloworldXamarin/HelloworldXamarin.shproj b/examples/csharp/HelloworldXamarin/HelloworldXamarin/HelloworldXamarin.shproj
new file mode 100644
index 0000000000..0eb2448b25
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/HelloworldXamarin/HelloworldXamarin.shproj
@@ -0,0 +1,11 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+ <PropertyGroup>
+ <ProjectGuid>{42FFF3D8-934F-4475-8E68-08DA340BF6E8}</ProjectGuid>
+ </PropertyGroup>
+ <Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" />
+ <Import Project="$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)\CodeSharing\Microsoft.CodeSharing.Common.Default.props" />
+ <Import Project="$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)\CodeSharing\Microsoft.CodeSharing.Common.props" />
+ <Import Project="HelloworldXamarin.projitems" Label="Shared" />
+ <Import Project="$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)\CodeSharing\Microsoft.CodeSharing.CSharp.targets" />
+</Project> \ No newline at end of file
diff --git a/examples/csharp/HelloworldXamarin/README.md b/examples/csharp/HelloworldXamarin/README.md
new file mode 100644
index 0000000000..4394dcc0c4
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/README.md
@@ -0,0 +1,35 @@
+gRPC C# on Xamarin
+========================
+
+EXPERIMENTAL ONLY
+-------------
+Support of the Xamarin platform is currently experimental.
+The example depends on experimental Grpc.Core nuget package that hasn't
+been officially released and is only available via the [daily builds](https://packages.grpc.io/)
+source.
+
+BACKGROUND
+-------------
+The example project supports Xamarin.Android and Xamarin.iOS
+
+For this sample, we've already generated the server and client stubs from [helloworld.proto][].
+
+PREREQUISITES
+-------------
+
+- The latest version Xamarin Studio or Visual Studio 2017 with Xamarin support installed.
+
+BUILD
+-------
+
+- Open the `HelloworldXamarin.sln` in Visual Studio (or Xamarin Studio)
+- Build the solution (Build -> Build All)
+
+Try it!
+-------
+
+You can deploy the example apps directly through Xamarin Studio IDE.
+Deployments can target both Android and iOS (both support physical device
+deployment as well as simulator).
+
+[helloworld.proto]:../../protos/helloworld.proto
diff --git a/examples/csharp/HelloworldXamarin/iOS/AppDelegate.cs b/examples/csharp/HelloworldXamarin/iOS/AppDelegate.cs
new file mode 100644
index 0000000000..e7620f91a2
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/iOS/AppDelegate.cs
@@ -0,0 +1,77 @@
+#region Copyright notice and license
+
+// Copyright 2018 The gRPC Authors
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#endregion
+
+using Foundation;
+using UIKit;
+
+namespace HelloworldXamarin.iOS
+{
+ // The UIApplicationDelegate for the application. This class is responsible for launching the
+ // User Interface of the application, as well as listening (and optionally responding) to application events from iOS.
+ [Register("AppDelegate")]
+ public class AppDelegate : UIApplicationDelegate
+ {
+ // class-level declarations
+
+ public override UIWindow Window
+ {
+ get;
+ set;
+ }
+
+ public override bool FinishedLaunching(UIApplication application, NSDictionary launchOptions)
+ {
+ // Override point for customization after application launch.
+ // If not required for your application you can safely delete this method
+
+ return true;
+ }
+
+ public override void OnResignActivation(UIApplication application)
+ {
+ // Invoked when the application is about to move from active to inactive state.
+ // This can occur for certain types of temporary interruptions (such as an incoming phone call or SMS message)
+ // or when the user quits the application and it begins the transition to the background state.
+ // Games should use this method to pause the game.
+ }
+
+ public override void DidEnterBackground(UIApplication application)
+ {
+ // Use this method to release shared resources, save user data, invalidate timers and store the application state.
+ // If your application supports background exection this method is called instead of WillTerminate when the user quits.
+ }
+
+ public override void WillEnterForeground(UIApplication application)
+ {
+ // Called as part of the transiton from background to active state.
+ // Here you can undo many of the changes made on entering the background.
+ }
+
+ public override void OnActivated(UIApplication application)
+ {
+ // Restart any tasks that were paused (or not yet started) while the application was inactive.
+ // If the application was previously in the background, optionally refresh the user interface.
+ }
+
+ public override void WillTerminate(UIApplication application)
+ {
+ // Called when the application is about to terminate. Save data, if needed. See also DidEnterBackground.
+ }
+ }
+}
+
diff --git a/examples/csharp/HelloworldXamarin/iOS/Assets.xcassets/AppIcon.appiconset/Contents.json b/examples/csharp/HelloworldXamarin/iOS/Assets.xcassets/AppIcon.appiconset/Contents.json
new file mode 100644
index 0000000000..64d0e3ddf8
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/iOS/Assets.xcassets/AppIcon.appiconset/Contents.json
@@ -0,0 +1,202 @@
+{
+ "images" : [
+ {
+ "idiom" : "iphone",
+ "size" : "20x20",
+ "scale" : "2x"
+ },
+ {
+ "idiom" : "iphone",
+ "size" : "20x20",
+ "scale" : "3x"
+ },
+ {
+ "idiom" : "iphone",
+ "size" : "29x29",
+ "scale" : "2x"
+ },
+ {
+ "idiom" : "iphone",
+ "size" : "29x29",
+ "scale" : "3x"
+ },
+ {
+ "idiom" : "iphone",
+ "size" : "40x40",
+ "scale" : "2x"
+ },
+ {
+ "idiom" : "iphone",
+ "size" : "40x40",
+ "scale" : "3x"
+ },
+ {
+ "idiom" : "iphone",
+ "size" : "60x60",
+ "scale" : "2x"
+ },
+ {
+ "idiom" : "iphone",
+ "size" : "60x60",
+ "scale" : "3x"
+ },
+ {
+ "idiom" : "ipad",
+ "size" : "20x20",
+ "scale" : "1x"
+ },
+ {
+ "idiom" : "ipad",
+ "size" : "20x20",
+ "scale" : "2x"
+ },
+ {
+ "idiom" : "ipad",
+ "size" : "29x29",
+ "scale" : "1x"
+ },
+ {
+ "idiom" : "ipad",
+ "size" : "29x29",
+ "scale" : "2x"
+ },
+ {
+ "idiom" : "ipad",
+ "size" : "40x40",
+ "scale" : "1x"
+ },
+ {
+ "idiom" : "ipad",
+ "size" : "40x40",
+ "scale" : "2x"
+ },
+ {
+ "idiom" : "ipad",
+ "size" : "76x76",
+ "scale" : "1x"
+ },
+ {
+ "idiom" : "ipad",
+ "size" : "76x76",
+ "scale" : "2x"
+ },
+ {
+ "idiom" : "ipad",
+ "size" : "83.5x83.5",
+ "scale" : "2x"
+ },
+ {
+ "idiom" : "ios-marketing",
+ "size" : "1024x1024",
+ "scale" : "1x"
+ },
+ {
+ "size" : "24x24",
+ "idiom" : "watch",
+ "scale" : "2x",
+ "role" : "notificationCenter",
+ "subtype" : "38mm"
+ },
+ {
+ "size" : "27.5x27.5",
+ "idiom" : "watch",
+ "scale" : "2x",
+ "role" : "notificationCenter",
+ "subtype" : "42mm"
+ },
+ {
+ "size" : "29x29",
+ "idiom" : "watch",
+ "role" : "companionSettings",
+ "scale" : "2x"
+ },
+ {
+ "size" : "29x29",
+ "idiom" : "watch",
+ "role" : "companionSettings",
+ "scale" : "3x"
+ },
+ {
+ "size" : "40x40",
+ "idiom" : "watch",
+ "scale" : "2x",
+ "role" : "appLauncher",
+ "subtype" : "38mm"
+ },
+ {
+ "size" : "44x44",
+ "idiom" : "watch",
+ "scale" : "2x",
+ "role" : "longLook",
+ "subtype" : "42mm"
+ },
+ {
+ "size" : "86x86",
+ "idiom" : "watch",
+ "scale" : "2x",
+ "role" : "quickLook",
+ "subtype" : "38mm"
+ },
+ {
+ "size" : "98x98",
+ "idiom" : "watch",
+ "scale" : "2x",
+ "role" : "quickLook",
+ "subtype" : "42mm"
+ },
+ {
+ "idiom" : "mac",
+ "size" : "16x16",
+ "scale" : "1x"
+ },
+ {
+ "idiom" : "mac",
+ "size" : "16x16",
+ "scale" : "2x"
+ },
+ {
+ "idiom" : "mac",
+ "size" : "32x32",
+ "scale" : "1x"
+ },
+ {
+ "idiom" : "mac",
+ "size" : "32x32",
+ "scale" : "2x"
+ },
+ {
+ "idiom" : "mac",
+ "size" : "128x128",
+ "scale" : "1x"
+ },
+ {
+ "idiom" : "mac",
+ "size" : "128x128",
+ "scale" : "2x"
+ },
+ {
+ "idiom" : "mac",
+ "size" : "256x256",
+ "scale" : "1x"
+ },
+ {
+ "idiom" : "mac",
+ "size" : "256x256",
+ "scale" : "2x"
+ },
+ {
+ "idiom" : "mac",
+ "size" : "512x512",
+ "scale" : "1x"
+ },
+ {
+ "idiom" : "mac",
+ "size" : "512x512",
+ "scale" : "2x"
+ }
+ ],
+ "info" : {
+ "version" : 1,
+ "author" : "xcode"
+ }
+}
diff --git a/examples/csharp/HelloworldXamarin/iOS/Assets.xcassets/Contents.json b/examples/csharp/HelloworldXamarin/iOS/Assets.xcassets/Contents.json
new file mode 100644
index 0000000000..4caf392f92
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/iOS/Assets.xcassets/Contents.json
@@ -0,0 +1,6 @@
+{
+ "info" : {
+ "version" : 1,
+ "author" : "xcode"
+ }
+} \ No newline at end of file
diff --git a/examples/csharp/HelloworldXamarin/iOS/Entitlements.plist b/examples/csharp/HelloworldXamarin/iOS/Entitlements.plist
new file mode 100644
index 0000000000..9ae599370b
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/iOS/Entitlements.plist
@@ -0,0 +1,6 @@
+<?xml version="1.0" encoding="UTF-8" ?>
+<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+</dict>
+</plist>
diff --git a/examples/csharp/HelloworldXamarin/iOS/HelloworldXamarin.iOS.csproj b/examples/csharp/HelloworldXamarin/iOS/HelloworldXamarin.iOS.csproj
new file mode 100644
index 0000000000..b5c0d1d119
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/iOS/HelloworldXamarin.iOS.csproj
@@ -0,0 +1,126 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+ <PropertyGroup>
+ <Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
+ <Platform Condition=" '$(Platform)' == '' ">iPhoneSimulator</Platform>
+ <ProjectGuid>{62336DF0-60D8-478F-8140-B3CB089B417E}</ProjectGuid>
+ <ProjectTypeGuids>{FEACFBD2-3405-455C-9665-78FE426C6842};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}</ProjectTypeGuids>
+ <OutputType>Exe</OutputType>
+ <RootNamespace>HelloworldXamarin.iOS</RootNamespace>
+ <AssemblyName>HelloworldXamarin.iOS</AssemblyName>
+ <IPhoneResourcePrefix>Resources</IPhoneResourcePrefix>
+ </PropertyGroup>
+ <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|iPhoneSimulator' ">
+ <DebugSymbols>true</DebugSymbols>
+ <DebugType>full</DebugType>
+ <Optimize>false</Optimize>
+ <OutputPath>bin\iPhoneSimulator\Debug</OutputPath>
+ <DefineConstants>DEBUG;ENABLE_TEST_CLOUD;</DefineConstants>
+ <ErrorReport>prompt</ErrorReport>
+ <WarningLevel>4</WarningLevel>
+ <CodesignKey>iPhone Developer</CodesignKey>
+ <MtouchDebug>true</MtouchDebug>
+ <MtouchNoSymbolStrip>true</MtouchNoSymbolStrip>
+ <MtouchFastDev>true</MtouchFastDev>
+ <IOSDebuggerPort>45216</IOSDebuggerPort>
+ <MtouchLink>None</MtouchLink>
+ <MtouchArch>x86_64</MtouchArch>
+ <MtouchHttpClientHandler>HttpClientHandler</MtouchHttpClientHandler>
+ <PlatformTarget>x86</PlatformTarget>
+ </PropertyGroup>
+ <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|iPhone' ">
+ <DebugType>pdbonly</DebugType>
+ <Optimize>true</Optimize>
+ <OutputPath>bin\iPhone\Release</OutputPath>
+ <ErrorReport>prompt</ErrorReport>
+ <WarningLevel>4</WarningLevel>
+ <CodesignKey>iPhone Developer</CodesignKey>
+ <MtouchFloat32>true</MtouchFloat32>
+ <CodesignEntitlements>Entitlements.plist</CodesignEntitlements>
+ <MtouchLink>SdkOnly</MtouchLink>
+ <MtouchArch>ARM64</MtouchArch>
+ <MtouchHttpClientHandler>HttpClientHandler</MtouchHttpClientHandler>
+ <PlatformTarget>x86</PlatformTarget>
+ </PropertyGroup>
+ <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|iPhoneSimulator' ">
+ <DebugType>pdbonly</DebugType>
+ <Optimize>true</Optimize>
+ <OutputPath>bin\iPhoneSimulator\Release</OutputPath>
+ <ErrorReport>prompt</ErrorReport>
+ <WarningLevel>4</WarningLevel>
+ <CodesignKey>iPhone Developer</CodesignKey>
+ <MtouchNoSymbolStrip>true</MtouchNoSymbolStrip>
+ <MtouchLink>None</MtouchLink>
+ <MtouchArch>x86_64</MtouchArch>
+ <MtouchHttpClientHandler>HttpClientHandler</MtouchHttpClientHandler>
+ <PlatformTarget>x86</PlatformTarget>
+ </PropertyGroup>
+ <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|iPhone' ">
+ <DebugSymbols>true</DebugSymbols>
+ <DebugType>full</DebugType>
+ <Optimize>false</Optimize>
+ <OutputPath>bin\iPhone\Debug</OutputPath>
+ <DefineConstants>DEBUG;ENABLE_TEST_CLOUD;</DefineConstants>
+ <ErrorReport>prompt</ErrorReport>
+ <WarningLevel>4</WarningLevel>
+ <CodesignKey>iPhone Developer</CodesignKey>
+ <DeviceSpecificBuild>true</DeviceSpecificBuild>
+ <MtouchDebug>true</MtouchDebug>
+ <MtouchNoSymbolStrip>true</MtouchNoSymbolStrip>
+ <MtouchFastDev>true</MtouchFastDev>
+ <MtouchFloat32>true</MtouchFloat32>
+ <CodesignEntitlements>Entitlements.plist</CodesignEntitlements>
+ <IOSDebuggerPort>35164</IOSDebuggerPort>
+ <MtouchLink>SdkOnly</MtouchLink>
+ <MtouchArch>ARM64</MtouchArch>
+ <MtouchHttpClientHandler>HttpClientHandler</MtouchHttpClientHandler>
+ <PlatformTarget>x86</PlatformTarget>
+ </PropertyGroup>
+ <ItemGroup>
+ <Reference Include="System" />
+ <Reference Include="System.Xml" />
+ <Reference Include="System.Core" />
+ <Reference Include="Xamarin.iOS" />
+ <Reference Include="System.IO.Compression" />
+ <Reference Include="System.Net.Http" />
+ <Reference Include="System.Runtime.Loader">
+ <HintPath>..\packages\System.Runtime.Loader.4.0.0\lib\netstandard1.5\System.Runtime.Loader.dll</HintPath>
+ </Reference>
+ <Reference Include="System.Interactive.Async">
+ <HintPath>..\packages\System.Interactive.Async.3.1.1\lib\netstandard1.3\System.Interactive.Async.dll</HintPath>
+ </Reference>
+ <Reference Include="Grpc.Core">
+ <HintPath>..\packages\Grpc.Core.1.15.0-dev\lib\netstandard1.5\Grpc.Core.dll</HintPath>
+ </Reference>
+ <Reference Include="Google.Protobuf">
+ <HintPath>..\packages\Google.Protobuf.3.6.0\lib\netstandard1.0\Google.Protobuf.dll</HintPath>
+ </Reference>
+ </ItemGroup>
+ <ItemGroup>
+ <ImageAsset Include="Assets.xcassets\AppIcon.appiconset\Contents.json" />
+ <ImageAsset Include="Assets.xcassets\Contents.json" />
+ </ItemGroup>
+ <ItemGroup>
+ <Folder Include="Resources\" />
+ </ItemGroup>
+ <ItemGroup>
+ <InterfaceDefinition Include="LaunchScreen.storyboard" />
+ <InterfaceDefinition Include="Main.storyboard" />
+ </ItemGroup>
+ <ItemGroup>
+ <None Include="Info.plist" />
+ <None Include="Entitlements.plist" />
+ <None Include="packages.config" />
+ </ItemGroup>
+ <ItemGroup>
+ <Compile Include="Main.cs" />
+ <Compile Include="AppDelegate.cs" />
+ <Compile Include="ViewController.cs" />
+ <Compile Include="ViewController.designer.cs">
+ <DependentUpon>ViewController.cs</DependentUpon>
+ </Compile>
+ </ItemGroup>
+ <Import Project="..\HelloworldXamarin\HelloworldXamarin.projitems" Label="Shared" Condition="Exists('..\HelloworldXamarin\HelloworldXamarin.projitems')" />
+ <Import Project="$(MSBuildExtensionsPath)\Xamarin\iOS\Xamarin.iOS.CSharp.targets" />
+ <Import Project="..\packages\Grpc.Core.1.15.0-dev\build\Xamarin.iOS\Grpc.Core.targets" Condition="Exists('..\packages\Grpc.Core.1.15.0-dev\build\Xamarin.iOS\Grpc.Core.targets')" />
+</Project> \ No newline at end of file
diff --git a/examples/csharp/HelloworldXamarin/iOS/Info.plist b/examples/csharp/HelloworldXamarin/iOS/Info.plist
new file mode 100644
index 0000000000..1663f19452
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/iOS/Info.plist
@@ -0,0 +1,48 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+ <key>CFBundleName</key>
+ <string>HelloworldXamarin</string>
+ <key>CFBundleIdentifier</key>
+ <string>io.grpc.examples.HelloworldXamarin</string>
+ <key>CFBundleShortVersionString</key>
+ <string>1.0</string>
+ <key>CFBundleVersion</key>
+ <string>1.0</string>
+ <key>LSRequiresIPhoneOS</key>
+ <true/>
+ <key>MinimumOSVersion</key>
+ <string>8.0</string>
+ <key>UIDeviceFamily</key>
+ <array>
+ <integer>1</integer>
+ <integer>2</integer>
+ </array>
+ <key>UILaunchStoryboardName</key>
+ <string>LaunchScreen</string>
+ <key>UIMainStoryboardFile</key>
+ <string>Main</string>
+ <key>UIMainStoryboardFile~ipad</key>
+ <string>Main</string>
+ <key>UIRequiredDeviceCapabilities</key>
+ <array>
+ <string>armv7</string>
+ </array>
+ <key>UISupportedInterfaceOrientations</key>
+ <array>
+ <string>UIInterfaceOrientationPortrait</string>
+ <string>UIInterfaceOrientationLandscapeLeft</string>
+ <string>UIInterfaceOrientationLandscapeRight</string>
+ </array>
+ <key>UISupportedInterfaceOrientations~ipad</key>
+ <array>
+ <string>UIInterfaceOrientationPortrait</string>
+ <string>UIInterfaceOrientationPortraitUpsideDown</string>
+ <string>UIInterfaceOrientationLandscapeLeft</string>
+ <string>UIInterfaceOrientationLandscapeRight</string>
+ </array>
+ <key>XSAppIconAssets</key>
+ <string>Assets.xcassets/AppIcon.appiconset</string>
+</dict>
+</plist>
diff --git a/examples/csharp/HelloworldXamarin/iOS/LaunchScreen.storyboard b/examples/csharp/HelloworldXamarin/iOS/LaunchScreen.storyboard
new file mode 100644
index 0000000000..5d2e905aa8
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/iOS/LaunchScreen.storyboard
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="UTF-8" standalone="no"?>
+<document type="com.apple.InterfaceBuilder3.CocoaTouch.Storyboard.XIB" version="3.0" toolsVersion="9532" systemVersion="15D21" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" launchScreen="YES" useTraitCollections="YES" initialViewController="01J-lp-oVM">
+ <dependencies>
+ <deployment identifier="iOS" />
+ <plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="9530" />
+ </dependencies>
+ <scenes>
+ <!--View Controller-->
+ <scene sceneID="EHf-IW-A2E">
+ <objects>
+ <viewController id="01J-lp-oVM" sceneMemberID="viewController">
+ <layoutGuides>
+ <viewControllerLayoutGuide type="top" id="Llm-lL-Icb" />
+ <viewControllerLayoutGuide type="bottom" id="xb3-aO-Qok" />
+ </layoutGuides>
+ <view key="view" contentMode="scaleToFill" id="Ze5-6b-2t3">
+ <rect key="frame" x="0.0" y="0.0" width="600" height="600" />
+ <autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES" />
+ <color key="backgroundColor" white="1" alpha="1" colorSpace="custom" customColorSpace="calibratedWhite" />
+ </view>
+ </viewController>
+ <placeholder placeholderIdentifier="IBFirstResponder" id="iYj-Kq-Ea1" userLabel="First Responder" sceneMemberID="firstResponder" />
+ </objects>
+ <point key="canvasLocation" x="53" y="375" />
+ </scene>
+ </scenes>
+</document>
diff --git a/examples/csharp/HelloworldXamarin/iOS/Main.cs b/examples/csharp/HelloworldXamarin/iOS/Main.cs
new file mode 100644
index 0000000000..a4ddf35c70
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/iOS/Main.cs
@@ -0,0 +1,38 @@
+#region Copyright notice and license
+
+// Copyright 2018 The gRPC Authors
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#endregion
+
+using System;
+using System.Collections.Generic;
+using System.Linq;
+
+using Foundation;
+using UIKit;
+
+namespace HelloworldXamarin.iOS
+{
+ public class Application
+ {
+ // This is the main entry point of the application.
+ static void Main(string[] args)
+ {
+ // if you want to use a different Application Delegate class from "AppDelegate"
+ // you can specify it here.
+ UIApplication.Main(args, null, "AppDelegate");
+ }
+ }
+}
diff --git a/examples/csharp/HelloworldXamarin/iOS/Main.storyboard b/examples/csharp/HelloworldXamarin/iOS/Main.storyboard
new file mode 100644
index 0000000000..92a28ce08d
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/iOS/Main.storyboard
@@ -0,0 +1,40 @@
+<?xml version="1.0" encoding="UTF-8" standalone="no"?>
+<document type="com.apple.InterfaceBuilder3.CocoaTouch.Storyboard.XIB" version="3.0" toolsVersion="6750" systemVersion="14C109" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" initialViewController="BYZ-38-t0r">
+ <dependencies>
+ <plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="6735" />
+ </dependencies>
+ <scenes>
+ <!--View Controller-->
+ <scene sceneID="tne-QT-ifu">
+ <objects>
+ <viewController id="BYZ-38-t0r" customClass="ViewController" sceneMemberID="viewController">
+ <layoutGuides>
+ <viewControllerLayoutGuide type="top" id="y3c-jy-aDJ" />
+ <viewControllerLayoutGuide type="bottom" id="wfy-db-euE" />
+ </layoutGuides>
+ <view key="view" contentMode="scaleToFill" id="8bC-Xf-vdC">
+ <rect key="frame" x="0.0" y="0.0" width="600" height="600" />
+ <autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES" />
+ <subviews>
+ <button opaque="NO" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" buttonType="roundedRect" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="oBE-Ac-vcx">
+ <rect key="frame" x="224" y="285" width="152" height="30" />
+ <state key="normal" title="Hello World, Click Me!">
+ <color key="titleShadowColor" white="0.5" alpha="1" colorSpace="calibratedWhite" />
+ </state>
+ </button>
+ </subviews>
+ <color key="backgroundColor" white="1" alpha="1" colorSpace="custom" customColorSpace="calibratedWhite" />
+ <constraints>
+ <constraint firstItem="oBE-Ac-vcx" firstAttribute="centerX" secondItem="8bC-Xf-vdC" secondAttribute="centerX" id="HiD-uS-i16" />
+ <constraint firstItem="oBE-Ac-vcx" firstAttribute="centerY" secondItem="8bC-Xf-vdC" secondAttribute="centerY" id="YgX-7e-bMc" />
+ </constraints>
+ </view>
+ <connections>
+ <outlet property="Button" destination="oBE-Ac-vcx" id="OkX-0Z-gth" />
+ </connections>
+ </viewController>
+ <placeholder placeholderIdentifier="IBFirstResponder" id="dkx-z0-nzr" sceneMemberID="firstResponder" />
+ </objects>
+ </scene>
+ </scenes>
+</document>
diff --git a/examples/csharp/HelloworldXamarin/iOS/ViewController.cs b/examples/csharp/HelloworldXamarin/iOS/ViewController.cs
new file mode 100644
index 0000000000..c553c1eb48
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/iOS/ViewController.cs
@@ -0,0 +1,91 @@
+#region Copyright notice and license
+
+// Copyright 2018 The gRPC Authors
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#endregion
+
+using System;
+using System.Threading.Tasks;
+
+using Grpc.Core;
+using Helloworld;
+
+using UIKit;
+
+namespace HelloworldXamarin.iOS
+{
+ public partial class ViewController : UIViewController
+ {
+ const int Port = 50051;
+ int count = 1;
+
+ public ViewController(IntPtr handle) : base(handle)
+ {
+ }
+
+ public override void ViewDidLoad()
+ {
+ base.ViewDidLoad();
+
+ // Perform any additional setup after loading the view, typically from a nib.
+ Button.AccessibilityIdentifier = "myButton";
+ Button.TouchUpInside += delegate
+ {
+ var title = SayHello();
+ Button.SetTitle(title, UIControlState.Normal);
+ };
+ }
+
+ public override void DidReceiveMemoryWarning()
+ {
+ base.DidReceiveMemoryWarning();
+ // Release any cached data, images, etc that aren't in use.
+ }
+
+ private string SayHello()
+ {
+ Server server = new Server
+ {
+ Services = { Greeter.BindService(new GreeterImpl()) },
+ Ports = { new ServerPort("localhost", Port, ServerCredentials.Insecure) }
+ };
+ server.Start();
+
+ Channel channel = new Channel("localhost:50051", ChannelCredentials.Insecure);
+
+ var client = new Greeter.GreeterClient(channel);
+ string user = "Xamarin " + count;
+
+ var reply = client.SayHello(new HelloRequest { Name = user });
+
+ channel.ShutdownAsync().Wait();
+ server.ShutdownAsync().Wait();
+
+ count++;
+
+ return "Greeting: " + reply.Message;
+ }
+
+
+ class GreeterImpl : Greeter.GreeterBase
+ {
+ // Server side handler of the SayHello RPC
+ public override Task<HelloReply> SayHello(HelloRequest request, ServerCallContext context)
+ {
+ return Task.FromResult(new HelloReply { Message = "Hello " + request.Name });
+ }
+ }
+ }
+}
diff --git a/examples/csharp/HelloworldXamarin/iOS/ViewController.designer.cs b/examples/csharp/HelloworldXamarin/iOS/ViewController.designer.cs
new file mode 100644
index 0000000000..2677a068dc
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/iOS/ViewController.designer.cs
@@ -0,0 +1,25 @@
+//
+// This file has been generated automatically by MonoDevelop to store outlets and
+// actions made in the Xcode designer. If it is removed, they will be lost.
+// Manual changes to this file may not be handled correctly.
+//
+using Foundation;
+
+namespace HelloworldXamarin.iOS
+{
+ [Register("ViewController")]
+ partial class ViewController
+ {
+ [Outlet]
+ UIKit.UIButton Button { get; set; }
+
+ void ReleaseDesignerOutlets()
+ {
+ if (Button != null)
+ {
+ Button.Dispose();
+ Button = null;
+ }
+ }
+ }
+}
diff --git a/examples/csharp/HelloworldXamarin/iOS/packages.config b/examples/csharp/HelloworldXamarin/iOS/packages.config
new file mode 100644
index 0000000000..ce4bceb62a
--- /dev/null
+++ b/examples/csharp/HelloworldXamarin/iOS/packages.config
@@ -0,0 +1,54 @@
+<?xml version="1.0" encoding="utf-8"?>
+<packages>
+ <package id="Google.Protobuf" version="3.6.0" targetFramework="xamarinios10" />
+ <package id="Grpc.Core" version="1.15.0-dev" targetFramework="xamarinios10" />
+ <package id="Microsoft.NETCore.Platforms" version="1.1.0" targetFramework="xamarinios10" />
+ <package id="Microsoft.Win32.Primitives" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="NETStandard.Library" version="1.6.1" targetFramework="xamarinios10" />
+ <package id="System.AppContext" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Collections" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Collections.Concurrent" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Console" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Diagnostics.Debug" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Diagnostics.Tools" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Diagnostics.Tracing" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Globalization" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Globalization.Calendars" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Interactive.Async" version="3.1.1" targetFramework="xamarinios10" />
+ <package id="System.IO" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.IO.Compression" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.IO.Compression.ZipFile" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.IO.FileSystem" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.IO.FileSystem.Primitives" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Linq" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Linq.Expressions" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Net.Http" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Net.Primitives" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Net.Sockets" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.ObjectModel" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Reflection" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Reflection.Extensions" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Reflection.Primitives" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Resources.ResourceManager" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Runtime" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Runtime.Extensions" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Runtime.Handles" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Runtime.InteropServices" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Runtime.InteropServices.RuntimeInformation" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Runtime.Loader" version="4.0.0" targetFramework="xamarinios10" />
+ <package id="System.Runtime.Numerics" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Security.Cryptography.Algorithms" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Security.Cryptography.Encoding" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Security.Cryptography.Primitives" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Security.Cryptography.X509Certificates" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Text.Encoding" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Text.Encoding.Extensions" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Text.RegularExpressions" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Threading" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Threading.Tasks" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Threading.Thread" version="4.0.0" targetFramework="xamarinios10" />
+ <package id="System.Threading.ThreadPool" version="4.0.10" targetFramework="xamarinios10" />
+ <package id="System.Threading.Timer" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Xml.ReaderWriter" version="4.3.0" targetFramework="xamarinios10" />
+ <package id="System.Xml.XDocument" version="4.3.0" targetFramework="xamarinios10" />
+</packages> \ No newline at end of file
diff --git a/src/csharp/README.md b/src/csharp/README.md
index 92be4bf1e5..d8aed94988 100644
--- a/src/csharp/README.md
+++ b/src/csharp/README.md
@@ -32,6 +32,14 @@ HOW TO USE
- To be able to generate code from Protocol Buffer (`.proto`) file definitions, add the [Grpc.Tools](https://www.nuget.org/packages/Grpc.Tools/) NuGet package that contains Protocol Buffers compiler (_protoc_) and the gRPC _protoc_ plugin.
+**Xamarin.Android and Xamarin.iOS (Experimental only)**
+
+See [Experimentally supported platforms](experimental) for instructions.
+
+**Unity (Experimental only)**
+
+See [Experimentally supported platforms](experimental) for instructions.
+
BUILD FROM SOURCE
-----------------
diff --git a/src/csharp/experimental/README.md b/src/csharp/experimental/README.md
index f892a2ee95..212791ac38 100644
--- a/src/csharp/experimental/README.md
+++ b/src/csharp/experimental/README.md
@@ -1,16 +1,22 @@
This directory contains useful resources for getting gRPC C# to work on
-not-yet-supported platforms.
+platforms that are not yet fully supported.
-# Unity & Xamarin
-gRPC C# currently doesn't support Unity or Xamarin, but some proof-of-concept
-work has been done. Some of the resources are shared in this directory to
-ease community work on Unity & Xamarin support.
+# Xamarin
-## Crosscompiling `grpc_csharp_ext` for Android
+gRPC C# now has experimental support for Xamarin.
+See [HelloworldXamarin](/examples/csharp/HelloworldXamarin) for an example how to use it.
-* Install [Android NDK](https://developer.android.com/ndk/index.html)
-* Run `./build_native_ext_for_android.sh` to crosscompile using cmake.
+What's currently supported:
-## Crosscompiling `grpc_csharp_ext` for iOS
+Xamarin.Android
+- supported API level: Kitkat 4.4+ (= API level 19)
+- supported ABIs: `armeabi-v7a` (vast majority of Android devices out there),
+ `arm64-v8a` (some newer Android devices), `x86` (for emulator)
-TBD
+Xamarin.iOS
+- supported architectures: arm64 (iPhone 6+) and x86_64 (iPhone simulator)
+
+# Unity
+gRPC C# currently doesn't support Unity, but some proof-of-concept
+work has been done. There is in-progress effort to provide users
+with a pre-built gRPC package that can be used in their projects.
diff --git a/tools/distrib/check_copyright.py b/tools/distrib/check_copyright.py
index e6388251cf..77f602ad1f 100755
--- a/tools/distrib/check_copyright.py
+++ b/tools/distrib/check_copyright.py
@@ -100,6 +100,10 @@ _EXEMPT = frozenset((
# Gradle wrappers used to build for Android
'examples/android/helloworld/gradlew.bat',
'src/android/test/interop/gradlew.bat',
+
+ # Designer-generated source
+ 'examples/csharp/HelloworldXamarin/Droid/Resources/Resource.designer.cs',
+ 'examples/csharp/HelloworldXamarin/iOS/ViewController.designer.cs',
))
RE_YEAR = r'Copyright (?P<first_year>[0-9]+\-)?(?P<last_year>[0-9]+) ([Tt]he )?gRPC [Aa]uthors(\.|)'