+ var dir = file.dirname
+ if dir != "" then dir.mkdir
+ var f
+ f = new FileWriter.open(file)
+ f.write("# GENERATED FILE\n")
+ f.write("# Docunits extracted from comments\n")
+ if mmodule != null then
+ f.write("import {mmodule.name}\n")
+ end
+ f.write("\n")
+ return f
+ end
+
+ # Compile an unit file and return the compiler return code
+ #
+ # Can terminate the program if the compiler is not found
+ private fun compile_unitfile(file: String): Int
+ do
+ var nit_dir = toolcontext.nit_dir
+ var nitc = nit_dir/"bin/nitc"
+ if not nitc.file_exists then
+ toolcontext.error(null, "Error: cannot find nitc. Set envvar NIT_DIR.")
+ toolcontext.check_errors
+ end
+ var opts = new Array[String]
+ if mmodule != null then
+ opts.add "-I {mmodule.location.file.filename.dirname}"
+ end
+ var cmd = "{nitc} --ignore-visibility --no-color '{file}' {opts.join(" ")} >'{file}.out1' 2>&1 </dev/null -o '{file}.bin'"
+ var res = sys.system(cmd)
+ return res
+ end
+end
+
+private class NitunitDecorator
+ super HTMLDecorator
+
+ var executor: NitUnitExecutor
+
+ redef fun add_code(v, block) do
+ var code = block.raw_content
+ var meta = block.meta or else "nit"
+ # Do not try to test non-nit code.
+ if meta != "nit" then return
+ # Try to parse code blocks
+ var ast = executor.toolcontext.parse_something(code)
+
+ # Skip pure comments
+ if ast isa TComment then return
+
+ # We want executable code
+ if not (ast isa AModule or ast isa ABlockExpr or ast isa AExpr) then
+ var message = ""
+ if ast isa AError then message = " At {ast.location}: {ast.message}."
+ executor.toolcontext.warning(executor.mdoc.location, "invalid-block", "Error: there is a block of invalid Nit code, thus not considered a nitunit. To suppress this warning, enclose the block with a fence tagged `nitish` or `raw` (see `man nitdoc`).{message}")
+ executor.failures.add("{executor.mdoc.location}: Invalid block of code.{message}")