improve term result

pull/373/head
Shuhei Kadowaki 2020-06-14 00:57:12 +09:00
parent dadce5110c
commit 7d6fddc749
3 changed files with 40 additions and 39 deletions

View File

@ -30,6 +30,7 @@ end
# utilitity functions
take2string!(io) = String(take!(io))
joinlines(lines) = join(lines, '\n')
"""
list_out_formats()
@ -217,7 +218,7 @@ function weave(
rm(intermediate)
elseif doctype == "md2pdf"
run_latex(doc, out_path, latex_cmd)
out_path = get_out_path(doc, out_path, ext = "pdf")
out_path = get_out_path(doc, out_path, "pdf")
end
@info "Weaved to $(out_path)"

View File

@ -15,7 +15,7 @@ const _DEFAULT_PARAMS = Dict{Symbol,Any}(
:fig_path => DEFAULT_FIG_PATH,
:dpi => 96,
:term => false,
:prompt => "\njulia> ",
:prompt => "julia>",
:label => nothing,
:wrap => true,
:line_width => 75,

View File

@ -192,55 +192,40 @@ function run_inline(inline::InlineCode, doc::WeaveDoc, report::Report, mod::Modu
return inline
end
reset_report(report::Report) = report.figures = String[]
function run_code(doc::WeaveDoc, chunk::CodeChunk, report::Report, mod::Module)
ss = parse_input(chunk.content)
n = length(ss)
results = ChunkOutput[]
for (i, s) in enumerate(ss)
reset_report(report)
obj, out = capture_output(
mod,
s,
doc.path,
chunk.options[:term],
i == n,
chunk.options[:error],
)
figures = report.figures # Captured figures
result = ChunkOutput(s, out, report.rich_output, figures)
report.rich_output = ""
push!(results, result)
end
return results
code = chunk.content
path = doc.path
error = chunk.options[:error]
codes = chunk.options[:term] ? split_code(code) : [code]
capture = code -> capture_output(code, mod, path, error, report)
return capture.(codes)
end
# Parse chunk input to array of expressions
function parse_input(s)
function split_code(code)
res = String[]
s = lstrip(s)
n = sizeof(s)
pos = 1
while (oldpos = pos) n
_, pos = Meta.parse(s, pos)
push!(res, s[oldpos:pos-1])
e = 1
ex = :init
while true
s = e
ex, e = Meta.parse(code, s)
isnothing(ex) && break
push!(res, strip(code[s:e-1]))
end
return res
end
function capture_output(mod, s, path, term, lastline, error)
local out = nothing
local obj = nothing
function capture_output(code, mod, path, error, report)
reset_report!(report)
old = stdout
rw, wr = redirect_stdout()
reader = @async read(rw, String)
local out = nothing
task_local_storage(:SOURCE_PATH, path) do
try
obj = include_string(mod, s, path) # TODO: fix line number
!isnothing(obj) && (term || lastline) && display(obj)
obj = include_string(mod, code, path) # TODO: fix line number
!isnothing(obj) && display(obj)
catch _err
err = unwrap_load_err(_err)
error || throw(err)
@ -254,13 +239,19 @@ function capture_output(mod, s, path, term, lastline, error)
end
end
out = replace(out, r"\u001b\[.*?m" => "") # remove ANSI color codes
return (obj, out)
return ChunkOutput(code, remove_ansi_code(out), report.rich_output, report.figures)
end
function reset_report!(report)
report.rich_output = ""
report.figures = String[]
end
unwrap_load_err(err) = return err
unwrap_load_err(err::LoadError) = return err.error
remove_ansi_code(s) = replace(s, r"\u001b\[.*?m" => "")
function eval_chunk(doc::WeaveDoc, chunk::CodeChunk, report::Report, mod::Module)
if !chunk.options[:eval]
chunk.output = ""
@ -399,7 +390,7 @@ function collect_term_results(chunk::CodeChunk)
prompt = chunk.options[:prompt]
result_chunks = CodeChunk[]
for r in chunk.result
output *= string(prompt, r.code, r.stdout)
output *= string('\n', indent_term_code(prompt, r.code), '\n', r.stdout)
if !isempty(r.figures)
rchunk = CodeChunk(
"",
@ -429,6 +420,15 @@ function collect_term_results(chunk::CodeChunk)
return result_chunks
end
function indent_term_code(prompt, code)
prompt_with_space = string(prompt, ' ')
n = length(prompt_with_space)
pads = ' ' ^ n
return map(enumerate(split(code, '\n'))) do (i,line)
isone(i) ? string(prompt_with_space, line) : string(pads, line)
end |> joinlines
end
function collect_hold_results(chunk::CodeChunk)
for r in chunk.result
chunk.output *= r.stdout