---
# System prepended metadata

title: '`MagicOnion` `Unary` `Hello World` 2022-02-06'
tags: [MagicOnion, Unary, net6.0, Visual Studio 2022, ASP.NET Core, Hello World]

---

---
lang: ja-jp
breaks: true
---
# `MagicOnion` `Unary` `Hello World` 2022-02-06

## 環境

* `ASP.NET Core`
* `net6.0`
* `Visual Studio 2022`

## 参考

Magic Onion Quick Start
https://github.com/Cysharp/MagicOnion/blob/master/README.md#quick-start

## 共通クラスライブラリ

#### `クラスライブラリ` テンプレートを使用して、共有クラスライブラリプロジェクトを作成

![](https://i.imgur.com/Uob4y97.png)


#### プロジェクトファイルを変更して、必要なパッケージ参照を追加

```xml=
<Project Sdk="Microsoft.NET.Sdk">

	<PropertyGroup>
		<TargetFramework>net6.0</TargetFramework>
		<Nullable>enable</Nullable>
		<ImplicitUsings>enable</ImplicitUsings>
	</PropertyGroup>

	<ItemGroup>
		<PackageReference Include="MagicOnion" Version="4.4.0" />
		<PackageReference Include="MagicOnion.Abstractions" Version="4.4.0" />
		<PackageReference Include="MagicOnion.Shared" Version="4.4.0" />
		<PackageReference Include="MessagePack" Version="2.3.85" />
		<PackageReference Include="MessagePack.Annotations" Version="2.3.85" />
	</ItemGroup>
</Project>
```

#### `IMyFirstService.cs` インターフェイスを作成

```csharp=
using MagicOnion;

namespace Shared
{
    // Defines .NET interface as a Server/Client IDL.
    // The interface is shared between server and client.
    public interface IMyFirstService : IService<IMyFirstService>
    {
        // The return type must be `UnaryResult<T>`.
        UnaryResult<int> SumAsync(int x, int y);
    }
}
```



## Webサービス側

#### `ASP.NET Core gRPCサービス`テンプレートを使用してプロジェクトを作成
![](https://i.imgur.com/xu1nrSG.png)


#### `Protos`、`Services` フォルダを削除

![](https://i.imgur.com/SuS7uVD.png)

#### プロジェクトファイルを変更して、必要なパッケージ参照を追加

```xml=
<Project Sdk="Microsoft.NET.Sdk.Web">

  <PropertyGroup>
    <TargetFramework>net6.0</TargetFramework>
    <Nullable>enable</Nullable>
    <ImplicitUsings>enable</ImplicitUsings>
  </PropertyGroup>

	<ItemGroup>
		<PackageReference Include="MagicOnion" Version="4.4.0" />
		<PackageReference Include="MagicOnion.Abstractions" Version="4.4.0" />
		<PackageReference Include="MagicOnion.Server" Version="4.4.0" />
		<PackageReference Include="MagicOnion.Shared" Version="4.4.0" />
		<PackageReference Include="MessagePack" Version="2.3.85" />
		<PackageReference Include="MessagePack.Annotations" Version="2.3.85" />
		<PackageReference Include="Microsoft.VisualStudio.Threading.Analyzers" Version="17.0.64">
			<PrivateAssets>all</PrivateAssets>
			<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
		</PackageReference>
	</ItemGroup>
	
  <ItemGroup>
    <PackageReference Include="Grpc.AspNetCore" Version="2.40.0" />
  </ItemGroup>

  <ItemGroup>
    <ProjectReference Include="..\Shared\Shared.csproj" />
  </ItemGroup>

</Project>
```

#### `Program.cs` に `MagicOnion` で必要な処理を追加

```csharp=
var builder = WebApplication.CreateBuilder(args);

// Additional configuration is required to successfully run gRPC on macOS.
// For instructions on how to configure Kestrel and gRPC clients on macOS, visit https://go.microsoft.com/fwlink/?linkid=2099682

// Add services to the container.
builder.Services.AddGrpc();
builder.Services.AddMagicOnion();    // ※ここを追加。

var app = builder.Build();

// Configure the HTTP request pipeline.
app.MapMagicOnionService();          // ※ここを削除／追加。
app.MapGet("/", () => "Communication with gRPC endpoints must be made through a gRPC client. To learn how to create a client, visit: https://go.microsoft.com/fwlink/?linkid=2086909");

app.Run();
```

#### `MyFirstService.cs` ※サービスを実装

```csharp=
using MagicOnion;
using MagicOnion.Server;
using Shared;

namespace gRPCService
{
    // Implements RPC service in the server project.
    // The implementation class must inherit `ServiceBase<IMyFirstService>` and `IMyFirstService`
    public class MyFirstService : 
        ServiceBase<
            IMyFirstService
            >, 
        IMyFirstService
    {
        // `UnaryResult<T>` allows the method to be treated as `async` method.
        public async UnaryResult<int> SumAsync(int x, int y)
        {
            Console.WriteLine($"Received:{x}, {y}");
            return x + y;
        }
    }
}

```


## コンソールクライアント

#### `コンソール アプリ` テンプレートを使用してソリューション／プロジェクトを作成

![](https://i.imgur.com/QW1YUv2.png)


#### プロジェクトファイルを変更して、必要なパッケージ参照を追加

```xml=
<Project Sdk="Microsoft.NET.Sdk">

	<PropertyGroup>
		OutputType>Exe</OutputType>
		<TargetFramework>net6.0</TargetFramework>
		<ImplicitUsings>enable</ImplicitUsings>
		<Nullable>enable</Nullable>
	</PropertyGroup>

	<ItemGroup>
		<PackageReference Include="Grpc.Net.Client" Version="2.42.0" />
		<PackageReference Include="MagicOnion.Client" Version="4.4.0" />
		<PackageReference Include="MagicOnion.Shared" Version="4.4.0" />
		<PackageReference Include="MessagePack" Version="2.3.85" />
		<PackageReference Include="MessagePack.Annotations" Version="2.3.85" />
	</ItemGroup>

	<ItemGroup>
		<ProjectReference Include="..\Shared\Shared.csproj" />
	</ItemGroup>

</Project>
```

#### `Program.cs` にクライアントの処理を記述

```csharp=
// See https://aka.ms/new-console-template for more information
using Grpc.Net.Client;
using MagicOnion.Client;
using Shared;

Console.WriteLine("Hello, World!");

// Connect to the server using gRPC channel.
var channel = GrpcChannel.ForAddress("https://localhost:7069");

// NOTE: If your project targets non-.NET Standard 2.1, use `Grpc.Core.Channel` class instead.
// var channel = new Channel("localhost", 5001, new SslCredentials());

// Create a proxy to call the server transparently.
var client = MagicOnionClient.Create<IMyFirstService>(channel);

// Call the server-side method using the proxy.
var result = await client.SumAsync(123, 456);
Console.WriteLine($"Result: {result}");
```

## 動作確認

![](https://i.imgur.com/O5baGMV.png)


###### tags: `MagicOnion` `ASP.NET Core` `net6.0` `Unary` `Hello World` `Visual Studio 2022`
