View Javadoc
1   // Copyright (c) Microsoft Corporation. All rights reserved.
2   // Licensed under the MIT License.
3   
4   package com.microsoft.azure.servicebus.management;
5   
6   import com.microsoft.azure.servicebus.IMessage;
7   
8   import java.time.Duration;
9   import java.util.List;
10  
11  /**
12   * Represents the metadata description of the queue.
13   */
14  public class QueueDescription {
15      Duration duplicationDetectionHistoryTimeWindow = ManagementClientConstants.DEFAULT_HISTORY_DEDUP_WINDOW;
16      String path;
17      Duration lockDuration = ManagementClientConstants.DEFAULT_LOCK_DURATION;
18      Duration defaultMessageTimeToLive = ManagementClientConstants.MAX_DURATION;
19      Duration autoDeleteOnIdle = ManagementClientConstants.MAX_DURATION;
20      int maxDeliveryCount = ManagementClientConstants.DEFAULT_MAX_DELIVERY_COUNT;
21      String forwardTo = null;
22      String forwardDeadLetteredMessagesTo = null;
23      String userMetadata = null;
24      long maxSizeInMB = ManagementClientConstants.DEFAULT_MAX_SIZE_IN_MB;
25      boolean requiresDuplicateDetection = false;
26      boolean enableDeadLetteringOnMessageExpiration = false;
27      boolean requiresSession = false;
28      boolean enableBatchedOperations = true;
29      boolean enablePartitioning = false;
30      EntityStatus status = EntityStatus.Active;
31      List<AuthorizationRule> authorizationRules = null;
32  
33      /**
34       * Initializes a new instance of QueueDescription with the specified relative path.
35       * @param path - Path of the topic.
36       *             Max length is 260 chars. Cannot start or end with a slash.
37       *             Cannot have restricted characters: '@','?','#','*'
38       */
39      public QueueDescription(String path) {
40          this.setPath(path);
41      }
42  
43      /**
44       * @return The path of the queue.
45       */
46      public String getPath() {
47          return this.path;
48      }
49  
50      /**
51       * @param path - The path of queue. Max length is 260 chars.
52       *             Cannot start or end with a slash.
53       *             Cannot have restricted characters: '@','?','#','*'
54       */
55      private void setPath(String path) {
56          EntityNameHelper.checkValidQueueName(path);
57          this.path = path;
58      }
59  
60      /**
61       * The amount of time that the message is locked by a given receiver
62       * so that no other receiver receives the same message.
63       * @return The duration of a peek lock. Default value is 60 seconds.
64       */
65      public Duration getLockDuration() {
66          return this.lockDuration;
67      }
68  
69      /**
70       * Sets The amount of time that the message is locked by a given receiver
71       * so that no other receiver receives the same message.
72       * @param lockDuration - The duration of a peek lock. Max value is 5 minutes.
73       */
74      public void setLockDuration(Duration lockDuration) {
75          if (lockDuration == null) {
76              throw new IllegalArgumentException("Value cannot be null");
77          }
78          this.lockDuration = lockDuration;
79          if (this.lockDuration.compareTo(ManagementClientConstants.MAX_DURATION) > 0) {
80              this.lockDuration = ManagementClientConstants.MAX_DURATION;
81          }
82      }
83  
84      /**
85       * @return the maximum size of the queue in megabytes, which is the size of memory allocated for the queue.
86       * Default value is 1024.
87       */
88      public long getMaxSizeInMB() {
89          return this.maxSizeInMB;
90      }
91  
92      /**
93       * @param maxSize - Maximum size of the queue in megabytes, which is the size of memory allocated for the queue.
94       */
95      public void setMaxSizeInMB(long maxSize) {
96          this.maxSizeInMB = maxSize;
97      }
98  
99      /**
100      * If enabled, duplicate messages having same {@link IMessage#getMessageId()} and sent to queue
101      * within duration of {@link #getDuplicationDetectionHistoryTimeWindow} will be discarded.
102      * @return value indicating if the queue requires guard against duplicate messages.
103     */
104     public boolean isRequiresDuplicateDetection() {
105         return requiresDuplicateDetection;
106     }
107 
108     /**
109      * @param requiresDuplicateDetection - True if duplicate detection needs to be enabled.
110      * See also - {@link #isRequiresDuplicateDetection()}
111      */
112     public void setRequiresDuplicateDetection(boolean requiresDuplicateDetection) {
113         this.requiresDuplicateDetection = requiresDuplicateDetection;
114     }
115 
116     /**
117      * @return boolean that indicates whether the queue supports the concept of session. Sessionful-messages follow FIFO ordering.
118      */
119     public boolean isRequiresSession() {
120         return requiresSession;
121     }
122 
123     /**
124      * @param requiresSession - True if queue should support sessions.
125      */
126     public void setRequiresSession(boolean requiresSession) {
127         this.requiresSession = requiresSession;
128     }
129 
130     /**
131      * Time-To-Live is the duration after which the message expires, starting from when
132      * the message is sent to Service Bus.
133      * This is the default value used when {@link IMessage#getTimeToLive()} is not set on a message itself.
134      * Messages older than their TimeToLive value will expire and no longer be retained in the message store.
135      * Subscribers will be unable to receive expired messages.
136      * @return The default time to live value for the messages. Default value is {@link ManagementClientConstants#MAX_DURATION}
137      */
138     public Duration getDefaultMessageTimeToLive() {
139         return defaultMessageTimeToLive;
140     }
141 
142     /**
143      * @param defaultMessageTimeToLive - The default message time to live value.
144      * Value cannot be lower than 1 second.
145      * See {@link #getDefaultMessageTimeToLive()}
146      */
147     public void setDefaultMessageTimeToLive(Duration defaultMessageTimeToLive) {
148         if (defaultMessageTimeToLive == null
149             || (defaultMessageTimeToLive.compareTo(ManagementClientConstants.MIN_ALLOWED_TTL) < 0
150                 || defaultMessageTimeToLive.compareTo(ManagementClientConstants.MAX_ALLOWED_TTL) > 0)) {
151             throw new IllegalArgumentException(
152                     String.format("The value must be between %s and %s.",
153                     ManagementClientConstants.MAX_ALLOWED_TTL,
154                             ManagementClientConstants.MIN_ALLOWED_TTL));
155         }
156 
157         this.defaultMessageTimeToLive = defaultMessageTimeToLive;
158         if (this.defaultMessageTimeToLive.compareTo(ManagementClientConstants.MAX_DURATION) > 0) {
159             this.defaultMessageTimeToLive = ManagementClientConstants.MAX_DURATION;
160         }
161     }
162 
163     /**
164      * @return The idle interval after which the queue is automatically deleted.
165      * Default value is {@link ManagementClientConstants#MAX_DURATION}
166      */
167     public Duration getAutoDeleteOnIdle() {
168         return autoDeleteOnIdle;
169     }
170 
171     /**
172      * @param autoDeleteOnIdle - The idle interval after which the queue is automatically deleted.
173      * The minimum duration is 5 minutes.
174      */
175     public void setAutoDeleteOnIdle(Duration autoDeleteOnIdle) {
176         if (autoDeleteOnIdle == null
177             || autoDeleteOnIdle.compareTo(ManagementClientConstants.MIN_ALLOWED_AUTODELETE_DURATION) < 0) {
178             throw new IllegalArgumentException(
179                     String.format("The value must be greater than %s.",
180                             ManagementClientConstants.MIN_ALLOWED_AUTODELETE_DURATION));
181         }
182 
183         this.autoDeleteOnIdle = autoDeleteOnIdle;
184         if (this.autoDeleteOnIdle.compareTo(ManagementClientConstants.MAX_DURATION) > 0) {
185             this.autoDeleteOnIdle = ManagementClientConstants.MAX_DURATION;
186         }
187     }
188 
189     /**
190      * Indicates whether this queue has dead letter support when a message expires.
191      * @return If true, the expired messages are moved to dead-letter sub-queue.
192      * Default value is false.
193      */
194     public boolean isEnableDeadLetteringOnMessageExpiration() {
195         return enableDeadLetteringOnMessageExpiration;
196     }
197 
198     /**
199      * @param enableDeadLetteringOnMessageExpiration - True if messages should be dead-lettered on expiration.
200      * See {@link #isEnableDeadLetteringOnMessageExpiration()}
201      */
202     public void setEnableDeadLetteringOnMessageExpiration(boolean enableDeadLetteringOnMessageExpiration) {
203         this.enableDeadLetteringOnMessageExpiration = enableDeadLetteringOnMessageExpiration;
204     }
205 
206     /**
207      * @return The duration of duplicate detection history that is maintained by the service.
208      * The default value is 1 minute.
209      */
210     public Duration getDuplicationDetectionHistoryTimeWindow() {
211         return duplicationDetectionHistoryTimeWindow;
212     }
213 
214     /**
215      * @param duplicationDetectionHistoryTimeWindow - The duration of duplicate detection history that is maintained by the service.
216      * Max value is 1 day and minimum is 20 seconds.
217      */
218     public void setDuplicationDetectionHistoryTimeWindow(Duration duplicationDetectionHistoryTimeWindow) {
219         if (duplicationDetectionHistoryTimeWindow == null
220             || (duplicationDetectionHistoryTimeWindow.compareTo(ManagementClientConstants.MIN_DUPLICATE_HISTORY_DURATION) < 0
221                 || duplicationDetectionHistoryTimeWindow.compareTo(ManagementClientConstants.MAX_DUPLICATE_HISTORY_DURATION) > 0)) {
222             throw new IllegalArgumentException(
223                     String.format("The value must be between %s and %s.",
224                             ManagementClientConstants.MIN_DUPLICATE_HISTORY_DURATION,
225                             ManagementClientConstants.MAX_DUPLICATE_HISTORY_DURATION));
226         }
227 
228         this.duplicationDetectionHistoryTimeWindow = duplicationDetectionHistoryTimeWindow;
229         if (this.duplicationDetectionHistoryTimeWindow.compareTo(ManagementClientConstants.MAX_DURATION) > 0) {
230             this.duplicationDetectionHistoryTimeWindow = ManagementClientConstants.MAX_DURATION;
231         }
232     }
233 
234     /**
235      * The maximum delivery count of a message before it is dead-lettered.
236      * The delivery count is increased when a message is received in {@link com.microsoft.azure.servicebus.ReceiveMode#PEEKLOCK} mode
237      * and didn't complete the message before the message lock expired.
238      * @return Default value is 10.
239      */
240     public int getMaxDeliveryCount() {
241         return maxDeliveryCount;
242     }
243 
244     /**
245      * The maximum delivery count of a message before it is dead-lettered.
246      * The delivery count is increased when a message is received in {@link com.microsoft.azure.servicebus.ReceiveMode#PEEKLOCK} mode
247      * and didn't complete the message before the message lock expired.
248      * @param maxDeliveryCount - Minimum value is 1.
249      */
250     public void setMaxDeliveryCount(int maxDeliveryCount) {
251         if (maxDeliveryCount < ManagementClientConstants.MIN_ALLOWED_MAX_DELIVERYCOUNT) {
252             throw new IllegalArgumentException(
253                     String.format("The value must be greater than %s.",
254                             ManagementClientConstants.MIN_ALLOWED_MAX_DELIVERYCOUNT));
255         }
256 
257         this.maxDeliveryCount = maxDeliveryCount;
258     }
259 
260     /**
261      * @return Indicates whether server-side batched operations are enabled.
262      * Defaults to true.
263      */
264     public boolean isEnableBatchedOperations() {
265         return enableBatchedOperations;
266     }
267 
268     /**
269      * @param enableBatchedOperations - Indicates whether server-side batched operations are enabled.
270      */
271     public void setEnableBatchedOperations(boolean enableBatchedOperations) {
272         this.enableBatchedOperations = enableBatchedOperations;
273     }
274 
275     /**
276      * @return The {@link AuthorizationRule} on the queue to control user access at entity level.
277      */
278     public List<AuthorizationRule> getAuthorizationRules() {
279         return authorizationRules;
280     }
281 
282     /**
283      * @param  authorizationRules - The {@link AuthorizationRule} on the queue to control user access at entity level.
284      */
285     public void setAuthorizationRules(List<AuthorizationRule> authorizationRules) {
286         this.authorizationRules = authorizationRules;
287     }
288 
289     /**
290      * Gets the status of the entity. When an entity is disabled, that entity cannot send or receive messages.
291      * @return The current status of the queue (Enabled / Disabled).
292      * The default value is Enabled.
293      */
294     public EntityStatus getEntityStatus() {
295         return this.status;
296     }
297 
298     /**
299      * @param status - the status of the queue (Enabled / Disabled).
300      * When an entity is disabled, that entity cannot send or receive messages.
301      */
302     public void setEntityStatus(EntityStatus status) {
303         this.status = status;
304     }
305 
306     /**
307      * @return The path of the recipient entity to which all the messages sent to the queue are forwarded to.
308      * If set, user cannot manually receive messages from this queue. The destination entity
309      * must be an already existing entity.
310      */
311     public String getForwardTo() {
312         return forwardTo;
313     }
314 
315     /**
316      * @param forwardTo - The path of the recipient entity to which all the messages sent to the queue are forwarded to.
317      * If set, user cannot manually receive messages from this queue. The destination entity
318      * must be an already existing entity.
319      */
320     public void setForwardTo(String forwardTo) {
321         if (forwardTo == null || forwardTo.isEmpty()) {
322             this.forwardTo = forwardTo;
323             return;
324         }
325 
326         EntityNameHelper.checkValidQueueName(forwardTo);
327         if (this.path.equals(forwardTo)) {
328             throw new IllegalArgumentException("Entity cannot have auto-forwarding policy to itself");
329         }
330 
331         this.forwardTo = forwardTo;
332     }
333 
334     /**
335      * @return The path of the recipient entity to which all the dead-lettered messages of this queue are forwarded to.
336      * If set, user cannot manually receive dead-lettered messages from this queue. The destination
337      * entity must already exist.
338      */
339     public String getForwardDeadLetteredMessagesTo() {
340         return forwardDeadLetteredMessagesTo;
341     }
342 
343     /**
344      * @param forwardDeadLetteredMessagesTo - The path of the recipient entity to which all the dead-lettered messages of this queue are forwarded to.
345      * If set, user cannot manually receive dead-lettered messages from this queue. The destination
346      * entity must already exist.
347      */
348     public void setForwardDeadLetteredMessagesTo(String forwardDeadLetteredMessagesTo) {
349         if (forwardDeadLetteredMessagesTo == null || forwardDeadLetteredMessagesTo.isEmpty()) {
350             this.forwardDeadLetteredMessagesTo = forwardDeadLetteredMessagesTo;
351             return;
352         }
353 
354         EntityNameHelper.checkValidQueueName(forwardDeadLetteredMessagesTo);
355         if (this.path.equals(forwardDeadLetteredMessagesTo)) {
356             throw new IllegalArgumentException("Entity cannot have auto-forwarding policy to itself");
357         }
358 
359         this.forwardDeadLetteredMessagesTo = forwardDeadLetteredMessagesTo;
360     }
361 
362     /**
363      * @return boolean indicating whether the queue is to be partitioned across multiple message brokers.
364      * Defaults to false
365      */
366     public boolean isEnablePartitioning() {
367         return enablePartitioning;
368     }
369 
370     /**
371      * @param enablePartitioning - true if queue is to be partitioned across multiple message brokers.
372      */
373     public void setEnablePartitioning(boolean enablePartitioning) {
374         this.enablePartitioning = enablePartitioning;
375     }
376 
377     /**
378      * @return Custom metdata that user can associate with the description.
379      */
380     public String getUserMetadata() {
381         return userMetadata;
382     }
383 
384     /**
385      * @param userMetadata - Custom metdata that user can associate with the description.
386      * Cannot be null. Max length is 1024 chars
387      */
388     public void setUserMetadata(String userMetadata) {
389         if (userMetadata == null) {
390             throw new IllegalArgumentException("Value cannot be null");
391         }
392 
393         if (userMetadata.length() > ManagementClientConstants.MAX_USERMETADATA_LENGTH) {
394             throw new IllegalArgumentException("Length cannot cross " + ManagementClientConstants.MAX_USERMETADATA_LENGTH + " characters");
395         }
396 
397         this.userMetadata = userMetadata;
398     }
399 
400     @Override
401     public boolean equals(Object o) {
402         if (o == this) {
403             return true;
404         }
405 
406         if (!(o instanceof QueueDescription)) {
407             return false;
408         }
409 
410         QueueDescription../../com/microsoft/azure/servicebus/management/QueueDescription.html#QueueDescription">QueueDescription other = (QueueDescription) o;
411         if (this.path.equalsIgnoreCase(other.path)
412                 && this.autoDeleteOnIdle.equals(other.autoDeleteOnIdle)
413                 && this.defaultMessageTimeToLive.equals(other.defaultMessageTimeToLive)
414                 && (!this.requiresDuplicateDetection || this.duplicationDetectionHistoryTimeWindow.equals(other.duplicationDetectionHistoryTimeWindow))
415                 && this.enableBatchedOperations == other.enableBatchedOperations
416                 && this.enableDeadLetteringOnMessageExpiration == other.enableDeadLetteringOnMessageExpiration
417                 && this.enablePartitioning == other.enablePartitioning
418                 && (this.forwardTo == null ? other.forwardTo == null : this.forwardTo.equalsIgnoreCase(other.forwardTo))
419                 && (this.forwardDeadLetteredMessagesTo == null ? other.forwardDeadLetteredMessagesTo == null : this.forwardDeadLetteredMessagesTo.equalsIgnoreCase(other.forwardDeadLetteredMessagesTo))
420                 && this.lockDuration.equals(other.lockDuration)
421                 && this.maxDeliveryCount == other.maxDeliveryCount
422                 && this.maxSizeInMB == other.maxSizeInMB
423                 && this.requiresDuplicateDetection == other.requiresDuplicateDetection
424                 && this.requiresSession == other.requiresSession
425                 && this.status.equals(other.status)
426                 && (this.userMetadata == null ? other.userMetadata == null : this.userMetadata.equals(other.userMetadata))
427                 && AuthorizationRuleSerializer.equals(this.authorizationRules, other.authorizationRules)) {
428             return true;
429         }
430 
431         return false;
432     }
433 
434     @Override
435     public int hashCode() {
436         return this.path.hashCode();
437     }
438 }