Jan Tattermusch | 8ab1f7e | 2015-05-06 15:56:30 -0700 | [diff] [blame] | 1 | #region Copyright notice and license |
| 2 | |
Jan Tattermusch | 7897ae9 | 2017-06-07 22:57:36 +0200 | [diff] [blame] | 3 | // Copyright 2015 gRPC authors. |
Jan Tattermusch | 8ab1f7e | 2015-05-06 15:56:30 -0700 | [diff] [blame] | 4 | // |
Jan Tattermusch | 7897ae9 | 2017-06-07 22:57:36 +0200 | [diff] [blame] | 5 | // Licensed under the Apache License, Version 2.0 (the "License"); |
| 6 | // you may not use this file except in compliance with the License. |
| 7 | // You may obtain a copy of the License at |
Jan Tattermusch | 8ab1f7e | 2015-05-06 15:56:30 -0700 | [diff] [blame] | 8 | // |
Jan Tattermusch | 7897ae9 | 2017-06-07 22:57:36 +0200 | [diff] [blame] | 9 | // http://www.apache.org/licenses/LICENSE-2.0 |
Jan Tattermusch | 8ab1f7e | 2015-05-06 15:56:30 -0700 | [diff] [blame] | 10 | // |
Jan Tattermusch | 7897ae9 | 2017-06-07 22:57:36 +0200 | [diff] [blame] | 11 | // Unless required by applicable law or agreed to in writing, software |
| 12 | // distributed under the License is distributed on an "AS IS" BASIS, |
| 13 | // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| 14 | // See the License for the specific language governing permissions and |
| 15 | // limitations under the License. |
Jan Tattermusch | 8ab1f7e | 2015-05-06 15:56:30 -0700 | [diff] [blame] | 16 | |
| 17 | #endregion |
| 18 | |
| 19 | using System; |
Jan Tattermusch | 998eb9b | 2015-07-20 22:12:53 -0700 | [diff] [blame] | 20 | using System.Threading; |
Jan Tattermusch | 8ab1f7e | 2015-05-06 15:56:30 -0700 | [diff] [blame] | 21 | using System.Threading.Tasks; |
| 22 | |
Jan Tattermusch | bff90ac | 2015-08-06 21:30:26 -0700 | [diff] [blame] | 23 | using Grpc.Core.Internal; |
| 24 | |
Jan Tattermusch | 8ab1f7e | 2015-05-06 15:56:30 -0700 | [diff] [blame] | 25 | namespace Grpc.Core |
| 26 | { |
| 27 | /// <summary> |
| 28 | /// Context for a server-side call. |
| 29 | /// </summary> |
Jan Tattermusch | 8368b2e | 2015-08-07 01:18:37 -0700 | [diff] [blame] | 30 | public class ServerCallContext |
Jan Tattermusch | 8ab1f7e | 2015-05-06 15:56:30 -0700 | [diff] [blame] | 31 | { |
Jan Tattermusch | 392fae2 | 2015-08-08 22:21:57 -0700 | [diff] [blame] | 32 | private readonly CallSafeHandle callHandle; |
Jan Tattermusch | 998eb9b | 2015-07-20 22:12:53 -0700 | [diff] [blame] | 33 | private readonly string method; |
| 34 | private readonly string host; |
| 35 | private readonly DateTime deadline; |
| 36 | private readonly Metadata requestHeaders; |
| 37 | private readonly CancellationToken cancellationToken; |
Jan Tattermusch | ae01709 | 2015-07-22 11:59:13 -0700 | [diff] [blame] | 38 | private readonly Metadata responseTrailers = new Metadata(); |
Jan Tattermusch | 998eb9b | 2015-07-20 22:12:53 -0700 | [diff] [blame] | 39 | |
| 40 | private Status status = Status.DefaultSuccess; |
Jan Tattermusch | 8368b2e | 2015-08-07 01:18:37 -0700 | [diff] [blame] | 41 | private Func<Metadata, Task> writeHeadersFunc; |
Jan Tattermusch | bff90ac | 2015-08-06 21:30:26 -0700 | [diff] [blame] | 42 | private IHasWriteOptions writeOptionsHolder; |
Jan Tattermusch | c9b03fe | 2017-02-06 08:45:00 -0800 | [diff] [blame] | 43 | private Lazy<AuthContext> authContext; |
Jan Tattermusch | 998eb9b | 2015-07-20 22:12:53 -0700 | [diff] [blame] | 44 | |
Jan Tattermusch | d148e8e | 2016-10-26 15:28:35 +0200 | [diff] [blame] | 45 | internal ServerCallContext(CallSafeHandle callHandle, string method, string host, DateTime deadline, Metadata requestHeaders, CancellationToken cancellationToken, |
Jan Tattermusch | 8368b2e | 2015-08-07 01:18:37 -0700 | [diff] [blame] | 46 | Func<Metadata, Task> writeHeadersFunc, IHasWriteOptions writeOptionsHolder) |
Jan Tattermusch | 998eb9b | 2015-07-20 22:12:53 -0700 | [diff] [blame] | 47 | { |
Jan Tattermusch | 392fae2 | 2015-08-08 22:21:57 -0700 | [diff] [blame] | 48 | this.callHandle = callHandle; |
Jan Tattermusch | 998eb9b | 2015-07-20 22:12:53 -0700 | [diff] [blame] | 49 | this.method = method; |
| 50 | this.host = host; |
| 51 | this.deadline = deadline; |
| 52 | this.requestHeaders = requestHeaders; |
| 53 | this.cancellationToken = cancellationToken; |
Jan Tattermusch | 8368b2e | 2015-08-07 01:18:37 -0700 | [diff] [blame] | 54 | this.writeHeadersFunc = writeHeadersFunc; |
Jan Tattermusch | bff90ac | 2015-08-06 21:30:26 -0700 | [diff] [blame] | 55 | this.writeOptionsHolder = writeOptionsHolder; |
Jan Tattermusch | c9b03fe | 2017-02-06 08:45:00 -0800 | [diff] [blame] | 56 | this.authContext = new Lazy<AuthContext>(GetAuthContextEager); |
Jan Tattermusch | 998eb9b | 2015-07-20 22:12:53 -0700 | [diff] [blame] | 57 | } |
Jan Tattermusch | 8368b2e | 2015-08-07 01:18:37 -0700 | [diff] [blame] | 58 | |
Jan Tattermusch | 12855fc | 2015-08-24 16:43:23 -0700 | [diff] [blame] | 59 | /// <summary> |
| 60 | /// Asynchronously sends response headers for the current call to the client. This method may only be invoked once for each call and needs to be invoked |
| 61 | /// before any response messages are written. Writing the first response message implicitly sends empty response headers if <c>WriteResponseHeadersAsync</c> haven't |
| 62 | /// been called yet. |
| 63 | /// </summary> |
| 64 | /// <param name="responseHeaders">The response headers to send.</param> |
| 65 | /// <returns>The task that finished once response headers have been written.</returns> |
Jan Tattermusch | 8368b2e | 2015-08-07 01:18:37 -0700 | [diff] [blame] | 66 | public Task WriteResponseHeadersAsync(Metadata responseHeaders) |
| 67 | { |
| 68 | return writeHeadersFunc(responseHeaders); |
| 69 | } |
Jan Tattermusch | 392fae2 | 2015-08-08 22:21:57 -0700 | [diff] [blame] | 70 | |
| 71 | /// <summary> |
| 72 | /// Creates a propagation token to be used to propagate call context to a child call. |
| 73 | /// </summary> |
| 74 | public ContextPropagationToken CreatePropagationToken(ContextPropagationOptions options = null) |
| 75 | { |
| 76 | return new ContextPropagationToken(callHandle, deadline, cancellationToken, options); |
| 77 | } |
Jan Tattermusch | 998eb9b | 2015-07-20 22:12:53 -0700 | [diff] [blame] | 78 | |
Jan Tattermusch | 5e10f18 | 2015-08-05 00:13:02 -0700 | [diff] [blame] | 79 | /// <summary>Name of method called in this RPC.</summary> |
Jan Tattermusch | 998eb9b | 2015-07-20 22:12:53 -0700 | [diff] [blame] | 80 | public string Method |
| 81 | { |
| 82 | get |
| 83 | { |
| 84 | return this.method; |
| 85 | } |
| 86 | } |
| 87 | |
Jan Tattermusch | 5e10f18 | 2015-08-05 00:13:02 -0700 | [diff] [blame] | 88 | /// <summary>Name of host called in this RPC.</summary> |
Jan Tattermusch | 998eb9b | 2015-07-20 22:12:53 -0700 | [diff] [blame] | 89 | public string Host |
| 90 | { |
| 91 | get |
| 92 | { |
| 93 | return this.host; |
| 94 | } |
| 95 | } |
| 96 | |
Jan Tattermusch | 5e10f18 | 2015-08-05 00:13:02 -0700 | [diff] [blame] | 97 | /// <summary>Address of the remote endpoint in URI format.</summary> |
Jan Tattermusch | 062c329 | 2015-07-23 20:28:42 -0700 | [diff] [blame] | 98 | public string Peer |
| 99 | { |
| 100 | get |
| 101 | { |
Jan Tattermusch | d148e8e | 2016-10-26 15:28:35 +0200 | [diff] [blame] | 102 | // Getting the peer lazily is fine as the native call is guaranteed |
| 103 | // not to be disposed before user-supplied server side handler returns. |
| 104 | // Most users won't need to read this field anyway. |
| 105 | return this.callHandle.GetPeer(); |
Jan Tattermusch | 062c329 | 2015-07-23 20:28:42 -0700 | [diff] [blame] | 106 | } |
| 107 | } |
| 108 | |
Jan Tattermusch | 5e10f18 | 2015-08-05 00:13:02 -0700 | [diff] [blame] | 109 | /// <summary>Deadline for this RPC.</summary> |
Jan Tattermusch | 998eb9b | 2015-07-20 22:12:53 -0700 | [diff] [blame] | 110 | public DateTime Deadline |
| 111 | { |
| 112 | get |
| 113 | { |
| 114 | return this.deadline; |
| 115 | } |
| 116 | } |
| 117 | |
Jan Tattermusch | 5e10f18 | 2015-08-05 00:13:02 -0700 | [diff] [blame] | 118 | /// <summary>Initial metadata sent by client.</summary> |
Jan Tattermusch | 998eb9b | 2015-07-20 22:12:53 -0700 | [diff] [blame] | 119 | public Metadata RequestHeaders |
| 120 | { |
| 121 | get |
| 122 | { |
| 123 | return this.requestHeaders; |
| 124 | } |
| 125 | } |
| 126 | |
Jan Tattermusch | 8368b2e | 2015-08-07 01:18:37 -0700 | [diff] [blame] | 127 | /// <summary>Cancellation token signals when call is cancelled.</summary> |
Jan Tattermusch | 998eb9b | 2015-07-20 22:12:53 -0700 | [diff] [blame] | 128 | public CancellationToken CancellationToken |
| 129 | { |
| 130 | get |
| 131 | { |
| 132 | return this.cancellationToken; |
| 133 | } |
| 134 | } |
| 135 | |
Jan Tattermusch | 5e10f18 | 2015-08-05 00:13:02 -0700 | [diff] [blame] | 136 | /// <summary>Trailers to send back to client after RPC finishes.</summary> |
Jan Tattermusch | 998eb9b | 2015-07-20 22:12:53 -0700 | [diff] [blame] | 137 | public Metadata ResponseTrailers |
| 138 | { |
| 139 | get |
| 140 | { |
| 141 | return this.responseTrailers; |
| 142 | } |
| 143 | } |
| 144 | |
| 145 | /// <summary> Status to send back to client after RPC finishes.</summary> |
| 146 | public Status Status |
| 147 | { |
| 148 | get |
| 149 | { |
| 150 | return this.status; |
| 151 | } |
Jan Tattermusch | ae01709 | 2015-07-22 11:59:13 -0700 | [diff] [blame] | 152 | |
Jan Tattermusch | 998eb9b | 2015-07-20 22:12:53 -0700 | [diff] [blame] | 153 | set |
| 154 | { |
| 155 | status = value; |
| 156 | } |
| 157 | } |
Jan Tattermusch | bff90ac | 2015-08-06 21:30:26 -0700 | [diff] [blame] | 158 | |
| 159 | /// <summary> |
| 160 | /// Allows setting write options for the following write. |
| 161 | /// For streaming response calls, this property is also exposed as on IServerStreamWriter for convenience. |
| 162 | /// Both properties are backed by the same underlying value. |
| 163 | /// </summary> |
| 164 | public WriteOptions WriteOptions |
| 165 | { |
| 166 | get |
| 167 | { |
| 168 | return writeOptionsHolder.WriteOptions; |
| 169 | } |
Jan Tattermusch | 8368b2e | 2015-08-07 01:18:37 -0700 | [diff] [blame] | 170 | |
Jan Tattermusch | bff90ac | 2015-08-06 21:30:26 -0700 | [diff] [blame] | 171 | set |
| 172 | { |
| 173 | writeOptionsHolder.WriteOptions = value; |
| 174 | } |
| 175 | } |
Jan Tattermusch | c9b03fe | 2017-02-06 08:45:00 -0800 | [diff] [blame] | 176 | |
| 177 | /// <summary> |
| 178 | /// Gets the <c>AuthContext</c> associated with this call. |
| 179 | /// Note: Access to AuthContext is an experimental API that can change without any prior notice. |
| 180 | /// </summary> |
| 181 | public AuthContext AuthContext |
| 182 | { |
| 183 | get |
| 184 | { |
| 185 | return authContext.Value; |
| 186 | } |
| 187 | } |
| 188 | |
| 189 | private AuthContext GetAuthContextEager() |
| 190 | { |
| 191 | using (var authContextNative = callHandle.GetAuthContext()) |
| 192 | { |
| 193 | return authContextNative.ToAuthContext(); |
| 194 | } |
| 195 | } |
Jan Tattermusch | bff90ac | 2015-08-06 21:30:26 -0700 | [diff] [blame] | 196 | } |
| 197 | |
| 198 | /// <summary> |
| 199 | /// Allows sharing write options between ServerCallContext and other objects. |
| 200 | /// </summary> |
| 201 | public interface IHasWriteOptions |
| 202 | { |
Jan Tattermusch | 12855fc | 2015-08-24 16:43:23 -0700 | [diff] [blame] | 203 | /// <summary> |
| 204 | /// Gets or sets the write options. |
| 205 | /// </summary> |
Jan Tattermusch | bff90ac | 2015-08-06 21:30:26 -0700 | [diff] [blame] | 206 | WriteOptions WriteOptions { get; set; } |
Jan Tattermusch | 8ab1f7e | 2015-05-06 15:56:30 -0700 | [diff] [blame] | 207 | } |
| 208 | } |