/// <inheritdoc/> public Task <HomeDocument> GetHomeAsync(CancellationToken cancellationToken) { if (_homeDocument != null) { return(InternalTaskExtensions.CompletedTask(_homeDocument)); } UriTemplate template = new UriTemplate("/"); Func <Task <Tuple <IdentityToken, Uri> >, HttpWebRequest> prepareRequest = PrepareRequestAsyncFunc(HttpMethod.GET, template, new Dictionary <string, string>()); Func <Task <HttpWebRequest>, Task <HomeDocument> > requestResource = GetResponseAsyncFunc <HomeDocument>(cancellationToken); Func <Task <HomeDocument>, HomeDocument> cacheResult = task => { _homeDocument = task.Result; return(task.Result); }; return(AuthenticateServiceAsync(cancellationToken) .Select(prepareRequest) .Then(requestResource) .Select(cacheResult)); }
/// <summary> /// Initializes a new instance of the <see cref="Claim"/> class using the provided values. /// </summary> /// <param name="service">The queueing service.</param> /// <param name="queueName">The name of the queue.</param> /// <param name="location">The absolute URI of the claim resource. If no claim was allocated by the server, this value is <see langword="null"/>.</param> /// <param name="timeToLive">The time to live of the claim.</param> /// <param name="age">The age of the claim.</param> /// <param name="owner"><see langword="true"/> if the current instance owns the claim (and is responsible for releasing it); otherwise, <see langword="false"/>.</param> /// <param name="messages">A collection of messages belonging to the claim.</param> /// <exception cref="ArgumentNullException"> /// If <paramref name="service"/> is <see langword="null"/>. /// <para>-or-</para> /// <para>If <paramref name="queueName"/> is <see langword="null"/>.</para> /// <para>-or-</para> /// <para>If <paramref name="messages"/> is <see langword="null"/>.</para> /// </exception> public Claim(IQueueingService service, QueueName queueName, Uri location, TimeSpan timeToLive, TimeSpan age, bool owner, IEnumerable <QueuedMessage> messages) { if (service == null) { throw new ArgumentNullException("service"); } if (queueName == null) { throw new ArgumentNullException("queueName"); } if (messages == null) { throw new ArgumentNullException("messages"); } _service = service; _queueName = queueName; _location = location; _timeToLive = timeToLive; _age = age; _messages = messages.ToArray(); if (!owner) { // prevent this object from releasing the resource _releaseTask = InternalTaskExtensions.CompletedTask(); } }
/// <inheritdoc/> /// <remarks> /// This method returns a cached base address if one is available. If no cached address is /// available, <see cref="ProviderBase{TProvider}.GetServiceEndpoint"/> is called to obtain /// an <see cref="Endpoint"/> with the type <c>rax:queues</c> and preferred type <c>cloudQueues</c>. /// </remarks> protected override Task <Uri> GetBaseUriAsync(CancellationToken cancellationToken) { if (_baseUri != null) { return(InternalTaskExtensions.CompletedTask(_baseUri)); } return(Task.Factory.StartNew( () => { Endpoint endpoint = GetServiceEndpoint(null, "rax:queues", "cloudQueues", null); Uri baseUri = new Uri(_internalUrl ? endpoint.InternalURL : endpoint.PublicURL); _baseUri = baseUri; return baseUri; })); }
/// <inheritdoc/> public Task <Claim> QueryClaimAsync(QueueName queueName, Claim claim, CancellationToken cancellationToken) { if (queueName == null) { throw new ArgumentNullException("queueName"); } if (claim == null) { throw new ArgumentNullException("claim"); } UriTemplate template = new UriTemplate("/queues/{queue_name}/claims/{claim_id}"); var parameters = new Dictionary <string, string>() { { "queue_name", queueName.Value }, { "claim_id", claim.Id.Value } }; Func <Task <Tuple <IdentityToken, Uri> >, HttpWebRequest> prepareRequest = PrepareRequestAsyncFunc(HttpMethod.GET, template, parameters); Func <Task <Tuple <HttpWebResponse, string> >, Task <Tuple <Uri, TimeSpan, TimeSpan, IEnumerable <QueuedMessage> > > > parseResult = task => { // this response uses ContentLocation instead of Location string location = task.Result.Item1.Headers[HttpResponseHeader.ContentLocation]; Uri locationUri = location != null ? new Uri(_baseUri, location) : null; JObject result = JsonConvert.DeserializeObject <JObject>(task.Result.Item2); TimeSpan age = TimeSpan.FromSeconds((int)result["age"]); TimeSpan ttl = TimeSpan.FromSeconds((int)result["ttl"]); IEnumerable <QueuedMessage> messages = result["messages"].ToObject <IEnumerable <QueuedMessage> >(); return(InternalTaskExtensions.CompletedTask(Tuple.Create(locationUri, ttl, age, messages))); }; Func <Task <HttpWebRequest>, Task <Tuple <Uri, TimeSpan, TimeSpan, IEnumerable <QueuedMessage> > > > requestResource = GetResponseAsyncFunc(cancellationToken, parseResult); Func <Task <Tuple <Uri, TimeSpan, TimeSpan, IEnumerable <QueuedMessage> > >, Claim> resultSelector = task => new Claim(this, queueName, task.Result.Item1, task.Result.Item2, task.Result.Item3, false, task.Result.Item4); return(AuthenticateServiceAsync(cancellationToken) .Select(prepareRequest) .Then(requestResource) .Select(resultSelector)); }
/// <summary> /// Asynchronously releases resources owned by this <see cref="Claim"/>. /// </summary> /// <remarks> /// This method calls <see cref="IQueueingService.ReleaseClaimAsync"/> to release messages /// claimed by this claim. To prevent other subscribers from re-claiming the messages, make /// sure to delete the messages before calling <see cref="DisposeAsync"/>. /// </remarks> /// <param name="cancellationToken">The <see cref="CancellationToken"/> that the task will observe.</param> /// <returns>A <see cref="Task"/> object representing the asynchronous operation.</returns> public Task DisposeAsync(CancellationToken cancellationToken) { lock (_lock) { if (_releaseTask == null) { if (_messages.Length == 0) { _releaseTask = InternalTaskExtensions.CompletedTask(); } else { _releaseTask = _service.ReleaseClaimAsync(_queueName, this, cancellationToken); } } } return(_releaseTask); }
/// <inheritdoc/> public Task <bool> CreateQueueAsync(QueueName queueName, CancellationToken cancellationToken) { if (queueName == null) { throw new ArgumentNullException("queueName"); } UriTemplate template = new UriTemplate("/queues/{queue_name}"); var parameters = new Dictionary <string, string> { { "queue_name", queueName.Value } }; Func <Task <Tuple <IdentityToken, Uri> >, HttpWebRequest> prepareRequest = PrepareRequestAsyncFunc(HttpMethod.PUT, template, parameters); Func <Task <Tuple <HttpWebResponse, string> >, Task <bool> > parseResult = task => { if (task.Result.Item1.StatusCode == HttpStatusCode.Created) { return(InternalTaskExtensions.CompletedTask(true)); } else { return(InternalTaskExtensions.CompletedTask(false)); } }; Func <Task <HttpWebRequest>, Task <bool> > requestResource = GetResponseAsyncFunc(cancellationToken, parseResult); return(AuthenticateServiceAsync(cancellationToken) .Select(prepareRequest) .Then(requestResource)); }
/// <inheritdoc/> public Task <Claim> ClaimMessageAsync(QueueName queueName, int?limit, TimeSpan timeToLive, TimeSpan gracePeriod, CancellationToken cancellationToken) { if (queueName == null) { throw new ArgumentNullException("queueName"); } if (limit < 0) { throw new ArgumentOutOfRangeException("limit"); } if (timeToLive <= TimeSpan.Zero) { throw new ArgumentOutOfRangeException("timeToLive"); } if (gracePeriod < TimeSpan.Zero) { throw new ArgumentOutOfRangeException("gracePeriod"); } UriTemplate template = new UriTemplate("/queues/{queue_name}/claims?limit={limit}"); var parameters = new Dictionary <string, string>() { { "queue_name", queueName.Value }, }; if (limit != null) { parameters["limit"] = limit.ToString(); } var request = new ClaimMessagesRequest(timeToLive, gracePeriod); Func <Task <Tuple <IdentityToken, Uri> >, Task <HttpWebRequest> > prepareRequest = PrepareRequestAsyncFunc(HttpMethod.POST, template, parameters, request); Func <Task <Tuple <HttpWebResponse, string> >, Task <Tuple <Uri, IEnumerable <QueuedMessage> > > > parseResult = task => { string location = task.Result.Item1.Headers[HttpResponseHeader.Location]; Uri locationUri = location != null ? new Uri(_baseUri, location) : null; if (task.Result.Item1.StatusCode == HttpStatusCode.NoContent) { // the queue did not contain any messages to claim Tuple <Uri, IEnumerable <QueuedMessage> > result = Tuple.Create(locationUri, Enumerable.Empty <QueuedMessage>()); return(InternalTaskExtensions.CompletedTask(result)); } IEnumerable <QueuedMessage> messages = JsonConvert.DeserializeObject <IEnumerable <QueuedMessage> >(task.Result.Item2); return(InternalTaskExtensions.CompletedTask(Tuple.Create(locationUri, messages))); }; Func <Task <HttpWebRequest>, Task <Tuple <Uri, IEnumerable <QueuedMessage> > > > requestResource = GetResponseAsyncFunc <Tuple <Uri, IEnumerable <QueuedMessage> > >(cancellationToken, parseResult); Func <Task <Tuple <Uri, IEnumerable <QueuedMessage> > >, Claim> resultSelector = task => new Claim(this, queueName, task.Result.Item1, timeToLive, TimeSpan.Zero, true, task.Result.Item2); return(AuthenticateServiceAsync(cancellationToken) .Then(prepareRequest) .Then(requestResource) .Select(resultSelector)); }