Skip to content

Commit 30c7b2a

Browse files
committed
Removed the need to be inside a 'structured' block when calling the 'race' function
1 parent 9bbc5e0 commit 30c7b2a

File tree

3 files changed

+73
-87
lines changed

3 files changed

+73
-87
lines changed

README.md

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -178,7 +178,7 @@ The library provides the `race` method to race two jobs. The `race` function ret
178178

179179
```scala 3
180180
val results = new ConcurrentLinkedQueue[String]()
181-
val actual: Int | String = structured {
181+
val actual: Int | String =
182182
race[Int, String](
183183
{
184184
delay(1.second)
@@ -190,7 +190,6 @@ val actual: Int | String = structured {
190190
"42"
191191
}
192192
)
193-
}
194193
actual should be("42")
195194
results.toArray should contain theSameElementsInOrderAs List("job2")
196195
```

core/src/main/scala/in/rcard/sus4s/sus4s.scala

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -232,7 +232,7 @@ object sus4s {
232232
* <h2>Example</h2>
233233
* {{{
234234
* val results = new ConcurrentLinkedQueue[String]()
235-
* val actual: Int | String = structured {
235+
* val actual: Int | String =
236236
* race[Int, String](
237237
* {
238238
* delay(1.second)
@@ -244,7 +244,6 @@ object sus4s {
244244
* "42"
245245
* }
246246
* )
247-
* }
248247
* actual should be("42")
249248
* results.toArray should contain theSameElementsInOrderAs List("job2")
250249
* }}}
@@ -260,7 +259,7 @@ object sus4s {
260259
* @return
261260
* The result of the first block that completes
262261
*/
263-
def race[A, B](firstBlock: Suspend ?=> A, secondBlock: Suspend ?=> B): Suspend ?=> A | B = {
262+
def race[A, B](firstBlock: Suspend ?=> A, secondBlock: Suspend ?=> B): A | B = {
264263
val loomScope = new ShutdownOnSuccess[A | B]()
265264
given suspended: Suspend = SuspendScope(loomScope.asInstanceOf[StructuredTaskScope[Any]])
266265
try {

core/src/test/scala/RaceSpec.scala

Lines changed: 70 additions & 82 deletions
Original file line numberDiff line numberDiff line change
@@ -10,126 +10,114 @@ import scala.util.Try
1010
class RaceSpec extends AnyFlatSpec with Matchers {
1111
"Racing two functions" should "return the result of the first one that completes and cancel the execution of the other" in {
1212
val results = new ConcurrentLinkedQueue[String]()
13-
val actual: Int | String = structured {
14-
race[Int, String](
15-
{
16-
delay(1.second)
17-
results.add("job1")
18-
throw new RuntimeException("Error")
19-
}, {
20-
delay(500.millis)
21-
results.add("job2")
22-
"42"
23-
}
24-
)
25-
}
13+
val actual: Int | String = race[Int, String](
14+
{
15+
delay(1.second)
16+
results.add("job1")
17+
throw new RuntimeException("Error")
18+
}, {
19+
delay(500.millis)
20+
results.add("job2")
21+
"42"
22+
}
23+
)
2624

2725
actual should be("42")
2826
results.toArray should contain theSameElementsInOrderAs List("job2")
2927
}
3028

3129
it should "return the result of the second one if the first one throws an exception" in {
3230
val results = new ConcurrentLinkedQueue[String]()
33-
val actual: Int | String = structured {
34-
race(
35-
{
36-
delay(1.second)
37-
results.add("job1")
38-
42
39-
}, {
40-
delay(500.millis)
41-
results.add("job2")
42-
throw new RuntimeException("Error")
43-
}
44-
)
45-
}
31+
val actual: Int | String = race(
32+
{
33+
delay(1.second)
34+
results.add("job1")
35+
42
36+
}, {
37+
delay(500.millis)
38+
results.add("job2")
39+
throw new RuntimeException("Error")
40+
}
41+
)
4642

4743
actual should be(42)
4844
results.toArray should contain theSameElementsInOrderAs List("job2", "job1")
4945
}
5046

5147
it should "honor the structural concurrency and wait for all the jobs to complete" in {
5248
val results = new ConcurrentLinkedQueue[String]()
53-
val actual: Int | String = structured {
54-
race(
55-
{
56-
val job1 = fork {
57-
fork {
58-
delay(2.second)
59-
results.add("job3")
60-
}
61-
delay(1.second)
62-
results.add("job1")
49+
val actual: Int | String = race(
50+
{
51+
val job1 = fork {
52+
fork {
53+
delay(2.second)
54+
results.add("job3")
6355
}
64-
42
65-
}, {
66-
delay(500.millis)
67-
throw new RuntimeException("Error")
56+
delay(1.second)
57+
results.add("job1")
6858
}
69-
)
70-
}
59+
42
60+
}, {
61+
delay(500.millis)
62+
throw new RuntimeException("Error")
63+
}
64+
)
7165

7266
actual should be(42)
7367
results.toArray should contain theSameElementsInOrderAs List("job1", "job3")
7468
}
7569

7670
it should "throw the exception thrown by the first function both throw an exception" in {
7771
val expectedResult = Try {
78-
structured {
79-
race(
80-
{
81-
delay(1.second)
82-
throw new RuntimeException("Error in job1")
83-
}, {
84-
delay(500.millis)
85-
throw new RuntimeException("Error in job2")
86-
}
87-
)
88-
}
72+
race(
73+
{
74+
delay(1.second)
75+
throw new RuntimeException("Error in job1")
76+
}, {
77+
delay(500.millis)
78+
throw new RuntimeException("Error in job2")
79+
}
80+
)
8981
}
9082

9183
expectedResult.failure.exception shouldBe a[RuntimeException]
9284
expectedResult.failure.exception.getMessage shouldBe "Error in job2"
9385
}
9486

9587
it should "honor the structural concurrency and return the value of the second function if the first threw an exception" in {
96-
val actual: Int | String = structured {
97-
race(
98-
{
99-
val job1 = fork {
100-
delay(500.millis)
101-
println("job1")
102-
throw new RuntimeException("Error in job1")
103-
}
104-
42
105-
}, {
106-
delay(1.second)
107-
println("job2")
108-
"42"
88+
val actual: Int | String = race(
89+
{
90+
val job1 = fork {
91+
delay(500.millis)
92+
println("job1")
93+
throw new RuntimeException("Error in job1")
10994
}
110-
)
111-
}
95+
42
96+
}, {
97+
delay(1.second)
98+
println("job2")
99+
"42"
100+
}
101+
)
112102

113103
actual should be("42")
114104
}
115105

116106
it should "honor the structured concurrency and cancel all the children jobs" in {
117107
val results = new ConcurrentLinkedQueue[String]()
118-
val actual: Int | String = structured {
119-
race(
120-
{
121-
val job1 = fork {
122-
delay(1.seconds)
123-
results.add("job1")
124-
}
125-
42
126-
}, {
127-
delay(500.millis)
128-
results.add("job2")
129-
"42"
108+
val actual: Int | String = race(
109+
{
110+
val job1 = fork {
111+
delay(1.seconds)
112+
results.add("job1")
130113
}
131-
)
132-
}
114+
42
115+
}, {
116+
delay(500.millis)
117+
results.add("job2")
118+
"42"
119+
}
120+
)
133121

134122
Thread.sleep(2000)
135123

0 commit comments

Comments
 (0)