Skip to content

Commit 9489649

Browse files
committed
Migrate Ammonite REPL tests to Scala 3 REPL
1 parent 514ea74 commit 9489649

File tree

2 files changed

+174
-8
lines changed

2 files changed

+174
-8
lines changed

modules/integration/src/test/scala/scala/cli/integration/ReplAmmoniteTestDefinitions.scala

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ import com.eed3si9n.expecty.Expecty.expect
55
import scala.cli.integration.TestUtil.{normalizeArgsForWindows, removeAnsiColors}
66

77
trait ReplAmmoniteTestDefinitions { this: ReplTestDefinitions =>
8-
protected val ammonitePrefix: String = "Ammonite REPL:"
8+
protected val ammonitePrefix: String = "Running in Ammonite REPL:"
99
def expectedScalaVersionForAmmonite: String =
1010
actualScalaVersion match {
1111
case s

modules/integration/src/test/scala/scala/cli/integration/ReplTestDefinitions.scala

Lines changed: 173 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ package scala.cli.integration
33
import com.eed3si9n.expecty.Expecty.expect
44

55
import scala.cli.integration.TestUtil.removeAnsiColors
6+
import scala.util.Properties
67

78
abstract class ReplTestDefinitions extends ScalaCliSuite with TestScalaVersionArgs {
89
this: TestScalaVersion =>
@@ -15,23 +16,39 @@ abstract class ReplTestDefinitions extends ScalaCliSuite with TestScalaVersionAr
1516
actualScalaVersion.coursierVersion >= "3.7.0-RC1".coursierVersion
1617

1718
protected val dryRunPrefix: String = "Dry run:"
18-
protected val runInReplPrefix: String = "Running in REPL:"
19+
protected val runInReplPrefix: String = "Running in Scala REPL:"
1920

2021
def runInRepl(
2122
codeToRunInRepl: String,
22-
testInputs: TestInputs = TestInputs.empty
23-
)(f: os.CommandResult => Unit): Unit = {
23+
testInputs: TestInputs = TestInputs.empty,
24+
cliOptions: Seq[String] = Seq.empty,
25+
shouldPipeStdErr: Boolean = false,
26+
check: Boolean = true,
27+
env: Map[String, String] = Map.empty
28+
)(
29+
runAfterRepl: os.CommandResult => Unit,
30+
runBeforeReplAndGetExtraCliOpts: () => Seq[os.Shellable] = () => Seq.empty
31+
): Unit = {
2432
testInputs.fromRoot { root =>
25-
f(
33+
val potentiallyExtraCliOpts = runBeforeReplAndGetExtraCliOpts()
34+
runAfterRepl(
2635
os.proc(
2736
TestUtil.cli,
2837
"repl",
38+
".",
2939
"--repl-quit-after-init",
3040
"--repl-init-script",
3141
codeToRunInRepl,
32-
extraOptions
42+
extraOptions,
43+
cliOptions,
44+
potentiallyExtraCliOpts
3345
)
34-
.call(cwd = root)
46+
.call(
47+
cwd = root,
48+
stderr = if shouldPipeStdErr then os.Pipe else os.Inherit,
49+
env = env,
50+
check = check
51+
)
3552
)
3653
}
3754
}
@@ -114,11 +131,160 @@ abstract class ReplTestDefinitions extends ScalaCliSuite with TestScalaVersionAr
114131
expect(output.contains("typer"))
115132
}
116133

117-
if canRunInRepl then
134+
if canRunInRepl then {
118135
test(s"$runInReplPrefix simple") {
119136
val expectedMessage = "1337"
120137
runInRepl(s"""println($expectedMessage)""")(r =>
121138
expect(r.out.trim() == expectedMessage)
122139
)
123140
}
141+
142+
test(s"$runInReplPrefix verify Scala version from the REPL") {
143+
val opts = if actualScalaVersion.startsWith("3") && !isScala38OrNewer then
144+
Seq("--with-compiler")
145+
else Seq.empty
146+
runInRepl(
147+
codeToRunInRepl = s"""println($retrieveScalaVersionCode)""",
148+
cliOptions = opts
149+
)(r => expect(r.out.trim() == actualScalaVersion))
150+
}
151+
152+
test(s"$runInReplPrefix test scope") {
153+
val message = "something something something REPL"
154+
runInRepl(
155+
codeToRunInRepl = "println(example.TestScopeExample.message)",
156+
testInputs = TestInputs(
157+
os.rel / "example" / "TestScopeExample.test.scala" ->
158+
s"""package example
159+
|
160+
|object TestScopeExample {
161+
| def message: String = "$message"
162+
|}
163+
|""".stripMargin
164+
),
165+
cliOptions = Seq("--test")
166+
)(r => expect(r.out.trim() == message))
167+
}
168+
169+
test(s"$runInReplPrefix https://github.com/scala/scala3/issues/21229") {
170+
runInRepl(
171+
codeToRunInRepl = "println(stuff.baz)",
172+
testInputs = TestInputs(
173+
os.rel / "Pprint.scala" ->
174+
"""//> using dep com.lihaoyi::pprint::0.9.0
175+
|package stuff
176+
|import scala.quoted.*
177+
|def foo = pprint(1)
178+
|inline def bar = pprint(1)
179+
|inline def baz = ${ bazImpl }
180+
|def bazImpl(using Quotes) = '{ pprint(1) }
181+
|""".stripMargin
182+
)
183+
)(res => expect(res.out.trim().nonEmpty))
184+
}
185+
186+
if !Properties.isWin then {
187+
test(s"$runInReplPrefix ScalaPy") {
188+
val opts =
189+
if actualScalaVersion.startsWith("3") && !isScala38OrNewer then Seq("--with-compiler")
190+
else Seq.empty
191+
runInRepl(
192+
codeToRunInRepl =
193+
s"""import me.shadaj.scalapy.py
194+
|println("Hello" + " from Scala " + $retrieveScalaVersionCode)
195+
|val sth = py.module("foo.something")
196+
|py.Dynamic.global.applyDynamicNamed("print")("" -> sth.messageStart, "" -> sth.messageEnd, "flush" -> py.Any.from(true))
197+
|""".stripMargin,
198+
testInputs = TestInputs(
199+
os.rel / "foo" / "something.py" ->
200+
"""messageStart = 'Hello from'
201+
|messageEnd = 'ScalaPy'
202+
|""".stripMargin
203+
),
204+
cliOptions = Seq("--python", "--power") ++ opts,
205+
shouldPipeStdErr = true
206+
) { res =>
207+
val output = res.out.trim().linesIterator.toVector.take(2).mkString("\n")
208+
expect(output ==
209+
s"""Hello from Scala $actualScalaVersion
210+
|Hello from ScalaPy""".stripMargin)
211+
}
212+
}
213+
214+
test(s"$runInReplPrefix ScalaPy with PYTHONSAFEPATH") {
215+
val opts =
216+
if actualScalaVersion.startsWith("3") && !isScala38OrNewer then Seq("--with-compiler")
217+
else Seq.empty
218+
runInRepl(
219+
codeToRunInRepl =
220+
s"""import me.shadaj.scalapy.py
221+
|println("Hello" + " from Scala " + $retrieveScalaVersionCode)
222+
|val sth = py.module("foo.something")
223+
|py.Dynamic.global.applyDynamicNamed("print")("" -> sth.messageStart, "" -> sth.messageEnd, "flush" -> py.Any.from(true))
224+
|""".stripMargin,
225+
testInputs = TestInputs(
226+
os.rel / "foo" / "something.py" ->
227+
"""messageStart = 'Hello from'
228+
|messageEnd = 'ScalaPy'
229+
|""".stripMargin
230+
),
231+
cliOptions = Seq("--python", "--power") ++ opts,
232+
shouldPipeStdErr = true,
233+
// check = false, // technically should be an error, but the REPL itself doesn't return it as such.
234+
env = Map("PYTHONSAFEPATH" -> "foo")
235+
) { errorRes =>
236+
// expect(errorRes.exitCode != 0) // technically should be an error, but the REPL itself doesn't return it as such.
237+
val errorOutput = TestUtil.removeAnsiColors(errorRes.err.trim() + errorRes.out.trim())
238+
expect(errorOutput.contains("No module named 'foo'"))
239+
}
240+
}
241+
242+
test(s"$runInReplPrefix with extra JAR") {
243+
runInRepl(codeToRunInRepl =
244+
"""import shapeless._; println("Here's an HList: " + (2 :: true :: "a" :: HNil))"""
245+
)(
246+
runBeforeReplAndGetExtraCliOpts = () =>
247+
val shapelessJar =
248+
os.proc(TestUtil.cs, "fetch", "--intransitive", "com.chuusai:shapeless_2.13:2.3.7")
249+
.call()
250+
.out
251+
.text()
252+
.trim
253+
Seq("--jar", shapelessJar)
254+
,
255+
runAfterRepl = res => expect(res.out.trim() == "Here's an HList: 2 :: true :: a :: HNil")
256+
)
257+
}
258+
259+
if !isScala38OrNewer then
260+
// TODO rewrite this test to work with Scala 3.8+ once 3.8.0 stable is out
261+
test(s"$runInReplPrefix as jar") {
262+
val inputs = TestInputs(
263+
os.rel / "CheckCp.scala" ->
264+
"""//> using dep com.lihaoyi::os-lib:0.9.1
265+
|package checkcp
266+
|class CheckCp
267+
|object CheckCp {
268+
| def hasDir: Boolean = {
269+
| val uri: java.net.URI = classOf[checkcp.CheckCp].getProtectionDomain.getCodeSource.getLocation.toURI
270+
| os.isDir(os.Path(java.nio.file.Paths.get(uri)))
271+
| }
272+
|}
273+
|""".stripMargin
274+
)
275+
val code = """println("hasDir=" + checkcp.CheckCp.hasDir)"""
276+
runInRepl(codeToRunInRepl = code, testInputs = inputs) {
277+
res => expect(res.out.trim().contains("hasDir=true"))
278+
}
279+
runInRepl(
280+
codeToRunInRepl = code,
281+
testInputs = inputs,
282+
cliOptions = Seq("--as-jar", "--power")
283+
) {
284+
res => expect(res.out.trim().contains("hasDir=false"))
285+
}
286+
287+
}
288+
}
289+
}
124290
}

0 commit comments

Comments
 (0)