REPL Environment
2023-07-19
Today I created a REPL (Read, Evaluate, Print, Loop) environment for my math language
that I am making in Java. I simply have a Repl class with a constructor and methods corresponding to each word
in the acronym. At first, there was only one parameter for the constructor, a Scanner
. But when I wanted
to test the read()
method, I realized I would have to create a mock Scanner
class which is actually
impossible because Scanner
is a final
class. This made me rethink and ultimately decide to have the constructor
take in an InputStream
instead. This is good because I can now test read()
by supplying the InputStream
with bytes, and
I can also still take input from System.in
because it is a type of InputStream
. This also makes it possible
to read code in from a file, since InputStream
could have data from a file. The story is very similar
with the print()
method. At first, I wanted to just print to System.out
, but I couldn't test this, so I instead
abstracted the functionality into a PrintStream
that is passed into the constructor. This is a very
clean solution and results in a very nice one-liner main
function:
public static void main(String[] args) throws IOException {
new Repl(System.in,System.out).loop();
}
This experience shows how tests encourage you to depend on abstractions rather than concretions and therefore writing cleaner code that adheres to the SOLID principles.