diff options
Diffstat (limited to 'src/repl')
-rw-r--r-- | src/repl/scala/tools/nsc/interpreter/ILoop.scala | 20 | ||||
-rw-r--r-- | src/repl/scala/tools/nsc/interpreter/Pasted.scala | 20 |
2 files changed, 21 insertions, 19 deletions
diff --git a/src/repl/scala/tools/nsc/interpreter/ILoop.scala b/src/repl/scala/tools/nsc/interpreter/ILoop.scala index 89061730f6..992cafb9c6 100644 --- a/src/repl/scala/tools/nsc/interpreter/ILoop.scala +++ b/src/repl/scala/tools/nsc/interpreter/ILoop.scala @@ -765,16 +765,13 @@ class ILoop(in0: Option[BufferedReader], protected val out: JPrintWriter) } private object paste extends Pasted { + import scala.util.matching.Regex.quote val ContinueString = " | " - val PromptString = "scala> " - val testPrompt = PromptString.trim - val testOurPrompt = prompt.trim - val testBoth = testPrompt != testOurPrompt + val PromptString = prompt.lines.toList.last + val anyPrompt = s"""\\s*(?:${quote(PromptString.trim)}|${quote(AltPromptString.trim)})\\s*""".r - def isPrompt(line: String) = { - val text = line.trim - text == testOurPrompt || (testBoth && text == testPrompt) - } + def isPrompted(line: String) = matchesPrompt(line) + def isPromptOnly(line: String) = line match { case anyPrompt() => true ; case _ => false } def interpret(line: String): Unit = { echo(line.trim) @@ -784,10 +781,9 @@ class ILoop(in0: Option[BufferedReader], protected val out: JPrintWriter) def transcript(start: String) = { echo("\n// Detected repl transcript paste: ctrl-D to finish.\n") - apply(Iterator(start) ++ readWhile(!isPrompt(_))) + apply(Iterator(start) ++ readWhile(!isPromptOnly(_))) } } - import paste.{ ContinueString, PromptString } /** Interpret expressions starting with the first line. * Read lines until a complete compilation unit is available @@ -809,7 +805,7 @@ class ILoop(in0: Option[BufferedReader], protected val out: JPrintWriter) echo("You typed two blank lines. Starting a new command.") None } - else in.readLine(ContinueString) match { + else in.readLine(paste.ContinueString) match { case null => // we know compilation is going to fail since we're at EOF and the // parser thinks the input is still incomplete, but since this is @@ -833,7 +829,7 @@ class ILoop(in0: Option[BufferedReader], protected val out: JPrintWriter) * and avoid the interpreter, as it's likely not valid scala code. */ if (code == "") None - else if (!paste.running && code.trim.startsWith(PromptString)) { + else if (!paste.running && paste.isPrompted(code)) { paste.transcript(code) None } diff --git a/src/repl/scala/tools/nsc/interpreter/Pasted.scala b/src/repl/scala/tools/nsc/interpreter/Pasted.scala index f5db3d9e3a..1600f32946 100644 --- a/src/repl/scala/tools/nsc/interpreter/Pasted.scala +++ b/src/repl/scala/tools/nsc/interpreter/Pasted.scala @@ -16,17 +16,21 @@ package interpreter * the same result. */ abstract class Pasted { + def interpret(line: String): Unit def ContinueString: String def PromptString: String - def interpret(line: String): Unit + def AltPromptString: String = "scala> " + + private val testBoth = PromptString != AltPromptString + private val spacey = " \t".toSet - def matchesPrompt(line: String) = matchesString(line, PromptString) + def matchesPrompt(line: String) = matchesString(line, PromptString) || testBoth && matchesString(line, AltPromptString) def matchesContinue(line: String) = matchesString(line, ContinueString) def running = isRunning private def matchesString(line: String, target: String): Boolean = ( (line startsWith target) || - (line.nonEmpty && " \t".toSet(line.head) && matchesString(line.tail, target)) + (line.nonEmpty && spacey(line.head) && matchesString(line.tail, target)) ) private def stripString(line: String, target: String) = line indexOf target match { case -1 => line @@ -39,7 +43,9 @@ abstract class Pasted { private class PasteAnalyzer(val lines: List[String]) { val referenced = lines flatMap (resReference findAllIn _.trim.stripPrefix("res")) toSet - val cmds = lines reduceLeft append split PromptString filterNot (_.trim == "") toList + val ActualPromptString = lines find matchesPrompt map (s => + if (matchesString(s, PromptString)) PromptString else AltPromptString) getOrElse PromptString + val cmds = lines reduceLeft append split ActualPromptString filterNot (_.trim == "") toList /** If it's a prompt or continuation line, strip the formatting bits and * assemble the code. Otherwise ship it off to be analyzed for res references @@ -67,10 +73,10 @@ abstract class Pasted { */ def fixResRefs(code: String, line: String) = line match { case resCreation(resName) if referenced(resName) => - code.lastIndexOf(PromptString) match { + code.lastIndexOf(ActualPromptString) match { case -1 => code case idx => - val (str1, str2) = code splitAt (idx + PromptString.length) + val (str1, str2) = code splitAt (idx + ActualPromptString.length) str2 match { case resAssign(`resName`) => code case _ => "%sval %s = { %s }".format(str1, resName, str2) @@ -82,7 +88,7 @@ abstract class Pasted { def run() { println("// Replaying %d commands from transcript.\n" format cmds.size) cmds foreach { cmd => - print(PromptString) + print(ActualPromptString) interpret(cmd) } } |