コード例 #1
0
ファイル: RpcClientCaches.cs プロジェクト: lulzzz/RpcLib
 /// <summary>
 /// Gets the queue of the given client.
 /// If the client is unknown yet, it is created with the given backlog.
 /// </summary>
 public RpcPeerCache GetClient(string clientID, IRpcCommandBacklog?commandBacklog)
 {
     if (false == queues.TryGetValue(clientID, out var queue))
     {
         queues[clientID] = queue = new RpcPeerCache(clientID, commandBacklog);
     }
     return(queue);
 }
コード例 #2
0
 /// <summary>
 /// Call this method at the beginning to enable the communication to the server, so that this client
 /// can both receive commands from the server and send commands to the server.
 /// </summary>
 /// <param name="clientMethods">A function which returns new instances of the client's RPC method implementations</param>
 /// <param name="clientConfig">The settings of this client</param>
 /// <param name="authAction">An action which authenticates the used HTTP client, e.g. by adding HTTP Basic Auth
 /// information according to the client.</param>
 /// <param name="commandBacklog">The backlog for storing failed commands to retry them later. May be null,
 ///     when only <see cref="RpcRetryStrategy.None"/> will be used.</param>
 public void Start(Func <IEnumerable <RpcFunctions> > clientMethods, RpcClientConfig clientConfig,
                   Action <HttpClient> authAction, IRpcCommandBacklog?commandBacklog)
 {
     if (isRunning)
     {
         return;
     }
     isRunning = true;
     // Remember client factory and settings
     this.clientMethods = clientMethods;
     this.clientConfig  = clientConfig;
     serverCache        = new RpcPeerCache(clientID: "", commandBacklog);
     // Create and authorize HTTP clients
     httpPull         = new HttpClient();
     httpPull.Timeout = TimeSpan.FromSeconds(RpcServerEngine.longPollingSeconds + 10); // Give some more seconds for timeout
     authAction(httpPull);
     httpPush         = new HttpClient();
     httpPush.Timeout = TimeSpan.FromMilliseconds(RpcCommand.defaultTimeoutMs);
     authAction(httpPush);
     // Loop to pull the next command for this client from the server, execute it (if not already executed before)
     // and send the response together with the next pull.
     _ = Task.Run(async() => {
         RpcCommandResult?lastResult = null;
         while (isRunning)
         {
             RpcCommand?next = null;
             try {
                 next = await PullFromServer(lastResult);
             }
             catch {
                 // Could not reach server. Try the same result report again.
                 await Task.Delay(1000); // Wait a second before trying again
             }
             if (next != null)
             {
                 lastResult = await ExecuteLocallyNow(next);
             }
         }
     });
     // Loop to execute (i.e. send to server) the next command in the queue.
     _ = Task.Run(async() => {
         while (isRunning)
         {
             RpcCommand?next = await serverCache.DequeueCommand(timeoutMs: -1);  // No timeout
             if (next != null)
             {
                 next.SetState(RpcCommandState.Sent);
                 await ExecuteOnServerNow(next);
                 // In case of a networking problem, wait a second before trying the next command
                 if (next.GetResult().Failure?.IsNetworkProblem ?? false)
                 {
                     await Task.Delay(1000);
                 }
             }
         }
     });
 }