tag:blogger.com,1999:blog-72620352511342826702024-03-21T07:02:28.573+01:00Przybysz Dominik TechBlogSoftware development and more...Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.comBlogger39125tag:blogger.com,1999:blog-7262035251134282670.post-58069305299334471362019-01-10T17:57:00.000+01:002019-01-10T17:57:46.250+01:00Not so easy functional programming in JavaScript<h2 id="introduction">Introduction</h2><p>JavaScript allows for operating on arrays in a functional way, e.g. using <code>filter</code> or <code>map</code> functions. As an argument for these functions we can pass lambda expression or function reference. Is there a difference between them? The answer is yes.</p><h2 id="whats-the-problem">What's the problem?</h2><p>In our project we are builing a mapping using <code>String.fromCharCode</code> function. To simplify the usage of this function looked similar to:</p><pre class="brush: javascript">[66, 67, 68].map(v => String.fromCharCode(v))</pre><p>When we run this code with node we received <code>[ 'B', 'C', 'D' ]</code>, but when we decided to refactor it to use function reference the result was different:</p><pre class="brush: javascript">> [66, 67, 68].map(String.fromCharCode)
[ 'B\u0000\u0000', 'C\u0001\u0000', 'D\u0002\u0000' ]</pre><h2 id="what-happened">What happened?</h2><p>To find the reason of this behavior, let's first play with function <code>String.fromCharCode</code> alone:</p><pre class="brush: javascript">> String.fromCharCode(66)
'B'
> String.fromCharCode([66, 67, 68])
'\u0000'
> String.fromCharCode(66, 67, 68)
'BCD'</pre><p><code>String.fromCharCode</code> deals with various types and numbers of arguments.</p><p>Now, let's examine the function <code>map</code>:</p><pre class="brush: javascript">> [66, 67, 68].map(v => v)
[ 66, 67, 68 ]
> [66, 67, 68].map((v, u) => [v, u])
[ [ 66, 0 ], [ 67, 1 ], [ 68, 2 ] ]
> [66, 67, 68].map((v, u, w) => [v, u, w])
[ [ 66, 0, [ 66, 67, 68 ] ],
[ 67, 1, [ 66, 67, 68 ] ],
[ 68, 2, [ 66, 67, 68 ] ] ]</pre><p><code>map</code>, like many other array functions, passes always <a href="https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/map#Syntax">three arguments to function</a>. First is current value, second is the index of current value and third is the whole array.</p><p>It means that passing <code>String.fromCharCode</code> to <code>map</code> function under the hood looks like this:</p><pre class="brush: javascript">> [66, 67, 68].map((v, u, w) => String.fromCharCode(v, u, w))
[ 'B\u0000\u0000', 'C\u0001\u0000', 'D\u0002\u0000' ]</pre><p>and it is equal to the initial example.</p><h2 id="conclusion">Conclusion</h2><p>We have to be careful when we want to use a function which can take more than one argument, but we want to pass only the value. We have to pass the function as a lambda expression:</p><pre class="brush: javascript">> [66, 67, 68].map(v => String.fromCharCode(v))
[ 'B', 'C', 'D' ]</pre><p>or create another function which ensures that only the first argument will be passed to desired function:</p><pre class="brush: javascript">> const useOnlyValue = f => v => f(v);
undefined
> [66, 67, 68].map(useOnlyValue(String.fromCharCode))
[ 'B', 'C', 'D' ]</pre>Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0tag:blogger.com,1999:blog-7262035251134282670.post-18431192193506492952019-01-03T18:52:00.001+01:002022-03-18T16:45:01.633+01:00Loops performance in Groovy<h2 id="introduction">Introduction</h2><p>In the <a href="https://adventofcode.com/2018">2018 Advent of Code</a> challenged I solved all the puzzles in <a href="http://groovy-lang.org/">Groovy</a>. It is pretty obvious, that choosing good data structure is the most important to obtain performant solution. However, the way we iterate over those structures is also very significant, at least when using Groovy.</p><h2 id="measuring-performance">Measuring performance</h2><p>I want to measure how long it takes to sum some numbers. For testing performance of loops I prepared a small function that simply sums some numbers:</p><pre class="brush: java">void printAddingTime(String message, long to, Closure<Long> adder) {
LocalTime start = LocalTime.now()
long sum = adder(to)
println("$message: $sum calculated in ${Duration.between(start, LocalTime.now()).toMillis()} ms")
}</pre><p>Pseudo code for summing functions is below:</p><pre class="brush: pascal">for i = 1 to n
for j = 1 to n
sum += i * j
end
end</pre><h2 id="loops-types">Loops types</h2><p>Let's implement the summing function in various ways.</p><h3 id="collect-and-sum"><code>collect</code> and <code>sum</code></h3><p>First loop type is to use built-in (by Groovy) function <code>collect</code> and <code>sum</code> on collections (<code>Range</code> it this example):</p><pre class="brush: java">(1..n).collect { long i ->
(1..n).collect { long j ->
i * j
}.sum()
}.sum()</pre><h3 id="each"><code>each</code></h3><p>Next, let's write the same function using <code>each</code> built-in function on collections (<code>Range</code> it this example) and then add results to accumulator variable:</p><pre class="brush: java">long sum = 0
(1..n).each { long i ->
(1..n).each { long j ->
sum += i * j
}
}
return sum</pre><h3 id="times"><code>times</code></h3><p>Now instead of using <code>each</code> we could use the function <code>times</code> built-in on <code>Number</code> by Groovy:</p><pre class="brush: java">long sum = 0
n.times { long i ->
n.times { long j ->
sum += (i + 1)*(j+1)
}
}
return sum</pre><p>We have to add <code>1</code> to <code>i</code> and <code>j</code> because times generates numbers from <code>0</code> to <code>n</code> exclusive.</p><h3 id="longstream-with-sum"><code>LongStream</code> with <code>sum</code></h3><p>Java 8 came with a new feature - streams. One example of streams is <a href="https://docs.oracle.com/javase/8/docs/api/java/util/stream/LongStream.html"><code>LongStream</code></a>. Fortunately, it has <code>sum</code> built-in function, which we can use:</p><pre class="brush: java">LongStream.range(0, n).map { i ->
LongStream.range(0, n).map { j ->
(i + 1) * (j + 1)
}.sum()
}.sum()</pre><p><code>LongStream</code> generates numbers in the same way as <code>times</code> function, so we also have to add <code>1</code> to <code>i</code> and <code>j</code> here.</p><h3 id="longstream-with-manual-sum"><code>LongStream</code> with manual sum</h3><p>Instead of <code>sum</code> function on <code>LongStream</code>, we can add all numbers manually:</p><pre class="brush: java">long sum = 0
LongStream.range(0, n).forEach { i ->
LongStream.range(0, n).forEach { j ->
sum += (i + 1) * (j + 1)
}
}
return sum</pre><h3 id="while"><code>while</code></h3><p>Of course since Groovy inherits from Java a big part of its syntax, we can use the <code>while</code> loop:</p><pre class="brush: java">long sum = 0
long i = 1
while(i <= n){
long j = 1
while(j <= n){
sum+= i*j
++j
}
++i
}
return sum</pre><h3 id="for"><code>for</code></h3><p>As we can use <code>while</code>, we can also use <code>for</code> loop in Groovy:</p><pre class="brush: java">long sum = 0
for (long i = 1; i <= n; ++i) {
for (long j = 1; j <= n; ++j) {
sum += i * j
}
}
return sum</pre><h2 id="results">Results</h2><p>My tests I run on Java <code>1.8</code> and Groovy <code>2.5.5</code>. Script <code>loops.groovy</code> was fired using bash script:</p><pre class="brush: bash">#!/bin/sh
for x in 10 100 1000 10000 100000; do
echo $x
groovy loops.groovy $x
echo
done</pre><p>Values are in milliseconds</p><table style="border-collapse: collapse;"><thead>
<tr class="header"> <th style="border: 1px solid white;" align="left">Loop n</th> <th style="border: 1px solid white;" align="right">10</th> <th style="border: 1px solid white;" align="right">100</th> <th style="border: 1px solid white;" align="right">1000</th> <th style="border: 1px solid white;" align="right">10000</th> <th style="border: 1px solid white;" align="right">100000</th> </tr>
</thead> <tbody>
<tr class="odd"> <td style="border: 1px solid white;" align="left"><code>collect</code> + <code>sum</code></td> <td style="border: 1px solid white;" align="right">7</td> <td style="border: 1px solid white;" align="right">22</td> <td style="border: 1px solid white;" align="right">216</td> <td style="border: 1px solid white;" align="right">16244</td> <td style="border: 1px solid white;" align="right">1546822</td> </tr>
<tr class="even"> <td style="border: 1px solid white;" align="left"><code>each</code></td> <td style="border: 1px solid white;" align="right">12</td> <td style="border: 1px solid white;" align="right">17</td> <td style="border: 1px solid white;" align="right">118</td> <td style="border: 1px solid white;" align="right">7332</td> <td style="border: 1px solid white;" align="right">706781</td> </tr>
<tr class="odd"> <td style="border: 1px solid white;" align="left"><code>times</code></td> <td style="border: 1px solid white;" align="right">2</td> <td style="border: 1px solid white;" align="right">10</td> <td style="border: 1px solid white;" align="right">109</td> <td style="border: 1px solid white;" align="right">8264</td> <td style="border: 1px solid white;" align="right">708684</td> </tr>
<tr class="even"> <td style="border: 1px solid white;" align="left"><code>LongStream</code> + <code>sum</code></td> <td style="border: 1px solid white;" align="right">7</td> <td style="border: 1px solid white;" align="right">17</td> <td style="border: 1px solid white;" align="right">127</td> <td style="border: 1px solid white;" align="right">7679</td> <td style="border: 1px solid white;" align="right">763341</td> </tr>
<tr class="odd"> <td style="border: 1px solid white;" align="left"><code>LongStream</code> + manual sum</td> <td style="border: 1px solid white;" align="right">18</td> <td style="border: 1px solid white;" align="right">35</td> <td style="border: 1px solid white;" align="right">149</td> <td style="border: 1px solid white;" align="right">6857</td> <td style="border: 1px solid white;" align="right">680804</td> </tr>
<tr class="even"> <td style="border: 1px solid white;" align="left"><code>while</code></td> <td style="border: 1px solid white;" align="right">8</td> <td style="border: 1px solid white;" align="right">20</td> <td style="border: 1px solid white;" align="right">103</td> <td style="border: 1px solid white;" align="right">3166</td> <td style="border: 1px solid white;" align="right">301967</td> </tr>
<tr class="odd"> <td style="border: 1px solid white;" align="left"><code>for</code></td> <td style="border: 1px solid white;" align="right">7</td> <td style="border: 1px solid white;" align="right">10</td> <td style="border: 1px solid white;" align="right">25</td> <td style="border: 1px solid white;" align="right">359</td> <td style="border: 1px solid white;" align="right">27966</td> </tr>
</tbody> </table><p>As you can spot, for small amount of iterations using built-in Groovy functions is good enough, but for much bigger amount of iterations we should use <code>while</code> or <code>for</code> loops like in plain, old Java.</p><h2 id="show-me-the-code">Show me the code</h2><p>Code for those examples are available <a href="https://gist.github.com/alien11689/3d92915142d70856f1fae2bd8351b7ea">here</a>. You can run those examples on your machine and check performance on your own.</p>Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0tag:blogger.com,1999:blog-7262035251134282670.post-2016223546304179092018-09-27T19:31:00.003+02:002022-03-18T16:56:12.430+01:00Testing Kotlin with Spock Part 3 - Interface default method<p>Kotlin allows you to put method implementation in an interface. The same mechanism can be found in Java interfaces as default methods (and also Groovy or Scala traits). Let's see the difference between the Kotlin and Java default methods in interface by testing it with Groovy and <a href="http://spockframework.org/">Spock</a>.</p><h2 id="what-do-we-want-to-test">What do we want to test?</h2><p>We often have an interface for access object from the database. In domain, they might look similar to this <code>KotlinOrderRepository</code>:</p><pre class="brush: java">interface KotlinOrderRepository {
fun save(order: Order)
fun find(orderId: OrderId): Order?
fun get(orderId: OrderId): Order =
find(orderId) ?: throw NotFound()
}</pre><h2 id="how-to-fake-it-with-groovy">How to fake it with Groovy?</h2><p>When we want to use such interface in tests, we can, of course, mock it. However, it is far better to fake repositories with a simple, in-memory implementation. Let's create <code>FakeKotlinOrderRepository</code> in Groovy:</p><pre class="brush: java">class FakeKotlinOrderRepository implements KotlinOrderRepository {
private Map<OrderId, Order> data = [:]
@Override
void save(Order order) {
data[order.id] = order
}
@Override
Order find(OrderId orderId) {
return data[orderId]
}
}</pre><p>Unfortunately, this causes a compilation error</p><pre class="brush: java">/testing-kotlin-in-spock/src/test/groovy/com/github/alien11689/testingkotlinwithspock/defaultmethod/FakeKotlinOrderRepository.groovy: 3: Can't have an abstract method in a non-abstract class. The class 'com.github.alien11689.testingkotlinwithspock.defaultmethod.FakeKotlinOrderRepository' must be declared abstract or the method 'com.github.alien11689.testingkotlinwithspock.defaultmethod.Order get(com.github.alien11689.testingkotlinwithspock.defaultmethod.OrderId)' must be implemented.
@ line 3, column 1.
class FakeKotlinOrderRepository implements KotlinOrderRepository {
^
1 error</pre><p>The compiler doesn't see the implementation of the <code>get</code> method in the Kotlin interface. We have to use some <em>magic</em> to make it work in groovy.</p><h2 id="solution">Solution</h2><p>To solve the problem, let's look into the generated classes:</p><pre class="brush: java">$ ls build/classes/main/com/github/alien11689/testingkotlinwithspock/defaultmethod/
JavaOrderRepository.class
KotlinOrderRepository.class
KotlinOrderRepository$DefaultImpls.class
NotFound.class
Order.class
OrderId.class</pre><p>The <code>KotlinOrderRepository$DefaultImpls</code> class is the one we're looking for as we can use it in Groovy to implement the missing operation.</p><pre class="brush: java">class FakeKotlinOrderRepository implements KotlinOrderRepository {
// ...
Order get(OrderId orderId) {
return KotlinOrderRepository.DefaultImpls.get(this, orderId)
}
}</pre><p>Now the code compiles and tests pass:</p><pre class="brush: java">class KotlinRepositoryWithDefaultMethodTest extends Specification {
OrderId orderId = new OrderId(UUID.randomUUID() as String)
Order order = new Order(orderId, 'data')
KotlinOrderRepository kotlinOrderRepository = new FakeKotlinOrderRepository()
def 'should get order from kotlin repository'() {
given:
kotlinOrderRepository.save(order)
expect:
kotlinOrderRepository.get(orderId) == order
}
def 'should throw NotFound when order does not exist in kotlin repository'() {
when:
kotlinOrderRepository.get(orderId)
then:
thrown(NotFound)
}
}</pre><h3 id="is-there-the-same-problem-with-java">Is there the same problem with Java?</h3><p>Let's have a quick look at how this works with Java interfaces. If we write a similar repository in Java:</p><pre class="brush: java">public interface JavaOrderRepository {
void save(Order order);
Optional<Order> find(OrderId orderId);
default Order get(OrderId orderId) {
return find(orderId).orElseThrow(NotFound::new);
}
}</pre><p>and create a fake implementation in Groovy:</p><pre class="brush: java">class FakeJavaOrderRepository implements JavaOrderRepository {
private Map<OrderId, Order> data = [:]
@Override
void save(Order order) {
data[order.id] = order
}
@Override
Optional<Order> find(OrderId orderId) {
return Optional.ofNullable(data[orderId])
}
}</pre><p>there is no compilation error and the tests pass:</p><pre class="brush: java">class JavaRepositoryWithDefaultMethodTest extends Specification {
OrderId orderId = new OrderId(UUID.randomUUID() as String)
Order order = new Order(orderId, 'data')
JavaOrderRepository javaOrderRepository = new FakeJavaOrderRepository()
def 'should get order from java repository'() {
given:
javaOrderRepository.save(order)
expect:
javaOrderRepository.get(orderId) == order
}
def 'should throw NotFound when order does not exist in java repository'() {
when:
javaOrderRepository.get(orderId)
then:
thrown(NotFound)
}
}</pre><p>Groovy can implement Java interfaces with the default methods without any problems.</p><h2 id="show-me-the-code">Show me the code</h2><p>Code is available <a href="https://github.com/alien11689/testing-kotlin-with-spock">here</a>.</p>Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0tag:blogger.com,1999:blog-7262035251134282670.post-31435824073120199672018-05-28T22:46:00.004+02:002022-03-18T16:52:04.052+01:00Testing Kotlin with Spock Part 2 - Enum with instance methodThe enum class with instance method in Kotlin is quite similar to its Java version, but they are look a bit different in the bytecode. Let's see the difference by writing some tests using <a href="http://spockframework.org/">Spock</a>.<br />
<br />
<br />
<h2 id="what-do-we-want-to-test">What do we want to test?</h2>Let's see the code that we want to test:<br />
<pre class="brush: java">enum class EnumWithInstanceMethod {
PLUS {
override fun sign(): String = "+"
},
MINUS {
override fun sign(): String = "-"
};
abstract fun sign(): String
}</pre>Obviously, it can be written in a better way (e. g. using enum instance variable), but this example shows the case we want to test in the simplest way.<br />
<br />
<br />
<h2 id="how-to-test-it-with-spock">How to test it with Spock?</h2><h3 id="the-simplest-test-that-does-not-work">The simplest test (that does not work)</h3>First, we can write the test like we would do it with a Java enum:<br />
<pre class="brush: java">def "should use enum method like in java"() {
expect:
EnumWithInstanceMethod.MINUS.sign() == '-'
}</pre>The test fails:<br />
<pre class="brush: java">Condition failed with Exception:
EnumWithInstanceMethod.MINUS.sign() == '-'
|
groovy.lang.MissingMethodException: No signature of method: static com.github.alien11689.testingkotlinwithspock.EnumWithInstanceMethod$MINUS.sign() is applicable for argument types: () values: []
Possible solutions: sign(), sign(), is(java.lang.Object), find(), with(groovy.lang.Closure), find(groovy.lang.Closure)
at com.github.alien11689.testingkotlinwithspock.EnumWithInstanceMethodTest.should use enum method like in java(EnumWithInstanceMethodTest.groovy:11)
Caused by: groovy.lang.MissingMethodException: No signature of method: static com.github.alien11689.testingkotlinwithspock.EnumWithInstanceMethod$MINUS.sign() is applicable for argument types: () values: []
Possible solutions: sign(), sign(), is(java.lang.Object), find(), with(groovy.lang.Closure), find(groovy.lang.Closure)
... 1 more</pre>Interesting... Why is Groovy telling us that we are trying to call a static method? Maybe we are not using the enum instance but something else?. Let's create a test where we pass the enum instance to method:<br />
<pre class="brush: java">static String consume(EnumWithInstanceMethod e) {
return e.sign()
}
def "should pass enum as parameter"() {
expect:
consume(EnumWithInstanceMethod.MINUS) == '-'
}</pre>Error message:<br />
<pre class="brush: java">Condition failed with Exception:
consume(EnumWithInstanceMethod.MINUS) == '-'
|
groovy.lang.MissingMethodException: No signature of method: static com.github.alien11689.testingkotlinwithspock.EnumWithInstanceMethodTest.consume() is applicable for argument types: (java.lang.Class) values: [class com.github.alien11689.testingkotlinwithspock.EnumWithInstanceMethod$MINUS]
Possible solutions: consume(com.github.alien11689.testingkotlinwithspock.EnumWithInstanceMethod)
at com.github.alien11689.testingkotlinwithspock.EnumWithInstanceMethodTest.should pass enum as parameter(EnumWithInstanceMethodTest.groovy:29)
Caused by: groovy.lang.MissingMethodException: No signature of method: static com.github.alien11689.testingkotlinwithspock.EnumWithInstanceMethodTest.consume() is applicable for argument types: (java.lang.Class) values: [class com.github.alien11689.testingkotlinwithspock.EnumWithInstanceMethod$MINUS]
Possible solutions: consume(com.github.alien11689.testingkotlinwithspock.EnumWithInstanceMethod)
... 1 more</pre>Now we see that we passed the class <code>com.github.alien11689.testingkotlinwithspock.EnumWithInstanceMethod$MINUS</code>, not the enum instance.<br />
<br />
<br />
<h3 id="but-it-works-in-java...">But it works in Java...</h3>Analogous code in JUnit works perfectly and the test passes:<br />
<pre class="brush: java">@Test
public void shouldReturnSign() {
assertEquals("-", EnumWithInstanceMethod.MINUS.sign());
}</pre>Java can access Kotlin's instance method without problems, so maybe something is wrong with Groovy...<br />
But the Java enum with instance method, e. g.<br />
<pre class="brush: java">public enum EnumWithInstanceMethodInJava {
PLUS {
public String sign() {
return "+";
}
},
MINUS {
public String sign() {
return "-";
}
};
public abstract String sign();
}</pre>works correctly in the Spock test:<br />
<pre class="brush: java">def "should use enum method"() {
expect:
EnumWithInstanceMethodInJava.MINUS.sign() == '-'
}</pre><br />
<br />
<h3 id="whats-the-difference">What's the difference?</h3>We can spot the difference just by looking at the compiled classes:<br />
<pre class="brush: java">$ tree build/classes/main/
build/classes/main/
└── com
└── github
└── alien11689
└── testingkotlinwithspock
├── AdultValidator.class
├── EnumWithInstanceMethod.class
├── EnumWithInstanceMethodInJava$1.class
├── EnumWithInstanceMethodInJava$2.class
├── EnumWithInstanceMethodInJava.class
├── EnumWithInstanceMethod$MINUS.class
├── EnumWithInstanceMethod$PLUS.class
├── Error.class
├── Ok.class
├── ValidationStatus.class
└── Validator.class</pre>Java generates anonymous classes (<code>EnumWithInstanceMethodInJava$1</code> and <code>EnumWithInstanceMethodInJava$2</code>) for the enum instances, but Kotlin names those classes after the enum instances names (<code>EnumWithInstanceMethod$MINUS</code> and <code>EnumWithInstanceMethod$PLUS</code>).<br />
How does it tie into the problem with Groovy? Groovy does not need the <code>.class</code> when accessing class in code, so when we try to access <code>EnumWithInstanceMethod.MINUS</code>, Groovy converts it to <code>EnumWithInstanceMethod.MINUS.class</code>, not the instance of the enum. The same problem does not occur in Java code since there is no <code>EnumWithInstanceMethodInJava$MINUS</code> class.<br />
<br />
<br />
<h2 id="solution">Solution</h2>Knowing the difference, we can solve the problem of accessing Kotlin's enum instance in our Groovy code.<br />
The first solution is accessing the enum instance with <code>valueOf</code> method:<br />
<pre class="brush: java">def "should use enum method working"() {
expect:
EnumWithInstanceMethod.valueOf('MINUS').sign() == '-'
}</pre>The second way is to tell Groovy explicitly that we want to access the static field which is the instance of enum:<br />
<pre class="brush: java">def "should use enum method"() {
expect:
EnumWithInstanceMethod.@MINUS.sign() == '-'
}</pre>You can choose either solution depending on style of your code and your preferences.<br />
<br />
<br />
<h2 id="show-me-the-code">Show me the code</h2>Code is available <a href="https://github.com/alien11689/testing-kotlin-with-spock">here</a>.Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0tag:blogger.com,1999:blog-7262035251134282670.post-84141985258718908182018-03-13T23:15:00.002+01:002022-03-18T16:52:16.458+01:00Testing Kotlin with Spock Part 1 - Object<p>The <code>object</code> keyword in Kotlin creates singleton in a very convenient way. It can be used for example as a state of an operation. <a href="http://spockframework.org/" target="_blank">Spock Framework</a> is one of the most expressive and readable test framework available in the Java ecosystem. Let's see how Kotlin <code>object</code> can be used in the Spock tests.</p><h2 id="what-do-we-want-to-test">What do we want to test?</h2><p>We have a single method <code>validate</code> in <code>Validator</code> interface which returns validation status: <code>Ok</code> or <code>Error</code>.</p><pre class="brush: java">sealed class ValidationStatus
object Ok : ValidationStatus()
object Error : ValidationStatus()
interface Validator<T> {
fun validate(value: T): ValidationStatus
}</pre><p>We also provide a simple implementation of this interface:</p><pre class="brush: java">class AdultValidator : Validator<Int> {
override fun validate(value: Int) = if (value >= 18) Ok else Error
}</pre><h2 id="how-to-test-it-with-spock">How to test it with Spock?</h2><h3 id="first---silly-approach">First - silly approach</h3><p>First, let's write a parameterized test for the validator:</p><pre class="brush: java">AdultValidator sut = new AdultValidator()
def 'should validate age #age'() {
expect:
sut.validate(age) == result
where:
age | result
0 | Error
17 | Error
18 | Ok
19 | Ok
}</pre><p>We expect it to pass, but it fails... <code>Error</code> and <code>Ok</code> are classes in the code above.</p><h3 id="second---naive-approach">Second - naive approach</h3><p>We need instances instead, so we modify the test a little:</p><pre class="brush: java">def 'should validate age #age'() {
expect:
sut.validate(age) == result
where:
age | result
0 | new Error()
17 | new Error()
18 | new Ok()
19 | new Ok()
}</pre><p>And again, this one fails as well. Why? It is because <code>Error</code> and <code>Ok</code> classes do not have overridden <code>equals</code> method. But why? We expects Kotlin objects (those created with <code>object</code> keyword, not plain object) to have it implemented correctly. What is more, it works correctly in Kotlin:</p><pre class="brush: java">fun isOk(status:ValidationStatus) = status == Ok</pre><h3 id="third---correct-approach">Third - correct approach</h3><p>Let's look into the class file:</p><pre class="brush: java">$ javap com/github/alien11689/testingkotlinwithspock/Ok.class
Compiled from "Validator.kt"
public final class com.github.alien11689.testingkotlinwithspock.Ok extends com.github.alien11689.testingkotlinwithspock.ValidationStatus {
public static final com.github.alien11689.testingkotlinwithspock.Ok INSTANCE;
static {};
}</pre><p>If we want to access the real object that Kotlin uses in such comparisson, then we should access the class static property called <code>INSTANCE</code>:</p><pre class="brush: java">def 'should validate age #age'() {
expect:
sut.validate(age) == result
where:
age | result
0 | Error.INSTANCE
17 | Error.INSTANCE
18 | Ok.INSTANCE
19 | Ok.INSTANCE
}</pre><p>Now the test passes.</p><h3 id="fourth---alternative-approach">Fourth - alternative approach</h3><p>We can also check the method result without specific instance of the object class and use <code>instanceof</code> or <code>Class#isAssignableFrom</code> instead.</p><pre class="brush: java">def 'should validate age #age'() {
when:
ValidationStatus result = sut.validate(age)
then:
result.class.isAssignableFrom(expected)
where:
age | expected
0 | Error
17 | Error
18 | Ok
19 | Ok
}</pre><h2 id="show-me-the-code">Show me the code</h2><p>Code is available <a href="https://github.com/alien11689/testing-kotlin-with-spock" target="_blank">here</a>;</p>Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0tag:blogger.com,1999:blog-7262035251134282670.post-24731979864562608762018-01-18T19:00:00.003+01:002018-09-27T20:10:49.795+02:00MapStruct mapper injection in OSGi Blueprint<h2 id="what-is-mapstruct">What is MapStruct?</h2>According to <a href="http://mapstruct.org/" target="_blank">MapStruct</a> website:<br />
<blockquote>MapStruct is a code generator that greatly simplifies the implementation of mappings between Java bean types based on a convention over configuration approach. The generated mapping code uses plain method invocations and thus is fast, type-safe and easy to understand.</blockquote><h2 id="inject-mapstruct-mapper-in-blueprint-osgi">Inject MapStruct mapper in Blueprint OSGi</h2>Such mappings are sometimes necessary in our integration projects. We also use OSGi to create our applications and <a href="http://aries.apache.org/modules/blueprint.html" target="_blank">Blueprint</a> for dependency injection. <a href="http://aries.apache.org/modules/blueprint-maven-plugin.html" target="_blank">Blueprin Maven Plugin</a> makes it very easy to use, providing annotation support.<br />
MapStruct supports component models like <code>cdi</code>, <code>spring</code> and <code>jsr330</code>, so generated classes could be used as beans. Fortunately, Blueprint Maven Plugin uses annotations from <a href="https://www.jcp.org/en/jsr/detail?id=330" target="_blank">JSR 330</a>, such as <code>Singleton</code> or <code>Named</code>.<br />
The only thing we have to do is to add property <code>componentModel</code> with value <code>jsr330</code> to a mapping interface:<br />
<pre class="brush: java">@Mapper(componentModel = "jsr330")
public interface PersonMapper {
Person toDomain(PersonDto personDto);
}</pre>and now we can inject <code>PersonMapper</code> to our beans:<br />
<pre class="brush: java">@Singleton
@AllArgsConstructor
public class CreatePersonHandler {
private final PersonRepository personRepository;
private final PersonMapper personMapper;
// ...
}</pre>Blueprint Maven Plugin will generate an <code>XML</code> file with bean <code>PersonMapperImpl</code> and inject it to <code>CreatePersonHandler</code>:<br />
<pre class="brush: java"><?xml version="1.0" encoding="UTF-8"?><blueprint xmlns="http://www.osgi.org/xmlns/blueprint/v1.0.0">
<bean id="createPersonHandler" class="com.github.alien11689.osgi.mapstructblueprint.CreatePersonHandler">
<argument ref="personRepository"/>
<argument ref="personMapperImpl"/>
</bean>
<bean id="personMapperImpl" class="com.github.alien11689.osgi.mapstructblueprint.PersonMapperImpl"/>
<bean id="personRepository" class="com.github.alien11689.osgi.mapstructblueprint.PersonRepository"/>
</blueprint></pre><h2 id="generate-all-mappers-with-jsr-330-annotations">Generate all mappers with JSR 330 annotations</h2>If you have multiple mappers and all of them should be beans, then you can simply add one compiler argument in configuration and all the mappers will have <code>@Singleton</code> and <code>@Named</code> annotations by default.<br />
<pre class="brush: java"><?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
...
<build>
<plugins>
...
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>${maven-compiler-plugin.version}</version>
<configuration>
<source>1.8</source>
<target>1.8</target>
<compilerArgs>
<compilerArg>
-Amapstruct.defaultComponentModel=jsr330
</compilerArg>
</compilerArgs>
</configuration>
</plugin>
...
</plugins>
</build>
</project></pre><h2 id="try-it-on-your-own">Try it on your own</h2>The code is available at <a href="https://github.com/alien11689/mapstruct-and-blueprint" target="_blank">Github</a>.Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com1tag:blogger.com,1999:blog-7262035251134282670.post-76350595945475529682017-11-14T19:40:00.000+01:002017-11-14T19:40:29.872+01:00Karaf configuration as Groovy file<h2 id="introduction">Introduction</h2>By deafault, <a href="http://karaf.apache.org/" target="_blank">Apache Karaf</a> keeps configuration for bundles in the <code>etc</code> directory as flat properties files. We can override configuration for the storing mechanism by providing own implementation of the <code>org.apache.felix.cm.PersistenceManager</code> interface and use much more readable format for bundle properties, e. g. <a href="http://przybyszd.blogspot.com/2015/09/easy-configuration-usege-with.html" target="_blank">groovy config</a>.<br />
<h2 id="turning-off-built-in-karaf-persistence">Turning off built-in Karaf persistence</h2>As we can read in <a href="https://github.com/apache/karaf/blob/master/manual/src/main/asciidoc/user-guide/configuration.adoc" target="_blank">Karaf documentation</a>:<br />
<blockquote>Apache Karaf persists configuration using own persistence manager in case of when available persistence managers do not support that.</blockquote>We will use our custom implementation of persistence, so Karaf persistence is not needed. We can turn it off by setting variable <code>storage</code> to an empty value:<br />
<pre class="brush: bash">$ cat etc/org.apache.karaf.config.cfg
storage=</pre>This option is available since version 4.1.3 when <a href="https://issues.apache.org/jira/browse/KARAF-4803" target="_blank">this issue</a> was resolved.<br />
<h2 id="registering-custom-persistence-manager">Registering custom Persistence Manager</h2>First we have to create and register an OSGi service implementing <code>org.apache.felix.cm.PersistenceManager</code>. If we build and install the bundle with such service while Karaf is running (e.g. by putting jar in the <code>deploy</code> directory), then we should have at least two <code>PersistenceManager</code> services registered:<br />
<pre class="brush: bash">karaf@root()> ls org.apache.felix.cm.PersistenceManager
[org.apache.felix.cm.PersistenceManager]
----------------------------------------
service.bundleid = 7
service.description = Platform Filesystem Persistence Manager
service.id = 14
service.pid = org.apache.felix.cm.file.FilePersistenceManager
service.ranking = -2147483648
service.scope = singleton
service.vendor = Apache Software Foundation
Provided by :
Apache Felix Configuration Admin Service (7)
Used by:
Apache Felix Configuration Admin Service (7)
[org.apache.felix.cm.PersistenceManager]
----------------------------------------
osgi.service.blueprint.compname = groovyConfigPersistenceManager
service.bundleid = 56
service.id = 117
service.pid = com.github.alien11689.osgi.util.groovyconfig.impl.GroovyConfigPersistenceManager
service.ranking = 100
service.scope = bundle
Provided by :
groovy-config (56)
Used by:
Apache Felix Configuration Admin Service (7)</pre>Loaded configurations will be cached by configuration admin. We can use <code>org.apache.felix.cm.NotCachablePersistenceManager</code> interface if we want to implement custom caching strategy.<br />
<h2 id="creating-a-new-properties-file">Creating a new properties file</h2>Let's create a new properties file in groovy, e.g:<br />
<pre class="brush: bash">$ cat etc/com.github.alien11689.test1.groovy
a = '7'
b {
c {
d = 1
e = 2
}
z = 9
}
x.y.z='test'</pre>If we search for properties with pid <code>com.github.alien11689.test1</code>, Karaf will find these.<br />
<pre class="brush: bash">karaf@root()> config:list '(service.pid=com.github.alien11689.test1)'
----------------------------------------------------------------
Pid: com.github.alien11689.test1
BundleLocation: null
Properties:
a = 7
b.c.d = 1
b.c.e = 2
b.z = 9
service.pid = com.github.alien11689.test1
x.y.z = test</pre>If we make any change to the file they won't be mapped to properties, because there are no file watchers defined for it.<br />
We could manage such properties using Karaf commands instead.<br />
<h2 id="managing-configuration-via-karaf-commands">Managing configuration via Karaf commands</h2>We can define a new pid using Karaf commands:<br />
<pre class="brush: bash">karaf@root()> config:property-set -p com.github.alien11689.test2 f.a 6
karaf@root()> config:property-set -p com.github.alien11689.test2 f.b 'test'</pre>Since our <code>PersistenceManager</code> has higher <code>service.ranking</code> (<code>100 > -2147483648</code>), new pid will be stored as a groovy file:<br />
<pre class="brush: bash">$ cat etc/com.github.alien11689.test2.groovy
f {
b='test'
a='6'
}</pre>We can also change/remove properties or remove the whole configuration pid using karaf commands and it will all be mapped to groovy configuration files.<br />
<h2 id="sources">Sources</h2>Sources are available on <a href="https://github.com/alien11689/osgi-groovy-config" target="_blank">github</a>.Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0tag:blogger.com,1999:blog-7262035251134282670.post-77179445518130833612017-08-24T16:49:00.000+02:002017-08-24T17:20:27.728+02:00Using Kotlin extensions in Groovy<h2 id="extensions-in-kotlin-and-groovy">Extensions in Kotlin and Groovy</h2><p><a target="_blank" href="https://kotlinlang.org/">Kotlin</a> and <a target="_blank" href="http://groovy-lang.org/">Groovy</a> have mechanisms for extending existing classes without using inheritance or decorators. In both languages, the mechanisms are called extension methods. Their source code looks different, but generated bytecode is quite similar. Thanks to that, Groovy is able to use Kotlin extensions just like its own.</p><p>Why would I want to use such extensions in Groovy? The main reason is that I want to test my extensions using the best testing framework available for the JVM - <a target="_blank" href="http://spockframework.org/">Spock Framework</a>.</p><p>Code is available <a target="_blank" href="https://github.com/alien11689/kotlin-extensions-in-groovy">here</a>.</p><h2 id="extensions-in-kotlin">Extensions in Kotlin</h2><p>There are many types of <a target="_blank" href="https://kotlinlang.org/docs/reference/extensions.html">extensions in Kotlin</a>. I decided to focus only on extension functions and properties.</p><p>As an example, I extend the <code>java.lang.String</code> class. First, I create an extension function <code>skipFirst</code>, which skips first <code>N</code> characters:</p><script src="https://gist.github.com/alien11689/7962203f343f15e30aba549e3ec409b5.js?file=kotlin-extensions-p1.kt"></script><br />
<p>Next, I create an extension property <code>answer</code>, which is the <a target="_blank" href="https://en.wikipedia.org/wiki/Phrases_from_The_Hitchhiker%27s_Guide_to_the_Galaxy#Answer_to_the_Ultimate_Question_of_Life.2C_the_Universe.2C_and_Everything_.2842.29">Answer to the Ultimate Question of Life, the Universe, and Everything</a>:</p><script src="https://gist.github.com/alien11689/7962203f343f15e30aba549e3ec409b5.js?file=kotlin-extensions-p2.kt"></script><br />
<p>Both extensions are declared in package <code>com.github.alien11689.extensions</code>, in file called <code>StringExtensions</code>. However, the generated class in target directory is named <code>StringExtensionsKt</code> and this is the name that must be used when accessing from other languages. Specific class name can be forced by annotation <a target="_blank" href="https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.jvm/-jvm-name/"><code>@file:JvmName</code></a>.</p><h2 id="using-kotlin-extensions-in-groovy-1">Using Kotlin extensions in Groovy</h2><p>There are two ways for using extensions in Groovy that are supported by good IDEs. First, you can declare scope where the extensions are available by <code>use</code> method:</p><script src="https://gist.github.com/alien11689/7962203f343f15e30aba549e3ec409b5.js?file=testing-use.groovy"></script><br />
<p>It is acceptable, but is not very convenient. The second and much better way is to use an extension module definition. The extension module is defined in file <code>org.codehaus.groovy.runtime.ExtensionModule</code> in directory <code>src/main/resources/META-INF/services/</code>. The same directory is monitored by <a target="_blank" href="https://docs.oracle.com/javase/8/docs/api/java/util/ServiceLoader.html">ServiceLoader</a>, but the file format is completely different:</p><script src="https://gist.github.com/alien11689/7962203f343f15e30aba549e3ec409b5.js?file=extensionModule"></script><br />
<p>The tests look much better now:</p><script src="https://gist.github.com/alien11689/7962203f343f15e30aba549e3ec409b5.js?file=testing-extension-module.groovy"></script>Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0tag:blogger.com,1999:blog-7262035251134282670.post-28299582388147242622017-02-18T19:18:00.000+01:002017-08-24T20:52:06.750+02:00OSGi Blueprint visualization<h2 id="what-is-blueprint">What is blueprint?</h2><p>Blueprint is a dependency injection framework for OSGi bundles. It could be written by hand or generated using <a target="_blank" href="http://aries.apache.org/modules/blueprint-maven-plugin.html">Blueprint Maven Plugin</a>. Blueprint file is only an XML describing beans, services and references. Each OSGi bundle could have one or more blueprint files.</p><p>Blueprint files represent architecture of our bundle. Let's visualize it using groovy script and graphviz available in my <a target="_blank" href="https://github.com/alien11689/blueprint-vizualizer">github repository</a> and analyze.</p><h2 id="example-generation">Example generation</h2><p><strong>Pre: All you need is groovy and graphviz installed on your OS</strong></p><p>I am working mostly with bundles with generated blueprint, so I will use blueprint file generated from Blueprint Maven Plugin tests as example. All examples are included in github repository.</p><p>Generation could be invoked by running <code>run.sh</code> script with given destination file prefix (png extension will be added to it) and path to blueprint file:</p><pre class="brush: bash">mkdir -p target
./run.sh target/fullBlueprint fullBlueprint.xml</pre><p>Visualization is available <a target="_blank" href="https://gist.github.com/alien11689/560e189859107159126e71d45065ec51/raw/d2a8b16e5741a1debf36168953f5608ec91a1656/fullBlueprint.png">here</a>.</p><h2 id="separating-domains">Separating domains</h2><p>First if you look at the image, you see that some beans are grouped. You could easily extract such domains with tree roots: <code>beanWithConfigurationProperties</code> and <code>beanWithCallbackMethods</code> to separate blueprint files and bundles in future and generate images from them:</p><pre class="brush: bash">./run.sh target/beanWithCallbackMethods example/firstCut/beanWithCallbackMethods.xml
./run.sh target/beanWithConfigurationProperties example/firstCut/beanWithConfigurationProperties.xml
./run.sh target/otherStuff example/firstCut/otherStuff.xml</pre><p>Now we have three, a bit cleaner, images: <a target="_blank" href="https://gist.github.com/alien11689/560e189859107159126e71d45065ec51/raw/d2a8b16e5741a1debf36168953f5608ec91a1656/beanWithConfigurationProperties.png"><code>beanWithConfigurationProperties.png</code></a>, <a target="_blank" href="https://gist.github.com/alien11689/560e189859107159126e71d45065ec51/raw/d2a8b16e5741a1debf36168953f5608ec91a1656/beanWithCallbackMethods.png"><code>beanWithCallbackMethods.png</code></a> and <a target="_blank" href="https://gist.github.com/alien11689/560e189859107159126e71d45065ec51/raw/d2a8b16e5741a1debf36168953f5608ec91a1656/otherStuff.png"><code>otherStuff.png</code></a>.</p><p>We also could generate image from more than one blueprint:</p><pre class="brush: bash">./run.sh target/joinFirstCut example/firstCut/otherStuff.xml example/firstCut/beanWithConfigurationProperties.xml example/firstCut/beanWithCallbackMethods.xml</pre><p>And the result is <a target="_blank" href="https://gist.github.com/alien11689/560e189859107159126e71d45065ec51/raw/d2a8b16e5741a1debf36168953f5608ec91a1656/joinFirstCut.png">here</a>. The image contains beans grouped by file, but if you do not like it, you could force generation without such separation using option <code>--no-group-by-file</code>:</p><pre class="brush: bash">./run.sh target/joinFirstCutGrouped example/firstCut/otherStuff.xml example/firstCut/beanWithConfigurationProperties.xml example/firstCut/beanWithCallbackMethods.xml --no-group-by-file</pre><p>It will generate <a target="_blank" href="https://gist.github.com/alien11689/560e189859107159126e71d45065ec51/raw/d2a8b16e5741a1debf36168953f5608ec91a1656/joinFirstCutGrouped.png">image with all beans from all files</a>.</p><h2 id="exclusion">Exclusion</h2><p>Sometimes it is difficult to spot and extract other domains. It will be easier to do some experiments on blueprint. For example, bean <code>my1</code> is a dependency for too many other beans. You could consider converting <code>my1</code> bean to OSGi service and extracting it to another bundle.</p><p>Let's exclude <code>my1</code> bean from generation via <code>-e</code> option and see what happens:</p><pre class="brush: bash">./run.sh target/otherStuffWithoutMy example/firstCut/otherStuff.xml -e my1</pre><p>Result is available <a target="_blank" href="https://gist.github.com/alien11689/560e189859107159126e71d45065ec51/raw/d2a8b16e5741a1debf36168953f5608ec91a1656/otherStuffWithoutMy.png">here</a>. Now we see, that tree with root bean <code>myFactoryBeanAsService</code> could be separated and <code>my1</code> could be inject to it as osgi service in another bundle.</p><p>You could exclude more than one bean adding <code>-e</code> switch for each of them, e. g. <code>-e my1 -e m2 -e myBean123</code>.</p><h2 id="conclusion">Conclusion</h2><p>Blueprint is great for dependency injection for OSGi bundles, but it is easy to create quite big context containing many domains. It is much easier to recognize or search for such domains using blueprint visualizer script.</p><br />
<pre class="prettyprint"><code class="language-html">YOUR CODE HRER</code></pre>Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0tag:blogger.com,1999:blog-7262035251134282670.post-62392034973655985062016-08-16T18:44:00.002+02:002016-08-16T18:44:38.213+02:00Deploy WSDL file as OSGI Bundle in Apache Karaf<h2 id="introduction">Introduction</h2><p>WSDL file describes webservices. Java classes are often generated from WSDL. For this purpose, we could use command line tools (e. g. <a href="http://cxf.apache.org/docs/wsdl-to-java.html">wsdl2Java</a> or <a href="http://docs.oracle.com/javase/6/docs/technotes/tools/share/wsimport.html">wsimport</a>) or using <a href="http://cxf.apache.org/docs/maven-cxf-codegen-plugin-wsdl-to-java.html">maven plugin</a>.</p><p>From the other side, we have <a href="http://karaf.apache.org/">Apache Karaf</a> which is OSGI container. Karaf has installed by default many deployers for creating OSGi bundles from files, e. g. <a href="http://karaf.apache.org/manual/latest/#_blueprint_deployer">Blueprint deployer</a>, <a href="http://karaf.apache.org/manual/latest/#_spring_deployer">Spring deployer</a> or <a href="http://karaf.apache.org/manual/latest/#_war_deployer">War deployer</a>.</p><p>It is easy to generate java classes from WSDL file and also to create custom deployer for Karaf, so why do not join these two features?</p><h2 id="installation-of-wsdl-deployer">Installation of WSDL deployer</h2><p>Source code of my WSDL deployer is provided <a href="https://github.com/alien11689/wsdl-deployer">here</a>. You can download and build it:</p><pre class="brush: bash">mvn clean install</pre><p>We also need Karaf. I will use the newest version 4.0.5. It could be download from <a href="http://karaf.apache.org/download.html">Karaf website</a>. When you download and unpack it, you can run it:</p><pre class="brush: bash">$ cd PUT_PATH_TO_KARAF_DIR_HERE
$ ./bin/karaf
__ __ ____
/ //_/____ __________ _/ __/
/ ,< / __ `/ ___/ __ `/ /_
/ /| |/ /_/ / / / /_/ / __/
/_/ |_|\__,_/_/ \__,_/_/
Apache Karaf (4.0.5)
Hit '<tab>' for a list of available commands
and '[cmd] --help' for help on a specific command.
Hit '<ctrl-d>' or type 'system:shutdown' or 'logout' to shutdown Karaf.
karaf@root()></pre><p>and install commons-io and wsdl-delpoyer bundles:</p><pre class="brush: bash">karaf@root()> install -s mvn:org.apache.servicemix.bundles/org.apache.servicemix.bundles.commons-io/1.4_3
Bundle ID: 52
karaf@root()> install -s mvn:com.github.alien11689.karaf/wsdl-deployer/1.0.0-SNAPSHOT
Bundle ID: 53</pre><h2 id="install-wsdl-from-karaf-shell">Install WSDL from Karaf shell</h2><p>I will test deployer using WSDL file named <code>exampleService-2.0.0.wsdl</code> (provided WSDL is similar to <a href="https://msdn.microsoft.com/en-us/library/windows/desktop/dd323317(v=vs.85).aspx">this</a>, but has another namespace in types schama for testing purpose):</p><pre class="brush: bash"><?xml version="1.0"?>
<wsdl:definitions
xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
xmlns:wsu="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd"
xmlns:soapenc="http://schemas.xmlsoap.org/soap/encoding/"
xmlns:tns="http://Example.org"
xmlns:sns="http://Example.org/schema"
xmlns:wsa="http://schemas.xmlsoap.org/ws/2004/08/addressing"
xmlns:wsp="http://schemas.xmlsoap.org/ws/2004/09/policy"
xmlns:wsap="http://schemas.xmlsoap.org/ws/2004/08/addressing/policy"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:msc="http://schemas.microsoft.com/ws/2005/12/wsdl/contract"
xmlns:wsaw="http://www.w3.org/2006/05/addressing/wsdl"
xmlns:soap12="http://schemas.xmlsoap.org/wsdl/soap12/"
xmlns:wsa10="http://www.w3.org/2005/08/addressing"
xmlns:wsx="http://schemas.xmlsoap.org/ws/2004/09/mex"
targetNamespace="http://Example.org"
xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/">
<wsdl:types>
<xsd:schema targetNamespace="http://Example.org/schema" elementFormDefault="qualified" >
<xsd:element name="Add">
<xsd:complexType>
<xsd:sequence>
<xsd:element minOccurs="0" name="a" type="xsd:int" />
<xsd:element minOccurs="0" name="b" type="xsd:int" />
</xsd:sequence>
</xsd:complexType>
</xsd:element>
<xsd:element name="AddResponse">
<xsd:complexType>
<xsd:sequence>
<xsd:element minOccurs="0" name="result" type="xsd:int" />
</xsd:sequence>
</xsd:complexType>
</xsd:element>
<xsd:element name="Subtract">
<xsd:complexType>
<xsd:sequence>
<xsd:element minOccurs="0" name="a" type="xsd:int" />
<xsd:element minOccurs="0" name="b" type="xsd:int" />
</xsd:sequence>
</xsd:complexType>
</xsd:element>
<xsd:element name="SubtractResponse">
<xsd:complexType>
<xsd:sequence>
<xsd:element minOccurs="0" name="result" type="xsd:int" />
</xsd:sequence>
</xsd:complexType>
</xsd:element>
</xsd:schema>
</wsdl:types>
<wsdl:message name="ICalculator_Add_InputMessage">
<wsdl:part name="parameters" element="sns:Add" />
</wsdl:message>
<wsdl:message name="ICalculator_Add_OutputMessage">
<wsdl:part name="parameters" element="sns:AddResponse" />
</wsdl:message>
<wsdl:message name="ICalculator_Subtract_InputMessage">
<wsdl:part name="parameters" element="sns:Subtract" />
</wsdl:message>
<wsdl:message name="ICalculator_Subtract_OutputMessage">
<wsdl:part name="parameters" element="sns:SubtractResponse" />
</wsdl:message>
<wsdl:portType name="ICalculator">
<wsdl:operation name="Add">
<wsdl:input wsaw:Action="http://Example.org/ICalculator/Add" message="tns:ICalculator_Add_InputMessage" />
<wsdl:output wsaw:Action="http://Example.org/ICalculator/AddResponse" message="tns:ICalculator_Add_OutputMessage" />
</wsdl:operation>
<wsdl:operation name="Subtract">
<wsdl:input wsaw:Action="http://Example.org/ICalculator/Subtract" message="tns:ICalculator_Subtract_InputMessage" />
<wsdl:output wsaw:Action="http://Example.org/ICalculator/SubtractResponse" message="tns:ICalculator_Subtract_OutputMessage" />
</wsdl:operation>
</wsdl:portType>
<wsdl:binding name="DefaultBinding_ICalculator" type="tns:ICalculator">
<soap:binding transport="http://schemas.xmlsoap.org/soap/http" />
<wsdl:operation name="Add">
<soap:operation soapAction="http://Example.org/ICalculator/Add" style="document" />
<wsdl:input>
<soap:body use="literal" />
</wsdl:input>
<wsdl:output>
<soap:body use="literal" />
</wsdl:output>
</wsdl:operation>
<wsdl:operation name="Subtract">
<soap:operation soapAction="http://Example.org/ICalculator/Subtract" style="document" />
<wsdl:input>
<soap:body use="literal" />
</wsdl:input>
<wsdl:output>
<soap:body use="literal" />
</wsdl:output>
</wsdl:operation>
</wsdl:binding>
<wsdl:service name="CalculatorService">
<wsdl:port name="ICalculator" binding="tns:DefaultBinding_ICalculator">
<soap:address location="http://localhost/ICalculator" />
</wsdl:port>
</wsdl:service>
</wsdl:definitions></pre><p>We could install it via command:</p><pre class="brush: bash">karaf@root()> install -s wsdl:file:PUT_PATH_TO_WSDL_HERE/exampleService-2.0.0.wsdl\$package=org.github.alien11689.example&s1=http://Example.org/schema&t1=org.github.alien11689.example.schema
Bundle ID: 54</pre><p>File must have format <code>${bundleSymbolicName}-${version}.wsdl</code>.</p><p>Provided options are:</p><ul><li><code>package</code> - allows to change package of generated interface</li>
<li>pair <code>s1</code> and <code>t1</code> - maps schema in WSDL to package (WSDL deployer is in draft verion nowadays provides options to map only one schema).</li>
</ul><p>Karaf has installed this file:</p><pre class="brush: bash">karaf@root()> headers 54
Bundle 54
---------
Manifest-Version = 2
Bundle-ManifestVersion = 2
Bundle-SymbolicName = exampleService-2.0.0.wsdl
Bundle-Version = 2.0.0
Export-Package =
org.github.alien11689.example.schema;version=2.0.0,
org.github.alien11689.example;version=2.0.0
Import-Package =
javax.jws,
javax.jws.soap,
javax.xml.bind.annotation,
javax.xml.namespace,
javax.xml.ws</pre><h2 id="install-wsdl-by-putting-it-into-karaf-drop-folder">Install WSDL by putting it into Karaf drop folder</h2><p>You can also install WSDL file by copying it to <code>deploy</code> directory:</p><pre class="brush: bash">cp PUT_PATH_TO_WSDL_HERE/exampleService-2.0.0.wsdl PUT_PATH_TO_KARAF_DIR_HERE/deploy/deployedExampleService-2.0.0.wsdl</pre><p>It is much more simple to do, but do not allow for customization (e. g. namespace to package mapping). It creates bundle:</p><pre class="brush: bash">karaf@root()> list | grep deployedExampleService
55 | Active | 80 | 2.0.0 | deployedExampleService-2.0.0.wsdl
karaf@root()> headers 55
Bundle 55
---------
Manifest-Version = 2
Bundle-ManifestVersion = 2
Bundle-SymbolicName = deployedExampleService-2.0.0.wsdl
Bundle-Version = 2.0.0
Export-Package =
org.example;version=2.0.0,
org.example.schema;version=2.0.0
Import-Package =
javax.jws,
javax.jws.soap,
javax.xml.bind.annotation,
javax.xml.namespace,
javax.xml.ws</pre><h2 id="how-does-it-work">How does it work?</h2><p>Deployer uses <code>wsimport</code> command to create in temporary directory and compile generated java classes. Compiled class are packed with <code>MANIFEST.MF</code> into <code>service.jar</code> and such jar is really installed in OSGi container. For example, my temporary directory is <code>/tmp/4ff81631-3c08-487a-b731-1f95c568026f</code>:</p><pre class="brush: bash">$ tree /tmp/4ff81631-3c08-487a-b731-1f95c568026f
/tmp/4ff81631-3c08-487a-b731-1f95c568026f
├── Jaxb-binding.xml
├── Jaxws-binding.xml
├── service.wsdl
├── src
│ └── org
│ └── github
│ └── alien11689
│ └── example
│ ├── CalculatorService.java
│ ├── ICalculator.java
│ └── schema
│ ├── Add.java
│ ├── AddResponse.java
│ ├── ObjectFactory.java
│ ├── package-info.java
│ ├── Subtract.java
│ └── SubtractResponse.java
└── target
├── org
│ └── github
│ └── alien11689
│ └── example
│ ├── CalculatorService.class
│ ├── ICalculator.class
│ └── schema
│ ├── Add.class
│ ├── AddResponse.class
│ ├── ObjectFactory.class
│ ├── package-info.class
│ ├── Subtract.class
│ └── SubtractResponse.class
└── service.jar</pre><p>And my <code>service.jar</code> contains:</p><pre class="brush: bash">$ jar tf /tmp/4ff81631-3c08-487a-b731-1f95c568026f/target/service.jar
META-INF/
META-INF/MANIFEST.MF
org/
org/github/
org/github/alien11689/
org/github/alien11689/example/
org/github/alien11689/example/schema/
org/github/alien11689/example/schema/Add.class
org/github/alien11689/example/schema/ObjectFactory.class
org/github/alien11689/example/schema/Subtract.class
org/github/alien11689/example/schema/SubtractResponse.class
org/github/alien11689/example/schema/package-info.class
org/github/alien11689/example/schema/AddResponse.class
org/github/alien11689/example/ICalculator.class
org/github/alien11689/example/CalculatorService.class</pre><h2 id="conclusion">Conclusion</h2><p>WSDL generation and Karaf deployers could be easily joined and simplified creation of OSGi bundles without explicite creation of jar. Provided WSDL deployer is just draft, but could be very useful when we have many WSDLs and do not want to create separate artifacts for them.</p><p>Source code of WSDL deployer is provided <a href="https://github.com/alien11689/wsdl-deployer">here</a>.</p>Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0tag:blogger.com,1999:blog-7262035251134282670.post-31619870001787875072016-01-31T13:23:00.000+01:002016-01-31T13:23:07.075+01:00Easy Hoogle usage from bash<h2 id="what-is-hoogle">What is <code>Hoogle</code>?</h2><p><a href="https://www.haskell.org/hoogle/">Hoogle</a> is Google for searching of Haskell functions. You could ask it for function name or its signature.</p><p>There is available command <code>hoogle</code>, which could be installed using <a href="http://docs.haskellstack.org/en/stable/README.html"><code>stack</code></a>:</p><pre class="brush: bash">$ stack install hoogle</pre><h2 id="using-hoogle-from-command-line">Using <code>hoogle</code> from command line</h2><p>To <code>hoogle</code> a function you could just pass it as parameter:</p><pre class="brush: bash">$ hoogle fmap
Prelude fmap :: Functor f => (a -> b) -> f a -> f b
Data.Functor fmap :: Functor f => (a -> b) -> f a -> f b
Control.Monad fmap :: Functor f => (a -> b) -> f a -> f b
Control.Monad.Instances fmap :: Functor f => (a -> b) -> f a -> f b
Data.Traversable fmapDefault :: Traversable t => (a -> b) -> t a -> t b
Network.Stream fmapE :: (a -> Result b) -> IO (Result a) -> IO (Result b)</pre><p>or pass its signature:</p><pre class="brush: bash">$ hoogle "(a -> b -> c) -> [a] -> [b] -> [c]"
Prelude zipWith :: (a -> b -> c) -> [a] -> [b] -> [c]
Data.List zipWith :: (a -> b -> c) -> [a] -> [b] -> [c]
Control.Applicative liftA2 :: Applicative f => (a -> b -> c) -> f a -> f b -> f c
Control.Monad liftM2 :: Monad m => (a1 -> a2 -> r) -> m a1 -> m a2 -> m r
Prelude scanl :: (a -> b -> a) -> a -> [b] -> [a]
Data.List scanl :: (a -> b -> a) -> a -> [b] -> [a]
Prelude scanr :: (a -> b -> b) -> b -> [a] -> [b]
Data.List scanr :: (a -> b -> b) -> b -> [a] -> [b]
Data.List deleteFirstsBy :: (a -> a -> Bool) -> [a] -> [a] -> [a]
Data.List intersectBy :: (a -> a -> Bool) -> [a] -> [a] -> [a]
...</pre><p>But it shows only list of the signatures of the functions. Sometimes we want to see more information about function. If you use option <code>-i</code>, then additional information will be shown:</p><pre class="brush: bash">$ hoogle -i "(a -> b -> c) -> [a] -> [b] -> [c]"
Prelude zipWith :: (a -> b -> c) -> [a] -> [b] -> [c]
zipWith generalises zip by zipping with the function given as the first argument, instead of a tupling function. For example, zipWith (+) is applied to two lists to produce the list of corresponding sums.
From package base
zipWith :: (a -> b -> c) -> [a] -> [b] -> [c]</pre><p>And again it is not enough, because it shows only documentation of first function from the list. We have to move a counter to see documentation of further functions, e. g. to show information about third item from the list:</p><pre class="brush: bash">$ hoogle -i -s 3 "(a -> b -> c) -> [a] -> [b] -> [c]"
Control.Applicative liftA2 :: Applicative f => (a -> b -> c) -> f a -> f b -> f c
Lift a binary function to actions.
From package base
liftA2 :: Applicative f => (a -> b -> c) -> f a -> f b -> f c</pre><h2 id="easier-hoogle-usage-in-bash">Easier <code>hoogle</code> usage in <code>bash</code></h2><p>It is cumbersome to count each time you want to read info about further functions, so I have prepared bash function which makes it easier.</p><p>To search for function type:</p><pre class="brush: bash">$ hoog "(a->b) -> f a -> f b"
1) Data.Traversable fmapDefault :: Traversable t => (a -> b) -> t a -> t b
2) Prelude fmap :: Functor f => (a -> b) -> f a -> f b
3) Data.Functor fmap :: Functor f => (a -> b) -> f a -> f b
4) Control.Monad fmap :: Functor f => (a -> b) -> f a -> f b
5) Control.Monad.Instances fmap :: Functor f => (a -> b) -> f a -> f b
6) Data.Functor (<$>) :: Functor f => (a -> b) -> f a -> f b
7) Control.Applicative (<$>) :: Functor f => (a -> b) -> f a -> f b</pre><p>Each function will have its counter at the beginning and just add its number at the end of command to show more information about specific function:</p><pre class="brush: bash">$ hoog "(a->b) -> f a -> f b" 6
Searching for: (a -> b) -> f a -> f b
Data.Functor (<$>) :: Functor f => (a -> b) -> f a -> f b
An infix synonym for fmap.
From package base
(<$>) :: Functor f => (a -> b) -> f a -> f b</pre><h2 id="how-to-install-hoog-command">How to install <code>hoog</code> command?</h2><p>Command is available <a href="https://gist.github.com/alien11689/bbdb7f6f8f76425a8526">here</a>. To use this command just add it to your <code>~/bashrc</code> file.</p>Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0tag:blogger.com,1999:blog-7262035251134282670.post-47076670228951526682016-01-17T16:40:00.002+01:002022-03-18T16:52:32.258+01:00Do not use AllArgsConstructor in your public API<h2 id="introduction">Introduction</h2><p>Do you think about compatibility of your public API when you modify classes from it? It is especially easy to miss out that something incompatibly changed when you are using <a href="https://projectlombok.org/">Lombok</a>. If you use <a href="https://projectlombok.org/api/lombok/AllArgsConstructor.html"><code>AllArgsConstructor</code></a> annotation it will cause many problems.</p><h2 id="what-is-the-problem">What is the problem?</h2><p>Let's define simple class with <code>AllArgsConstructor</code>:</p><pre class="brush: java">@Data
@AllArgsConstructor
public class Person {
private final String firstName;
private final String lastName;
private Integer age;
}</pre><p>Now we can use generated constructor in spock test:</p><pre class="brush: java">def 'use generated allArgsConstructor'() {
when:
Person p = new Person('John', 'Smith', 30)
then:
with(p) {
firstName == 'John'
lastName == 'Smith'
age == 30
}
}</pre><p>And the test is green.</p><p>Let's add new optional field to our Person class - <code>email</code>:</p><pre class="brush: java">@Data
@AllArgsConstructor
public class Person {
private final String firstName;
private final String lastName;
private Integer age;
private String email;
}</pre><p>Adding optional field is considered compatible change. But our test fails...</p><pre>groovy.lang.GroovyRuntimeException: Could not find matching constructor for: com.github.alien11689.allargsconstructor.Person(java.lang.String, java.lang.String, java.lang.Integer)</pre><h2 id="how-to-solve-this-problem">How to solve this problem?</h2><h3 id="after-adding-field-add-previous-constructor">After adding field add previous constructor</h3><p>If you still want to use <code>AllArgsConstructor</code> you have to ensure compatibility by adding previous version of constructor on your own:</p><pre class="brush: java">@Data
@AllArgsConstructor
public class Person {
private final String firstName;
private final String lastName;
private Integer age;
private String email;
public Person(String firstName, String lastName, Integer age) {
this(firstName, lastName, age, null);
}
}</pre><p>And now our test again passes.</p><h3 id="annotation-lombok.data-is-enough">Annotation <code>lombok.Data</code> is enough</h3><p>If you use only <a href="https://projectlombok.org/api/lombok/Data.html"><code>Data</code></a> annotation, then constructor, with only mandatory (<code>final</code>) fields, will be generated. It is because <code>Data</code> implies <a href="https://projectlombok.org/api/lombok/RequiredArgsConstructor.html"><code>RequiredArgsConstructor</code></a>:</p><pre class="brush: java">@Data
public class Person {
private final String firstName;
private final String lastName;
private Integer age;
}</pre><pre class="brush: java">class PersonTest extends Specification {
def 'use generated requiredFieldConstructor'() {
when:
Person p = new Person('John', 'Smith')
p.age = 30
then:
with(p) {
firstName == 'John'
lastName == 'Smith'
age == 30
}
}
}</pre><p>After adding new field <code>email</code> test still passes.</p><h3 id="use-builder-annotation">Use <code>Builder</code> annotation</h3><p>Annotation <a href="https://projectlombok.org/api/lombok/Builder.html"><code>Builder</code></a> generates for us <code>PersonBuilder</code> class which helps us create new <code>Person</code>:</p><pre class="brush: java">@Data
@Builder
public class Person {
private final String firstName;
private final String lastName;
private Integer age;
}</pre><pre class="brush: java">class PersonTest extends Specification {
def 'use builder'() {
when:
Person p = Person.builder()
.firstName('John')
.lastName('Smith')
.age(30).build()
then:
with(p) {
firstName == 'John'
lastName == 'Smith'
age == 30
}
}
}</pre><p>After adding email field test still passes.</p><h1 id="conclusion">Conclusion</h1><p>If you use <code>AllArgsConstructor</code> you have to be sure what are you doing and know issues related to its compatibility. In my opinion the best option is not to use this annotation at all and instead stay with <code>Data</code> or <code>Builder</code> annotation.</p><p>Sources are available <a href="https://github.com/alien11689/do-no-use-allArgsConstructor">here</a>.</p>Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com1tag:blogger.com,1999:blog-7262035251134282670.post-35011199261777437002015-12-13T16:27:00.001+01:002022-03-18T16:52:50.942+01:00Primitives and its wrapped types compatibility<h2 id="introduction">Introduction</h2><p>How often do you think about possible changes in your API? Do you consider that something required could become optional in future? How about compatibility of such change? One of this changes is going from primitive (e. g. <code>int</code>) to its wrapped type (e. g. <code>Integer</code>). Let's check it out.</p><h2 id="api---first-iteration">API - first iteration</h2><p>Let's start with simple DTO class <code>Dep</code> in our public API.</p><pre class="brush: java">public class Dep {
private int f1;
public int getF1(){
return f1;
}
public void setF1(int f1){
this.f1 = f1;
}
// other fields and methods omitted
}</pre><p><code>f1</code> is obligatory field that never will be null.</p><p>Let's use it in <code>Main</code> class:</p><pre class="brush: java">public class Main {
public static void main(String... args) {
Dep dep = new Dep();
dep.setF1(123);
System.out.println(dep.getF1());
}
}</pre><p>compile it:</p><pre class="brush: bash">$ javac depInt/Dep.java
$ javac -cp depInt main/Main.java</pre><p>and run:</p><pre class="brush: bash">$ java -cp depInt:main Main
123</pre><p>It works.</p><h2 id="api---obligatory-field-become-optional">API - obligatory field become optional</h2><p>Now suppose our business requirements have changed. <code>f1</code> is not longer obligatory and we want possibility to set it to <code>null</code>.</p><p>So we provide next iteration of <code>Dep</code> class where <code>f1</code> field has type <code>Integer</code>.</p><pre class="brush: java">public class Dep {
private Integer f1;
public Integer getF1(){
return f1;
}
public void setF1(Integer f1){
this.f1 = f1;
}
// other fields and methods omitted
}</pre><p>We compile only the new <code>Dep</code> class because we do not want to change the <code>Main</code> class:</p><pre class="brush: bash">$ javac depInteger/Dep.java</pre><p>and run it with old <code>Main</code>:</p><pre class="brush: bash">$ java -cp depInteger:main Main
Exception in thread "main" java.lang.NoSuchMethodError: Dep.setF1(I)V
at Main.main(Main.java:4)</pre><p>Wow! It does not work...</p><h2 id="why-does-it-not-work">Why does it not work?</h2><p>We can use <code>javap</code> tool to investigate <code>Main</code> class.</p><pre class="brush: bash; highlight: [18, 21]">$ javap -c main/Main.class
Compiled from "Main.java"
public class Main {
public Main();
Code:
0: aload_0
1: invokespecial #1 // Method java/lang/Object."<init>":()V
4: return
public static void main(java.lang.String...);
Code:
0: new #2 // class Dep
3: dup
4: invokespecial #3 // Method Dep."<init>":()V
7: astore_1
8: aload_1
9: bipush 123
11: invokevirtual #4 // Method Dep.setF1:(I)V
14: getstatic #5 // Field java/lang/System.out:Ljava/io/PrintStream;
17: aload_1
18: invokevirtual #6 // Method Dep.getF1:()I
21: invokevirtual #7 // Method java/io/PrintStream.println:(I)V
24: return
}</pre><p>The most important are 11th and 18th instructions of <code>main</code> method. <code>Main</code> lookups for methods which use <code>int</code> (<code>I</code> in method signature).</p><p>Next let's compile the <code>Main</code> class with <code>Dep</code> which has <code>f1</code> of type <code>Integer</code>:</p><pre class="brush: bash">javac -cp depInteger main/Main.java</pre><p>and use <code>javap</code> on this class:</p><pre class="brush: bash; highlight: [19, 22]">$ javap -c main/Main.class
Compiled from "Main.java"
public class Main {
public Main();
Code:
0: aload_0
1: invokespecial #1 // Method java/lang/Object."<init>":()V
4: return
public static void main(java.lang.String...);
Code:
0: new #2 // class Dep
3: dup
4: invokespecial #3 // Method Dep."<init>":()V
7: astore_1
8: aload_1
9: bipush 123
11: invokestatic #4 // Method java/lang/Integer.valueOf:(I)Ljava/lang/Integer;
14: invokevirtual #5 // Method Dep.setF1:(Ljava/lang/Integer;)V
17: getstatic #6 // Field java/lang/System.out:Ljava/io/PrintStream;
20: aload_1
21: invokevirtual #7 // Method Dep.getF1:()Ljava/lang/Integer;
24: invokevirtual #8 // Method java/io/PrintStream.println:(Ljava/lang/Object;)V
27: return
}</pre><p>Now we see the difference. The <code>main</code> method:</p><ul><li>converts <code>int</code> to <code>Integer</code> in instruction 11th,</li>
<li>invokes method <code>setF1</code> which takes parameter of type <code>Integer</code> (<code>Ljava/lang/Integer;</code>) in instruction 14th,</li>
<li>invokes method <code>getF1</code> which returns <code>Integer</code> in instruction 21st.</li>
</ul><p>These differences do not allow us to use the <code>Main</code> class with <code>Dep</code> without recompilation if we change <code>f1</code>.</p><h2 id="how-about-groovy">How about Groovy?</h2><p>We have <code>GroovyMain</code> class which do the same as <code>Main</code> class written in Java.</p><pre class="brush: java">class GroovyMain {
static void main(String... args) {
Dep dep = new Dep(f1: 123)
println(dep.f1)
}
}</pre><p>We will compile <code>GroovyMain</code> class only with <code>Dep</code> which uses <code>int</code>:</p><pre class="brush: bash">$ groovyc -cp lib/groovy-all-2.4.5.jar:depInt -d main main/GroovyMain.groovy</pre><p>It runs great as expected with <code>int</code>:</p><pre class="brush: bash">$ java -cp lib/groovy-all-2.4.5.jar:depInt:main GroovyMain
123</pre><p>but with <code>Integer</code>... It works the same!</p><pre class="brush: bash">$ java -cp lib/groovy-all-2.4.5.jar:depInteger:main GroovyMain
123</pre><p>Groovy is immune to such change.</p><h3 id="with-compilestatic">With CompileStatic</h3><p>But what if we compile groovy with <a href="http://docs.groovy-lang.org/next/html/gapi/groovy/transform/CompileStatic.html"><code>CompileStatic</code></a> annotation? This annotation instructs groovy compiler to compile class with type checking and should produce bytecode similar to <code>javac</code> output.</p><p><code>GroovyMainCompileStatic</code> class is <code>GroovyMain</code> class with only <code>CompileStatic</code> annotation:</p><pre class="brush: java">import groovy.transform.CompileStatic
@CompileStatic
class GroovyMainCompileStatic {
static void main(String... args) {
Dep dep = new Dep(f1: 123)
println(dep.f1)
}
}</pre><p>When we compile this with <code>Dep</code> with <code>int</code> field:</p><pre class="brush: bash">$ groovyc -cp lib/groovy-all-2.4.5.jar:depInt -d main main/GroovyMainCompileStatic.groovy</pre><p>then of course it works:</p><pre class="brush: bash">$ java -cp lib/groovy-all-2.4.5.jar:depInt:main GroovyMainCompileStatic
123</pre><p>but with <code>Dep</code> with <code>Integer</code> field it fails like in Java:</p><pre class="brush: bash">$ java -cp lib/groovy-all-2.4.5.jar:depInteger:main GroovyMainCompileStatic
Exception in thread "main" java.lang.NoSuchMethodError: Dep.setF1(I)V
at GroovyMainCompileStatic.main(GroovyMainCompileStatic.groovy:6)</pre><h2 id="conclusion">Conclusion</h2><p>Change from primitive to its wrapped java type is not compatible change. Bytecode which uses dependent class assumes that there will be method which consumes or returns e. g. <code>int</code> and cannot deal with the same class which provides such method with <code>Integer</code> in place of <code>int</code>.</p><p>Groovy is much more flexible and could handle it, but only if we do not use <code>CompileStatic</code> annotation.</p><p>The source code is available <a href="https://github.com/alien11689/primitive-and-its-wrapped-types-compatibility">here</a>.</p>Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0tag:blogger.com,1999:blog-7262035251134282670.post-48802391322246141412015-12-08T22:03:00.002+01:002022-03-18T16:53:08.453+01:00Spring autowire with qualifiers<h2 id="introduction">Introduction</h2><p><code>Autowired</code> is great annotation, which by default inject beans by type to annotated element (constructor, setter or field). But how to use it, when there is more than one bean of requested type.</p><h2 id="autowired-with-one-bean"><code>Autowired</code> with one bean</h2><p>Suppose we will work with small interface:</p><pre class="brush: java">interface IHeaderPrinter {
String printHeader(String header)
}</pre><p>When we have only one bean implementing <code>IHeaderPrinter</code>:</p><pre class="brush: java">@Component
class HtmlHeaderPrinter implements IHeaderPrinter{
@Override
String printHeader(String header) {
return "<h1>$header</h1>"
}
}</pre><p>then everything works great and test passes.</p><pre class="brush: java">@Autowired
IHeaderPrinter headerPrinter
@Test
void shouldPrintHtmlHeader() {
assert headerPrinter.printHeader('myTitle') == '<h1>myTitle</h1>'
}</pre><h2 id="two-implementations">Two implementations</h2><p>But what will happen, if we add another implementation of <code>IHeaderPrinter</code>, e. g. <code>MarkdownHeaderPrinter</code>?</p><pre class="brush: java">@Component
class MarkdownHeaderPrinter implements IHeaderPrinter {
@Override
String printHeader(String header) {
return "# $header"
}
}</pre><p>Now out test with fail with exception:</p><pre class="brush: java">Error creating bean with name 'com.blogspot.przybyszd.spring.autowire.SpringAutowireWithQualifiersApplicationTests': Injection of autowired dependencies failed; nested exception is org.springframework.beans.factory.BeanCreationException: Could not autowire field: private com.blogspot.przybyszd.spring.autowire.IHeaderPrinter com.blogspot.przybyszd.spring.autowire.SpringAutowireWithQualifiersApplicationTests.headerPrinter; nested exception is org.springframework.beans.factory.NoUniqueBeanDefinitionException: No qualifying bean of type [com.blogspot.przybyszd.spring.autowire.IHeaderPrinter] is defined: expected single matching bean but found 2: markdownHeaderPrinter,htmlHeaderPrinter</pre><p>We have to decide which implementation we want to use in our test, so ...</p><h2 id="two-implementations-with-qualifier">Two implementations with <code>Qualifier</code></h2><p>Each bean is registered with name equal its class. For example <code>HtmlHeaderPrinter</code> is named <code>htmlHeaderPrinter</code>. The name is also its qualifier. We have to tell <code>Autowired</code>, that it should inject <code>htmlHeaderPrinter</code>:</p><pre class="brush: java; highlight: 2">@Autowired
@Qualifier('htmlHeaderPrinter')
IHeaderPrinter headerPrinter</pre><p>Now our test passes again.</p><h2 id="two-implementations-qualified-by-field-name">Two implementations qualified by field name</h2><p>If field is names like implementing class (for example <code>htmlHeaderPrinter</code>), then this class implementation will be injected:</p><pre class="brush: java">@Autowired
IHeaderPrinter htmlHeaderPrinter</pre><p>And test passes:</p><pre class="brush: java">@Test
void shouldPrintHtmlHeader() {
assert htmlHeaderPrinter.printHeader('myTitle') == '<h1>myTitle</h1>'
}</pre><p>Thanks to <code>@marcinjasion</code>.</p><h2 id="two-implementation-with-primary">Two implementation with <code>Primary</code></h2><p>We often have one implementation which we almost always want to inject, so do we still have to put <code>Qualifier</code> with its name wherever we want to use it? No.</p><p>We could mark one implementation as <code>Primary</code> and this bean will be wired by default (unless we explicit give another <code>Qualifier</code> to use injection point):</p><pre class="brush: java; highlight: 2">@Component
@Primary
class HtmlHeaderPrinter implements IHeaderPrinter{
// ...
}</pre><pre class="brush: java">@Autowired
IHeaderPrinter headerPrinter</pre><h2 id="summary">Summary</h2><p><code>Autowired</code> annotation allows us to inject dependencies to beans. It works great without additional configuration, when each bean could be uniquely find by type. When we have more than one bean, that could be injected, we have to use <code>Qualifier</code> or <code>Primary</code> annotation to help it find desired implementation.</p><p>Source code is available <a href="https://github.com/alien11689/spring-autowire-with-qualifiers">here</a>.</p>Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0tag:blogger.com,1999:blog-7262035251134282670.post-14852553621842153082015-12-02T21:06:00.001+01:002022-03-18T16:53:20.595+01:00Scheduling tasks using Message Queue<h2 id="introduction">Introduction</h2><p>How to schedule your task for later execution? You often create table in database, configure job that checks if due time of any task occured and then execute it.</p><p>But there is easier way if only you have message broker with your application... You could publish/send your message and tell it that it should be delivered with specified delay.</p><h2 id="scheduling-messages-using-activemq">Scheduling messages using ActiveMQ</h2><p><a href="https://activemq.apache.org/">ActiveMQ</a> is open source message broker written in Java. It is implementation of JMS (Java Message Service).</p><p>You could start its broker with scheduling support by adding flag <code>schedulerSupport</code> to broker configuration:</p><pre class="brush: java; highlight: 6"><beans ...>
...
<broker xmlns="http://activemq.apache.org/schema/core"
brokerName="localhost"
dataDirectory="${activemq.data}"
schedulerSupport="true">
...
</broker>
...
</beans></pre><p>Now, if you want to delay receiving message by few seconds, you could add property during message creation, e.g.:</p><pre class="brush: java">message.setLongProperty(ScheduledMessage.AMQ_SCHEDULED_DELAY, 8000)</pre><p>Delay unit is miliseconds.</p><p>Of course queue must be persisted.</p><p>When you listen for message on the same queue, then you will see that message indeed will be received with 8 second delay.</p><pre class="brush: bash">...
Send time: Tue Dec 01 18:51:23 CET 2015
...
Message received at Tue Dec 01 18:51:31 CET 2015
...</pre><h2 id="scheduling-messages-using-rabbitmq">Scheduling messages using RabbitMQ</h2><p>Scheduling tasks is not only the feature of ActiveMQ. It is also available with <a href="https://www.rabbitmq.com/">RabbitMQ</a>.</p><p>RabitMQ is message broker written in Erlang. It uses protocol AMQP.</p><p>First you have to install plugin <code>rabbitmq_delayed_message_exchange</code>. It could be done via command:</p><pre class="brush: bash">rabbitmq-plugins enable --offline rabbitmq_delayed_message_exchange</pre><p>You have to define exchange in RabbitMQ which will use features from this plugin. Queue for delayed messages should be bound to this exchange. Routing key should be set to queue name.</p><pre class="brush: java">channel.exchangeDeclare(exchange, 'x-delayed-message', true, false, ['x-delayed-type': 'direct']);
channel.queueBind(queue, exchange, queue);
channel.queueDeclare(queue, true, false, false, null);</pre><p>Of course queue must be persisted.</p><p>To test it just publish new message with property <code>x-delay</code>:</p><pre class="brush: java">channel.basicPublish(exchange,
queue,
new AMQP.BasicProperties.Builder().headers('x-delay': 8000).build(),
"Message: $currentUuid".bytes)</pre><p>Message will be delayed with 8 seconds:</p><pre class="brush: bash">...
Send time: Tue Dec 01 19:04:18 CET 2015
...
Message received at Tue Dec 01 19:04:26 CET 2015
...</pre><h2 id="conclusion">Conclusion</h2><p>Why you create similar mechanism for handling scheduled tasks on your own, when you could use your message brokers and delayed messages to schedule future tasks?</p><p>Sources are available <a href="https://github.com/alien11689/scheduled-messages">here</a>.</p>Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0tag:blogger.com,1999:blog-7262035251134282670.post-11201212688025619692015-11-14T16:24:00.001+01:002022-03-18T16:58:36.923+01:00Kotlin's extensions for each classExtensions in Kotlin are very powerful mechanism. It allows for add any method to any of existing classes. Each instance has (as in Java) <code>equals</code>, <code>toString</code> and <code>hashCode</code> methods, but there is much more in Kotlin.<br />
<br />
<h2>Example classes</h2><br />
Let's define some simple classes describing person: normal class and data class.<br />
<br />
<pre class="brush: java">class PersonJaxb {
var firstName: String? = null
var lastName: String? = null
var age: Int? = null
}
data class Person(val firstName: String, val lastName: String, val age: Int)
</pre><br />
<h2>Normal class extensions</h2><br />
All instances have methods described below.<br />
<br />
<h3><code>apply</code> method</h3><br />
I often work with jaxb classes similar to <code>PersonJaxb</code>, which has not all arg constructor and all fields must be set via setters. Kotlin helps to deal with it via <code>apply</code> method. Target instance is provided as delagate to closure so we could define all fields values in it and returns <code>this</code>. The signature is <code>T.apply(f: T.() -> Unit): T</code>.<br />
<br />
<pre class="brush: java">@Test
fun applyTest() {
//when
val person = PersonJaxb().apply {
firstName = "John"
lastName = "Smith"
age = 20
}
//then
assertEquals(20, person.age)
assertEquals("John", person.firstName)
assertEquals("Smith", person.lastName)
}
</pre><br />
<h3><code>let</code> method</h3><br />
Another extension is <code>let</code> method which is similar to map operation for collections. It has signature <code>T.let(f: (T) -> R): R</code>. <code>this</code> is passed as parameter to given closure/function.<br />
<br />
<pre class="brush: java">@Test
fun letTest() {
//when
val fullName = Person("John", "Smith", 20).let {
"${it.firstName} ${it.lastName}"
}
//then
assertEquals("John Smith", fullName)
}
</pre><br />
<h3><code>run</code> method</h3><br />
<code>run</code> method looks like merge of <code>apply</code> and <code>let</code> methods: access to <code>this</code> is via delegate as in <code>apply</code>, but it also returns value as in <code>let</code> method. It has signature <code>T.run(f: T.() -> R): R</code>.<br />
<br />
<pre class="brush: java">@Test
fun runTest() {
//when
val fullName = Person("John", "Smith", 20).run {
"$firstName $lastName"
}
//then
assertEquals("John Smith", fullName)
}
</pre><br />
<h3><code>to</code> method</h3><br />
Each instance has also defined <code>to</code> infix operator, which is used to create <code>Pair</code>. Pairs is helpful to create map entries. It has signature <code>A.to(that: B): Pair<A, B></code>.<br />
<br />
<pre class="brush: java">@Test
fun toTest() {
//when
val pair = Person("John", "Smith", 20) to 5
//then
assertEquals(Person("John", "Smith", 20), pair.first)
assertEquals(5, pair.second)
}
</pre><br />
<h2>Data class methods</h2><br />
Data class instances have also some other helpful methods (which are not extensions, but are generated for us).<br />
<br />
<h3><code>componentX</code> methods</h3><br />
Data class <code>Person</code> has three fields and it has component method generated for each of them: <code>component1</code> for <code>firstName</code>, <code>component2</code> for <code>lastName</code> and <code>component3</code> for <code>age</code>.<br />
<br />
<pre class="brush: java">@Test
fun componentsTest() {
//when
val p = Person("John", "Smith", 20)
//then
assertEquals("John", p.component1())
assertEquals("Smith", p.component2())
assertEquals(20, p.component3())
}
</pre><br />
Why is it helpful? <code>componentX</code> methods are used in extracting (similar to Scala case classes extracting mechanism), e. g.:<br />
<br />
<pre class="brush: java">@Test
fun extractingTest() {
//when
val (first, last, age) = Person("John", "Smith", 20)
//then
assertEquals(20, age)
assertEquals("John", first)
assertEquals("Smith", last)
}
</pre><br />
<h3><code>copy</code> method</h3><br />
<code>copy</code> method allows to create new instance based on current instance.<br />
<br />
<pre class="brush: java">@Test
fun copyTest() {
//when
val person = Person("John", "Smith", 20).copy(lastName = "Kowalski", firstName = "Jan")
//then
assertEquals(Person("Jan", "Kowalski", 20), person)
}
</pre><br />
<h2>Summary</h2><br />
Kotlin's extensions for each instances are very simple and help to solve many problems. The code written with these extensions is much more readable and concise than written in Java.<br />
<br />
Sources are available <a href="https://github.com/alien11689/kotlins-extenstions-for-each-class">here</a>.Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0tag:blogger.com,1999:blog-7262035251134282670.post-6928916003063593172015-10-11T18:43:00.003+02:002022-03-18T16:59:13.742+01:00Kotlin, Callable and ExecutorServiceI've recently written about using <a href="http://przybyszd.blogspot.com/2015/09/groovy-callable-and-executorservice.html">Callable in Groovy</a>, but how does it look like in <a href="https://kotlinlang.org/">kotlin</a>?<br />
<br />
<h2>Callable instance as separete class </h2>First, let's create class which implements Callable interface:<br />
<pre class="brush: java">class MyJob : Callable<Int> {
override fun call() = 42
}
</pre><br />
Now we could pass instance of this class to executorService:<br />
<pre class="brush: java">fun callableAsClassInstance() =
executorService.submit(MyJob()).get()
</pre><br />
When we run it, as we expect, it returns 42. (Tests are written in groovy, not in kotlin).<br />
<pre class="brush: java">def 'should submit callable as class instance from kotlin'() {
expect:
callableExample.callableAsClassInstance() == 42
}
</pre><br />
<h2>Casting to Callable</h2>If we create map with string "call" to closure or just closure and try to cast to Callable, we always obtain CastClassException:<br />
<pre class="brush: java">fun callableAsMap() =
executorService.submit(mapOf("call" to { 42 }) as Callable<Int>).get()
fun callableAsClosure() =
executorService.submit({ 42 } as Callable<Int>).get()
</pre><pre class="brush: java">def 'should submit callable as closure from kotlin'() {
when:
callableExample.callableAsClosure() == 42
then:
thrown(ClassCastException)
}
def 'should submit callable as map from kotlin'() {
when:
callableExample.callableAsMap() == 42
then:
thrown(ClassCastException)
}
</pre><br />
It does not work as in groovy...<br />
<br />
<h2>Pass instance method</h2>So maybe passing an instance method which produces value will work?<br />
<pre class="brush: java">private fun callMe() = 42
fun callableAsPassedFunction(): Int? {
return executorService.submit(::callMe).get()
}
</pre><br />
It does not even compile. Why? It moans that there is no submit method which could be called with such argument...<br />
<br />
But, what interesting, if we create a value to which we assign closure and pass it to submit method then everything is ok and get returns 42.<br />
<pre class="brush: java">private val callMe = { 42 }
fun callableAsPassedLocalFunction(): Int? {
return executorService.submit(callMe).get()
}
</pre><br />
<h2>Inline implementation</h2>Of course, there is also an option to create Callable inline:<br />
<pre class="brush: java">fun callableAsInlineImplementation() =
executorService.submit(Callable<Int> { 42 }).get()
</pre><br />
And this is IHMO the best and the most comfortable way to create Callable in kotlin, because its syntax is much nicer than in java or groovy.<br />
<br />
Source code is available <a href="https://github.com/alien11689/CallableInKotlin">here</a>.Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0tag:blogger.com,1999:blog-7262035251134282670.post-12159588798014145172015-09-20T17:09:00.002+02:002022-03-18T16:49:28.463+01:00Easy configuration usage with ConfigSlurper<h1>What's the problem?</h1><br />
We have to deal with properties in almost every projects that we write. <a href="http://docs.oracle.com/javase/8/docs/api/java/util/Properties.html">Properties</a> class, which we use in these cases, is just mapping key to value. Sometimes it is fine, but in many cases properties look like tree. Example of properties file is shown below:<br />
<br />
<pre class="brush: java">systemName=test
endpoint.first.protocol=http
endpoint.first.address=localhost
endpoint.first.port=8080
endpoint.first.path=test
endpoint.second.protocol=ftp
endpoint.second.address=localhost
endpoint.second.port=21
endpoint.second.user=admin
endpoint.second.password=pass
</pre><br />
Here we have simple properties like systemName and also complex endpoints definition (all properties which start with <i>endpoint</i>) and single endpoints definition (each endpoint properties starts with <i>endpoint.<ENDPOINT_NAME></i>). <br />
<br />
How simple could it be to treat this properties like a tree and simply extract subset of them?<br />
<br />
The answer is using <a href="http://docs.groovy-lang.org/latest/html/gapi/groovy/util/ConfigSlurper.html">ConfigSlurper</a>.<br />
<br />
<h1>ConfigSlurper from properties</h1><br />
To use ConfigSlurper just parse properties object:<br />
<br />
<pre class="brush: java">def 'should import configuration from properties'() {
given:
Properties p = new Properties()
p.load(ConfigSlurperTest.getResourceAsStream('/configuration.properties'))
expect:
new ConfigSlurper().parse(p).systemName as String == 'test'
}
</pre><br />
Parse method returns <a href="http://docs.groovy-lang.org/latest/html/gapi/groovy/util/ConfigObject.html">ConfigObject</a> which is just very clever map <a href="http://">Map</a>.<br />
<br />
Now you could get property using dot notation:<br />
<br />
<pre class="brush: java">def 'should get nested property'() {
expect:
fromProperties.endpoint.first.protocol == 'http'
}
</pre><br />
But there is a deal. If you use ConfigObject then you cannot use it like normal Properties and get property with dots.<br />
<br />
<pre class="brush: java">def 'should not used nested property as one string'() {
expect:
fromProperties.'endpoint.first.protocol' != 'http'
}
</pre><br />
ConfigObject allows you to extract subtree as Properties:<br />
<br />
<pre class="brush: java">def 'should get first endpoint info from properties'() {
expect:
fromProperties.endpoint.first.toProperties() == [
protocol: 'http',
address : 'localhost',
port : '8080',
path : 'test'
]
}
</pre><br />
and even:<br />
<br />
<pre class="brush: java">def 'should allow for nested property as one string when toProperties called'() {
expect:
fromProperties.endpoint.toProperties()['first.protocol'] == 'http'
}
</pre><br />
If you want to know how many endpoint you have and how they are named you could use keySet method:<br />
<br />
<pre class="brush: java">def 'should get list of endpoints'() {
expect:
fromProperties.endpoint.keySet() == ['first', 'second'] as Set
}
</pre><br />
ConfigSlurper do not return null even if property is not found, so you could get nested property without fear:<br />
<br />
<pre class="brush: java">def 'should not throw exception when missing property'() {
expect:
fromProperties.endpoint.third.port.toProperties() == [:] as Properties
}
</pre><br />
You have only to be careful, when have property named like begining of another property:<br />
<br />
<pre class="brush: java">def 'should throw exception when asking for too nested property'() {
when:
fromProperties.endpoint.first.port.test
then:
thrown(MissingPropertyException)
}
</pre><br />
<i>fromProperties.endpoint.first.port</i> returns String and do not have test property.<br />
<br />
You could also print properties from ConfigObject:<br />
<br />
<pre class="brush: java">println fromProperties.prettyPrint()
</pre><br />
The output looks like this:<br />
<br />
<pre class="brush: java">endpoint {
first {
path='test'
port='8080'
protocol='http'
address='localhost'
}
second {
password='pass'
protocol='ftp'
address='localhost'
port='21'
user='admin'
}
}
systemName='test'
</pre><br />
Hmm... It looks like DSL. Why do not keep your configuration in this manner?<br />
<br />
<h1>ConfigSlurper from script</h1>Your configuration could be a groovy script.<br />
<br />
<pre class="brush: java">systemName = 'test'
endpoint {
first {
path = 'test'
port = 8080
protocol = 'http'
address = 'localhost'
}
second {
password = 'pass'
protocol = 'ftp'
address = 'localhost'
port = 21
user = 'admin'
}
}
test.key = ['really': 'nested?'] as Properties
</pre><br />
You could pass such configuration as resource stream or file content:<br />
<br />
<pre class="brush: java">def 'should get config from script as url'() {
given:
ConfigObject config = new ConfigSlurper().parse(ConfigSlurperTest.getResource('/configuration.groovy'))
expect:
config.systemName == 'test'
}
def 'should get config from script as string'() {
given:
ConfigObject config = new ConfigSlurper().parse(ConfigSlurperTest.getResource('/configuration.groovy').text)
expect:
config.systemName == 'test'
}
</pre><br />
What interesting all your properties do not have to be strings. It could be any object: String, long, int, etc.<br />
<br />
<pre class="brush: java">def 'should get nested properties from script as int'() {
expect:
fromScript.endpoint.first.port == 8080
}
def 'should get really nested properties from script and continue digging'() {
expect:
fromScript.test.key.really == 'nested?'
}
</pre><br />
<h1>Conclusion</h1>You could deal with properties like simple Map, but why if you could instead use it like tree of properties?<br />
<br />
Sources are available <a href="https://github.com/alien11689/ConfigSlurperDemo">here</a>.Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0tag:blogger.com,1999:blog-7262035251134282670.post-31577524262975534172015-09-07T21:41:00.001+02:002022-03-18T16:49:50.235+01:00Groovy, Callable and ExecutorServiceSuppose you want submit job to <a href="https://docs.oracle.com/javase/8/docs/api/java/util/concurrent/ExecutorService.html">ExecutorService</a>. <br />
<br />
<h2>The Baroque version</h2>You could create a class that implements <a href="https://docs.oracle.com/javase/8/docs/api/java/util/concurrent/Callable.html">Callable</a>:<br />
<pre class="brush: java">class MyJob implements Callable<Integer>{
@Override
Integer call() throws Exception {
return 42
}
}
</pre><br />
and give it to the executor service:<br />
<br />
<pre class="brush: java">def 'submit callable as MyJob object'() {
expect:
executorService.submit(new MyJob()).get() == 42
}
</pre><br />
The response is, as expected, 42.<br />
<br />
<h2>Map as Callable version</h2>You want to use this job only in one place so why not inline this class:<br />
<pre class="brush: java">def 'submit callable as map'() {
expect:
executorService.submit([call: { 42 }] as Callable).get() == 42
}
</pre><br />
The response is again 42.<br />
<br />
<h2>Groovy closure version</h2>Why not use closure instead of map?<br />
<pre class="brush: java">def 'submit callable as closure'(){
expect:
executorService.submit { 42 }.get() == 42
}
</pre><br />
The response is ... null.<br />
<br />
<pre class="brush: java">Condition not satisfied:
executorService.submit { 42 }.get() == 42
| | | |
| | null false
| java.util.concurrent.FutureTask@21de60b4
java.util.concurrent.Executors$FinalizableDelegatedExecutorService@1700915
</pre><br />
Why? It is because Groovy treats this closure as <a href="https://docs.oracle.com/javase/8/docs/api/java/lang/Runnable.html">Runnable</a>, not <a href="https://docs.oracle.com/javase/8/docs/api/java/util/concurrent/Callable.html">Callable</a> and <a href="https://docs.oracle.com/javase/8/docs/api/java/util/concurrent/Future.html#get--">Future<t>#get</t></a> returns null when task is complete.<br />
<br />
<h2>Groovy closure version with cast</h2>We have to cast our closure before submiting to executor service:<br />
<pre class="brush: java">def 'submit callable as closure with cast'() {
when:
int result = executorService.submit({ return 42 } as Callable<Integer>).get()
then:
result == 42
}
</pre><br />
The response is, as expected, again 42.<br />
<br />
What interesting, the same test with inlined result variable fails... Strange... It could be <a href="https://code.google.com/p/spock/">Spock framework</a> error.<br />
<br />
Source code is available <a href="https://github.com/alien11689/CallableInGroovy">here</a>.Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0tag:blogger.com,1999:blog-7262035251134282670.post-60507000621022301142015-09-06T16:52:00.002+02:002022-03-18T16:50:13.642+01:00Writing JAXB in GroovySuppose you want write a jaxb class in groovy. Why? Because you do not have to write these all getters, setters and other methods. You only have to write your fields down.<br />
<br />
<code><pre class="brush: java">@XmlRootElement
@HashCodeAndEquals
@ToString
class Person {
String firstName
String lastName
Integer age
}
</pre></code><br />
<br />
Lets check if we could unmarshal xml to Person class:<br />
<br />
<code><pre class="brush: java">def 'should unmarshall person xml to object'(){
given:
JAXBContext jc = JAXBContext.newInstance(Person)
String xml = '<person><firstname>John</firstname><lastname>Smith</lastname><age>20</age></person>'
expect:
jc.createUnmarshaller().unmarshal(new StringReader(xml)) == new Person(firstName: 'John', lastName: 'Smith', age: 20)
}
</pre></code><br />
<br />
When we try this, then we obtain an eception:<br />
<br />
<code><pre class="brush: java">com.sun.xml.internal.bind.v2.runtime.IllegalAnnotationsException: 1 counts of IllegalAnnotationExceptions
groovy.lang.MetaClass is an interface, and JAXB can't handle interfaces.
this problem is related to the following location:
at groovy.lang.MetaClass
at public groovy.lang.MetaClass com.blogspot.przybyszd.jaxbingroovy.Person.getMetaClass()
at com.blogspot.przybyszd.jaxbingroovy.Person
at com.sun.xml.internal.bind.v2.runtime.IllegalAnnotationsException$Builder.check(IllegalAnnotationsException.java:91)
at com.sun.xml.internal.bind.v2.runtime.JAXBContextImpl.getTypeInfoSet(JAXBContextImpl.java:445)
at com.sun.xml.internal.bind.v2.runtime.JAXBContextImpl.<init>(JAXBContextImpl.java:277)
at com.sun.xml.internal.bind.v2.runtime.JAXBContextImpl.<init>(JAXBContextImpl.java:124)
at com.sun.xml.internal.bind.v2.runtime.JAXBContextImpl$JAXBContextBuilder.build(JAXBContextImpl.java:1123)
at com.sun.xml.internal.bind.v2.ContextFactory.createContext(ContextFactory.java:147)
at javax.xml.bind.ContextFinder.newInstance(ContextFinder.java:247)
at javax.xml.bind.ContextFinder.newInstance(ContextFinder.java:234)
at javax.xml.bind.ContextFinder.find(ContextFinder.java:462)
at javax.xml.bind.JAXBContext.newInstance(JAXBContext.java:641)
at javax.xml.bind.JAXBContext.newInstance(JAXBContext.java:584)
at com.blogspot.przybyszd.jaxbingroovy.PersonJaxbTest.should unmarshall person xml to object(PersonJaxbTest.groovy:10)
</init></init>
</pre></code><br />
<br />
It is because groovy defines getMetaClass method for us. Marshaller and Unmarshaller use by default <a href="http://docs.oracle.com/javaee/7/api/javax/xml/bind/annotation/XmlAccessType.html#PUBLIC_MEMBER">XmlAccessType.PUBLIC_MEMBER</a> what means that public getters and setters should be used during marshalling/unmarshalling.<br />
<br />
To solve this just add <a href="http://docs.oracle.com/javaee/7/api/javax/xml/bind/annotation/XmlAccessorType.html">XmlAccessorType</a> annotatnio with <a href="http://docs.oracle.com/javaee/7/api/javax/xml/bind/annotation/XmlAccessType.html#FIELD">XmlAccessType.FIELD</a> on jaxb class:<br />
<br />
<code><pre class="brush: java">@XmlRootElement
@EqualsAndHashCode
@XmlAccessorType(XmlAccessType.FIELD)
class Person {
String firstName
String lastName
Integer age
}
</pre></code><br />
<br />
Of course if you want to apply this rule for each jaxb class in package, then you could put XmlAccessorType in pacakge-info.java file.<br />
<br />
<code><pre class="brush: java">@XmlAccessorType(XmlAccessType.FIELD)
package com.blogspot.przybyszd.jaxbingroovy;
import javax.xml.bind.annotation.XmlAccessType;
import javax.xml.bind.annotation.XmlAccessorType;
</pre></code><br />
<br />
Great, it works.<br />
<br />
Now let's check out marshaller:<br />
<br />
<code><br />
<pre class="brush: java">def 'should marshall person'() {
given:
JAXBContext jc = JAXBContext.newInstance(Person)
Person p = new Person(firstName: 'John', lastName: 'Smith', age: 20)
StringWriter sw = new StringWriter()
when:
jc.createMarshaller().marshal(p, sw)
then:
String xml = sw.toString()
GPathResult gPathResult = new XmlSlurper().parseText(xml)
gPathResult.name() == 'person'
gPathResult.firstName == 'John'
gPathResult.lastName == 'Smith'
gPathResult.age == '20'
}
</pre></code><br />
<br />
And it also works.<br />
<br />
Source is available <a href="https://github.com/alien11689/JaxbInGroovy">here</a>.Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0tag:blogger.com,1999:blog-7262035251134282670.post-9602933635442722092015-08-16T21:46:00.000+02:002015-09-06T17:09:32.978+02:00All field constructor in GroovyTupleConstructor annotation in Groovy generate constructors for class with each of its properties (eventually also fields). The class below<br />
<br />
<pre class="brush: java">@TupleConstructor(includeFields = true)
class Person {
String firstName
String lastName
private boolean male
}
</pre><br />
will have constructors: Person(), Persion(String), Person(String, String) and Person(String, String, boolean). You could test it using code below.<br />
<br />
<pre class="brush: java">class TupleConstructorTest extends GroovyTestCase{
@Test
void testSimpleTupleConstructorShouldGenerateConstructor() {
assertScript '''
import groovy.transform.TupleConstructor
@TupleConstructor(includeFields = true)
class Person {
private final String firstName
private final String lastName
private final boolean male
String toString(){ "$firstName $lastName $male" }
}
assert Person.constructors.size() == 4
assert new Person().toString() == 'null null false'
assert new Person('John').toString() == 'John null false'
assert new Person('John','Smith').toString() == 'John Smith false'
assert new Person('John','Smith', true).toString() == 'John Smith true'
'''
}
}
</pre><br />
I almost always create classes with all private final fields and generate constructior with all fields using my IDE.<br />
<br />
So I have prepared new transformation AllFieldConstructor which bases on TupleConstructor and generates only constructor with all fields as parameters.<br />
<br />
<pre class="brush: java">class AllFieldConstructorTest extends GroovyTestCase{
@Test
void testSimpleTupleConstructorShouldGenerateConstructor() {
assertScript '''
import com.blogspot.przybyszd.transformations.AllFieldConstructor
@AllFieldConstructor
class Person {
private final String firstName
private final String lastName
private final boolean male
String toString(){ "$firstName $lastName $male" }
}
assert Person.constructors.size() == 1
assert new Person('John','Smith', true).toString() == 'John Smith true'
'''
}
}
</pre><br />
The sources are available <a href="https://github.com/alien11689/groovy-transformations">here</a>Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0tag:blogger.com,1999:blog-7262035251134282670.post-27339228483990264092015-06-04T18:17:00.000+02:002015-09-06T17:09:46.572+02:00Git aliases for better Gerrit usage<h2>What is Gerrit?</h2><div><a href="https://code.google.com/p/gerrit/">Gerrit</a> is a web application for code review and git project management. You push commit to specific ref in Gerrit and your collaborators could comment your code, give you a score (-2, -1, 0, 1, 2) or merge it with specific branch. Gerrit generates also events, so yout CI server (for example <a href="https://jenkins-ci.org/">Jenkins</a>) could start build based on this commit and give the positive score if build is <i>green</i> or negative if it fails.</div><div><br />
</div><h2>Pushing commits to gerrit</h2><div>If you want to push commit to gerrit, then commit has to have generated Change-Id, which is uniq review identifier. You do not need to generate Change-Id on your own, because you could install pre-commit hook from Gerrit:</div><div><br />
</div><div><pre class="brush: bash">gitdir=$(git rev-parse --git-dir); scp -p -P <GERRIT_PORT> <GERRIT_SSH>:hooks/commit-msg ${gitdir}/hooks/</div></pre><div><br />
</div><div>Of course, you have to set GERRIT_PORT and GERRIT_SSH to point to yout Gerrit.</div><div><br />
</div><div>To push a commit for review you should use command:</div><div><br />
</div><div><pre class="brush: bash">git push origin HEAD:refs/for/<BRANCH_NAME>
</pre></div><div><br />
</div><div>It means that your current HEAD should be pushed to remote reference on origin (if Gerrit remote repository is named as origin). BRANCH_NAME is the remote branch with which your code will be compared and to which your commit should be merged (if it pass review).</div><div><br />
</div><div>You often push to master so there is alias to push as review for master in alias section in ~/.gitconfig (globally) or .git/config (only in current repository):</div><div><br />
</div><div><pre class="brush: bash">[alias]
...
push-for-review = push origin HEAD:refs/for/master
...
</pre><br />
To execute it just type:<br />
<br />
<pre class="brush: bash">git push-for-review
</pre><br />
If I want to push as review to another branch then I use another alias:<br />
<br />
<pre class="brush: bash">[alias]
...
push-for-review-branch = !git push origin HEAD:refs/for/$1
...
</pre><br />
and branch name could be pass as argument from command line:<br />
<br />
<pre class="brush: bash">git push-for-review-branch <BRANCH_NAME>
</pre><br />
<h2>Pushing drafts</h2></div><div>If you think that your commit is not ready to merge with remote branch, but you want to share it or just have it in remote repository, you could push it to draft reference. Draft on gerrit is available only for you and other users which are invited by you. Draft could be pushed via command:</div><div><br />
</div><div><pre class="brush: bash">git push origin HEAD:refs/drafts/<BRANCH_NAME>
</pre></div><div><br />
</div><div>Branch name must be given, because draft could be published and then merged, so branch have to be known before.</div><div><br />
</div><div>There also are simple aliases, which could be used in the same way as during push for review:<br />
<br />
<pre class="brush: bash">[alias]
...
push-as-draft = push origin HEAD:refs/drafts/master
push-as-draft-branch = !git push origin HEAD:refs/drafts/$1
...</div></pre><h2>Invite for review</h2><div>After pushing for review or draft you could invite user or group, then they will be notified by Gerrit about new change. To invite from command line there should be added four aliases:<br />
<br />
<pre class="brush: bash">[alias]
...
gerrit-remote = "!sh -c \"git remote -v | grep push | grep ssh | grep gerrit | head -1 | awk '{print $2}' | cut -d'/' -f3\""
gerrit-host = "!sh -c \"git gerrit-remote | cut -d':' -f1\""
gerrit-port = "!sh -c \"git gerrit-remote | cut -d':' -f2\""
gerrit-invite = "!sh -c \"ssh -p `git gerrit-port` `git gerrit-host` 'gerrit set-reviewers --add' $1 `git log | grep Change-Id | head -1 | tr -d ' ' | cut -d':' -f2`\""
...
</pre><br />
First alias selects remote repository which contains <i>gerrit</i> in name or url, could be used to push via ssh and extracts url to this repository.<br />
<br />
Second and third alias uses the first to extract host and port from repository url. It is necessary for executing remote command via ssh.<br />
<br />
The last alias extract Change-Id from HEAD and add user or group given form command line. Example usage:<br />
<br />
<pre class="brush: bash">git gerrit-invite <USER_OR_GROUP>
</pre></div><h2>Summary</h2><div>Gerrit is a great tool for git management and code reviewing, but it is difficult to type all references by memory. Git aliases described here are great support and simplify Gerrit usage.</div>Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0tag:blogger.com,1999:blog-7262035251134282670.post-19369525714431021132015-03-29T10:50:00.000+02:002015-09-06T17:10:03.265+02:00All you need is docker (and fig)<div><h1>Introduction</h1></div><div>Suppose you want to run scala repl or groovy shell or any other repl-like executable. You should download executable, unpack it, set PATH environmnt variable and now you could use it. Can it be simple? Yes, dockerize everything.</div><div><br />
</div><div><h1>Prepare containers</h1></div><div>I expect that you have installed <a href="https://www.docker.com/">docker</a> and <a href="http://www.fig.sh/">fig</a> on your machine.</div><div>Checkout <a href="https://github.com/alien11689/docker-with-fig">this project</a> from github and build containers:</div><div><br />
</div><div><pre class="brush: bash">$ cd docker-with-fig</pre></div><div><pre class="brush: bash">$ fig build </pre></div><div><br />
</div><div>It could take several minutes, depends on your internet connection.</div><div><br />
</div><div>You could also build only some of available container, for example with scala and groovy:</div><div><pre class="brush: bash">$ fig build scala groovy</pre></div><div><br />
</div><div>Available containers are:</div><ul><li>haskell</li>
<li>scala</li>
<li>groovy</li>
<li>python27</li>
<li>python34</li>
<li>clojure</li>
</ul><h1>Run containers</h1><div>Now you could start for example scala:</div><div><pre class="brush: bash">$ fig run scala</pre></div><div><pre class="brush: bash">Welcome to Scala version 2.11.6 (Java HotSpot(TM) 64-Bit Server VM, Java 1.8.0_40).
Type in expressions to have them evaluated.
Type :help for more information.
scala></pre></div><div><br />
</div><div>Or groovy:</div><div><pre class="brush: bash">$ fig run groovy</pre></div><div><pre class="brush: bash">Mar 29, 2015 7:48:22 AM java.util.prefs.FileSystemPreferences$1 run
INFO: Created user preferences directory.
Groovy Shell (2.4.2, JVM: 1.8.0_40)
Type ':help' or ':h' for help.
-------------------------------------------------------------------------------
groovy:000></pre></div><div><br />
</div><div>Or clojure with lein:</div><div><pre class="brush: bash">$ fig run clojure</pre></div><div><pre class="brush: bash">nREPL server started on port 52730 on host 127.0.0.1 - nrepl://127.0.0.1:52730
REPL-y 0.3.5, nREPL 0.2.6
Clojure 1.6.0
Java HotSpot(TM) 64-Bit Server VM 1.8.0_40-b25
Docs: (doc function-name-here)
(find-doc "part-of-name-here")
Source: (source function-name-here)
Javadoc: (javadoc java-object-or-class-here)
Exit: Control+D or (exit) or (quit)
Results: Stored in vars *1, *2, *3, an exception in *e
user=></pre></div><div><br />
</div><div>Or python 3.4:</div><div><pre class="brush: bash">$ fig run python34</pre></div><div><pre class="brush: bash">Python 3.4.2 (default, Oct 8 2014, 13:08:17)
[GCC 4.9.1] on linux
Type "help", "copyright", "credits" or "license" for more information.
>>></pre></div><div><br />
</div><div>Or ghci haskell:</div><div><pre class="brush: bash">$fig run haskell</pre></div><div><pre class="brush: bash">GHCi, version 7.6.3: http://www.haskell.org/ghc/ :? for help
Loading package ghc-prim ... linking ... done.
Loading package integer-gmp ... linking ... done.
Loading package base ... linking ... done.
Prelude></pre></div><div><br />
</div><div><div>You could also run command on docker container with use of files from your current directory because it is mapped to /project directory on docker. Container starts with /project directory as current directory.</div><div>For example you have a simple file in your current dir:</div><div><pre class="brush: bash">$ cat simplePrint.scala </pre></div><div><pre class="brush: bash">println("Hello World")</pre></div><div><br />
You could run command with this file:<br />
<br />
</div><div><pre class="brush: bash">$ fig -f PATH_TO_DOCKER_WITH_FIG_PROJECT/fig.yml run scala scala simplePrint.scala</pre></div><div><pre class="brush: bash">Hello World</pre></div><div><br />
</div><div>First 'scala' in command means that you want to run scala container and 'scala simplePrint.scala' means that you want to execute this command on container.</div><div><br />
</div><h1>Conclusion</h1><div>It is simple, isn't it? All you need is docker and fig and you could use repl or run command with scala, groovy, cojure and any other which are currently supported...</div></div>Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0tag:blogger.com,1999:blog-7262035251134282670.post-34306053945231549502014-06-21T19:17:00.001+02:002014-06-21T19:22:04.703+02:00Sorting photos after holiday<h1>Introduction</h1>When my wife an I are on vacation, we always take photos using two cameras. One is my own and second belongs to my wife. After holidays we want to have one folder with all the photos sorted by date and time and named in this manner, so we do not have to select sort_by_date each time we want to view them. Of course, date and time on our cameras are synchronized.<br />
<br />
<h1>Main</h1>Creation date and time could be obtain from photo file using <i><a href="http://owl.phy.queensu.ca/~phil/exiftool/">exiftool</a></i> program from command line:<br />
<pre class="brush: bash">$ exiftool DSCN6201.JPG</pre>and the output looks like this:<br />
<pre class="brush: bash">ExifTool Version Number : 9.13
File Name : DSCN6201.JPG
Directory : .
File Size : 2.8 MB
...</pre>Date/Time Original : 2013:08:15 08:56:34<br />
Create Date : 2013:08:15 08:56:34<br />
...<br />
I have written shell script which using exiftool rename all JPG files in current directory with <i>prefix_yyyy_mm_dd__hh_mm_ss.JPG</i> pattern. I only have to copy script file to photo directory and execute it with given prefix:<br />
<pre class="brush: bash">$ ls
DSCN6201.JPG DSCN6203.JPG DSCN8338.JPG DSCN8340.JPG
DSCN6202.JPG DSCN8337.JPG DSCN8339.JPG sorter.sh
$ ./sorter.sh holidays
$ ls
holidays_2013_08_15__08_55_55.JPG holidays_2013_08_15__08_56_34.JPG
holidays_2013_08_15__08_56_08.JPG holidays_2013_08_17__08_37_44.JPG
holidays_2013_08_15__08_56_22.JPG holidays_2013_08_17__08_41_55.JPG
holidays_2013_08_15__08_56_29.JPG sorter.sh</pre>Script is available <a href="https://bitbucket.org/alien11689/photosorter">here</a>.<br />
<br />
<h1>Conclusion</h1>Simple shell script can rename all your photos based on their creation date and time.Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0tag:blogger.com,1999:blog-7262035251134282670.post-26173180022197130582014-05-25T13:51:00.001+02:002014-05-25T13:51:17.544+02:00Convert html page to mobi<h1>Introduction</h1>Sometimes I want to read webpage on my kindle. There are many pictures and source code blocks on this. What can you do? You can print webpage as pdf, but this is not good idea, because you cannot scale such document on kindle. Mobi is better file format so there must be better option and indeed is.<br />
<br />
<h1>Kindlegen</h1><div>Amazon provides little program called <a href="http://www.amazon.com/gp/feature.html?docId=1000765211">kindlegen</a>, which could convert html, epub and some other formats to another and there is mobi. You have to save webpage with all css files and images somewhere on your disk. You could do this for example with <a href="http://www.google.pl/intl/pl/chrome/browser/">Google Chrome</a>, just push CTRL+S and select place. Now you should have html file and directory name like your html file without extension, but with _files suffix. For example I have download <a href="http://przybyszd.blogspot.com/">this webpage</a> on my desktop and I have file <span style="font-family: Courier New, Courier, monospace;">Przybysz Dominik TechBlog.html </span>and <span style="font-family: Courier New, Courier, monospace;">Przybysz Dominik TechBlog_files</span> directory.</div><div>To use kindlegen you need all css and image files placed in the same directory as html file, so all local links from html files have to have deleted prefix describing directory. For example I have deleted <span style="font-family: Courier New, Courier, monospace;">./Przybysz Dominik TechBlog_files/</span><span style="font-family: inherit;"> <span style="font-family: inherit;">f</span>rom all src atributtes and moved html file to directory with other files.</span></div><div><span style="font-family: inherit;">Now you could use kindlegen:</span></div><pre class="brush: java">kindlegen Przybysz\ Dominik\ TechBlog.html -o blog.mobi</pre>Now your mobi file is ready to be placed on you kindle.<br />
<br />
<h1>Conclusion</h1><div>With one simple program you could convert any webpage to mobi format and read it on your kindle.</div><br />
Dominik Przybyszhttp://www.blogger.com/profile/16007058624118936033noreply@blogger.com0