View Javadoc
1   /**
2    * Copyright (c) 2014, stateful.co
3    * All rights reserved.
4    *
5    * Redistribution and use in source and binary forms, with or without
6    * modification, are permitted provided that the following conditions
7    * are met: 1) Redistributions of source code must retain the above
8    * copyright notice, this list of conditions and the following
9    * disclaimer. 2) Redistributions in binary form must reproduce the above
10   * copyright notice, this list of conditions and the following
11   * disclaimer in the documentation and/or other materials provided
12   * with the distribution. 3) Neither the name of the stateful.co nor
13   * the names of its contributors may be used to endorse or promote
14   * products derived from this software without specific prior written
15   * permission.
16   *
17   * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
18   * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT
19   * NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
20   * FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
21   * THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
22   * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
23   * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
24   * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
25   * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
26   * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
27   * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
28   * OF THE POSSIBILITY OF SUCH DAMAGE.
29   */
30  package co.stateful.core;
31  
32  import co.stateful.spi.Counter;
33  import co.stateful.spi.Counters;
34  import com.jcabi.aspects.Parallel;
35  import com.jcabi.aspects.Tv;
36  import com.jcabi.urn.URN;
37  import java.math.BigDecimal;
38  import java.security.SecureRandom;
39  import java.util.Set;
40  import java.util.concurrent.Callable;
41  import java.util.concurrent.ConcurrentSkipListSet;
42  import org.hamcrest.MatcherAssert;
43  import org.hamcrest.Matchers;
44  import org.junit.Test;
45  
46  /**
47   * Integration case for {@link DyCounter}.
48   * @author Yegor Bugayenko (yegor@tpc2.com)
49   * @version $Id$
50   */
51  public final class DyCounterITCase {
52  
53      /**
54       * DyCounter can increment and set.
55       * @throws Exception If some problem inside
56       */
57      @Test
58      public void incrementAndSet() throws Exception {
59          final Counters counters = new DefaultUser(
60              new URN("urn:test:7889978")
61          ).counters();
62          final String name = "test-78";
63          counters.create(name);
64          final Counter counter = counters.get(name);
65          final BigDecimal start = new BigDecimal(new SecureRandom().nextLong());
66          counter.set(start);
67          MatcherAssert.assertThat(
68              counter.increment(new BigDecimal(0L)),
69              Matchers.equalTo(start)
70          );
71          final BigDecimal delta = new BigDecimal(new SecureRandom().nextLong());
72          MatcherAssert.assertThat(
73              counter.increment(delta),
74              Matchers.equalTo(start.add(delta))
75          );
76      }
77  
78      /**
79       * DyCounter can increment and set in parallel threads.
80       * @throws Exception If some problem inside
81       */
82      @Test
83      public void incrementAndSetInThreads() throws Exception {
84          final Counters counters = new DefaultUser(
85              new URN("urn:test:78833")
86          ).counters();
87          final String name = "test-9990";
88          counters.create(name);
89          final Counter counter = counters.get(name);
90          final BigDecimal start = new BigDecimal(new SecureRandom().nextLong());
91          counter.set(start);
92          final Set<BigDecimal> values = new ConcurrentSkipListSet<BigDecimal>();
93          new Callable<Void>() {
94              @Override
95              @Parallel(threads = Tv.TWENTY)
96              public Void call() throws Exception {
97                  values.add(counter.increment(new BigDecimal(1L)));
98                  return null;
99              }
100         } .call();
101         MatcherAssert.assertThat(
102             values,
103             Matchers.hasSize(Tv.TWENTY)
104         );
105     }
106 
107 }