Guest User

Untitled

a guest
Apr 23rd, 2018
108
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C# 4.64 KB | None | 0 0
  1. using System;
  2. using System.Collections.Generic;
  3. using System.Linq;
  4. using System.Text;
  5. using System.Threading;
  6. using System.Threading.Tasks;
  7. using System.Timers;
  8.  
  9. namespace GWork
  10. {
  11.     public class RequestList
  12.     {
  13.         //create an event for notifing when item was added (use empty delegate to avoid checks if OnItemQueued is null)
  14.         public event Action<RequestMessage> OnRequestMessageAdded = delegate { };
  15.         public event Action<RequestMessage> OnRequestMessageStarted = delegate { };
  16.         public event Action<RequestMessage, ResponseMessage> OnRequestMessageDone = delegate { };
  17.  
  18.         Dictionary<Guid, RequestMessage> requests;
  19.         public RequestList()
  20.         {
  21.             requests = new Dictionary<Guid, RequestMessage>();
  22.         }
  23.  
  24.         public void Add(RequestMessage request)
  25.         {
  26.             request.Status = MessageStatus.Pending;
  27.             //Create a cancellation token source, this will be used to cancel a task
  28.             request.RequestCancelToken = new CancellationTokenSource();
  29.             requests.Add(request.MessageID, request);
  30.             OnRequestMessageAdded(request);
  31.             //Create and start a task and pass on the cancellation token to it
  32.             var task = Task.Factory.StartNew(() =>
  33.                 //We also pass on the token to the operation for it access the token to check for
  34.                 //cancellation
  35.                 Process(request), request.RequestCancelToken.Token
  36.             );
  37.  
  38.         }
  39.  
  40.         public void Cancel(RequestMessage request)
  41.         {
  42.             var dictRequestValue = (from x in requests
  43.                           where x.Key == request.MessageID
  44.                           select x).First().Value;
  45.  
  46.             dictRequestValue.RequestCancelToken.Cancel();
  47.             dictRequestValue.Status = MessageStatus.Cancelled;
  48.         }
  49.  
  50.         private void ProcessLogin(RequestMessage request, CancellationToken token)
  51.         {
  52.             //This simulates work
  53.             var sw = new SpinWait();
  54.             for (var i = 0; i < 1000; i++)
  55.             {
  56.                 for (int j = 0; j < 50; j++)
  57.                 {
  58.                     sw.SpinOnce();
  59.                 }
  60.                 //Check for requested cancellation amidst execution logic
  61.                 if (token.IsCancellationRequested)
  62.                 {
  63.                     //This throws an OperationCanceledException if the token has had cancellation requested
  64.                     token.ThrowIfCancellationRequested();
  65.                 }
  66.             }
  67.         }
  68.  
  69.         private ResponseMessage ProcessRequest(RequestMessage request, CancellationToken token)
  70.         {
  71.             ResponseMessage response = new ResponseMessage(request);
  72.             try
  73.             {
  74.                 //Check for requested cancellation before processing message
  75.                 if (token.IsCancellationRequested)
  76.                 {
  77.                     //This throws an OperationCanceledException if the token has had cancellation requested
  78.                     token.ThrowIfCancellationRequested();
  79.                 }
  80.  
  81.                 switch (request.MessageType)
  82.                 {
  83.                     case RequestMessageType.Login:
  84.                         ProcessLogin(request, token);
  85.                         break;
  86.  
  87.                 }
  88.                 response.Status = MessageStatus.Done;
  89.             }
  90.             catch (OperationCanceledException)
  91.             {
  92.                 response.Status = MessageStatus.Cancelled;
  93.             }
  94.             catch (Exception ex)
  95.             {
  96.                 response.Status = MessageStatus.Error;
  97.                 response.MessageData = String.Format("Error: {0}.  Trace{1}.", ex.Message, ex.StackTrace);
  98.             }
  99.             return response;
  100.         }
  101.  
  102.         //This method contains the operation being executed by the task in parallel
  103.         private void Process(RequestMessage request)
  104.         {
  105.  
  106.             request.Status = MessageStatus.Processing;
  107.             CancellationToken token = request.RequestCancelToken.Token;
  108.  
  109.             System.Timers.Timer timeout = new System.Timers.Timer(request.Timeout);
  110.             timeout.AutoReset = false;
  111.             timeout.Elapsed += new ElapsedEventHandler((s, e) =>
  112.             {
  113.                 request.RequestCancelToken.Cancel();
  114.             });
  115.             timeout.Start();
  116.  
  117.             ResponseMessage response = ProcessRequest(request, token);
  118.  
  119.            
  120.             //This code is reached if the task gets to complete prior to a cancellation request
  121.             request.Status = MessageStatus.Done;
  122.             OnRequestMessageDone(request, response);
  123.         }
  124.  
  125.  
  126.     }
  127. }
Add Comment
Please, Sign In to add comment