"""
sm.run_sfi(dedent( macro drop _all
local local1 = 1
local local2 "two"
local local3 `""3""' """))
"""disp `"`local1' `local2' `local3'"' """) run_as_program_w_locals(
1 two "3"
We can run multi-line Stata code as a Stata program to prevent the echo of commands. But this approach requires special care for handling both local macros and valid Stata code that cannot be run inside a Stata program.
(Note: An alternative approach, prepending each Stata command with noisily
and placing them inside a quietly
block, was rejected at a certain point as more difficult overall, but it may be worth revisiting if unanticipated issues with the current run-as-program approach arise.)
We aim to run Stata code inside a Stata program, yet handling locals as if the code were run normally (rather than inside the program scope).
We accomplish this by first grabbing any previously-defined locals (with stata_more.get_local_dict
) and artificially defining their values at the start of the program (using stata_more.locals_code_from_dict
).
Then we also want to artificially transfer any locals created within the program to the outside scope. We do this by making the program an s-class program and storing any locals present at the end of the program via sreturn
. These locals can then be quietly defined in the main scope after the program run has completed.
run_as_program_w_locals (std_code, local_dict=None)
sm.run_sfi(dedent("""
macro drop _all
local local1 = 1
local local2 "two"
local local3 `""3""' """))
run_as_program_w_locals("""disp `"`local1' `local2' `local3'"' """)
1 two "3"
code = '''\
local test1 "blah blah"
local test2 "blah"
'''
run_as_program_w_locals("""disp `"`local1' `local2' `local3'"' \n""" + code)
test_eq(sm.get_local_dict(),
{'test2': 'blah',
'test1': 'blah blah',
'local1': '1',
'local2': 'two',
'local3': '"3"'})
1 two "3"
run_non_prog_noecho (std_non_prog_code, run_as_prog=<function run_as_program_w_locals>)
We remove comments from single-line code to avoid the error that would otherwise result.
Certain valid Stata code (referred to here as prog_code
because it defines Stata programs–or runs mata or python code blocks) cannot be run inside a Stata program, so we need to identify such code and run it separately.
run_prog_noecho (std_prog_code)
Other programs (that is, Stata’s program define
, as well as mata or python blocks) cannot be defined/run within a Stata program, however. Instead, we will just run them directly, quietly to prevent echo, except for the case of mata programs, in which case quietly
would block the output.
prog_block_code = dedent("""\
program define display1
disp "display1 output"
end
""")
run_prog_noecho(prog_block_code)
run_single("display1")
display1 output
hello
. mata:
------------------------------------------------- mata (type end to exit) -----
: display("hello")
hello
: end
-------------------------------------------------------------------------------
.
run_noecho (code, sc_delimiter=False, run_as_prog=<function run_as_program_w_locals>)
After break_out_prog_blocks
, run each prog and non-prog block noecho
run_noecho(dedent('''\
capture program drop ender
program define ender
disp "ender output"
end
capture program drop display2
program define display2
ender
end
display2
'''))
ender output
run_noecho(dedent("""\
disp `"`local1' `local2' `local3'"'
disp `"`local1' `local2' `local3' `test1'"'
"""), run_as_prog=run_as_program_w_locals)
1 two "3"
1 two "3" blah blah
code = """\
local local1 "foo"
local local2 "bar"
local abcd "foo bar"
"""
run_noecho(code, run_as_prog=run_as_program_w_locals)
run_noecho(dedent("""\
disp `"`local1' `local2' `local3'"'
disp `"`local1' `local2' `local3' `test1'"'
"""), run_as_prog=run_as_program_w_locals)
foo bar "3"
foo bar "3" blah blah
(1978 automobile data)
Price
-------------------------------------------------------------
Percentiles Smallest
1% 3291 3291
5% 3748 3299
10% 3895 3667 Obs 74
25% 4195 3748 Sum of wgt. 74
50% 5006.5 Mean 6165.257
Largest Std. dev. 2949.496
75% 6342 13466
90% 11385 13594 Variance 8699526
95% 13466 14500 Skewness 1.653434
99% 15906 15906 Kurtosis 4.819188