Skip to content

Commit 0d6a0eb

Browse files
committed
Merge tag 'v1.6.3' via #647
Thank you @joseph-flinn!
2 parents 9150529 + 09f2569 commit 0d6a0eb

File tree

7 files changed

+157
-63
lines changed

7 files changed

+157
-63
lines changed

Diff for: .github/workflows/tests.yml

+3-3
Original file line numberDiff line numberDiff line change
@@ -29,13 +29,13 @@ jobs:
2929
run: |
3030
curl -O -sSL https://raw.githubusercontent.com/sdispater/poetry/master/get-poetry.py
3131
python get-poetry.py -y --version 1.0.10
32-
echo "::set-env name=PATH::$HOME/.poetry/bin:$PATH"
32+
echo "PATH=${HOME}/.poetry/bin:${PATH}" >> $GITHUB_ENV
3333
rm get-poetry.py
3434
3535
- name: Get poetry cache paths from config
3636
run: |
37-
echo ::set-env name=poetry_cache_dir::$(poetry config --list | sed -n 's/.*cache-dir = //p' | sed -e 's/^"//' -e 's/"$//')
38-
echo ::set-env name=poetry_virtualenvs_path::$(poetry config --list | sed -n 's/.*virtualenvs.path = .* # //p' | sed -e 's/^"//' -e 's/"$//')
37+
echo "poetry_cache_dir=$(poetry config --list | sed -n 's/.*cache-dir = //p' | sed -e 's/^\"//' -e 's/\"$//')" >> $GITHUB_ENV
38+
echo "poetry_virtualenvs_path=$(poetry config --list | sed -n 's/.*virtualenvs.path = .* # //p' | sed -e 's/^\"//' -e 's/\"$//')" >> $GITHUB_ENV
3939
4040
- name: Configure poetry
4141
shell: bash

Diff for: CHANGES

+11
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,17 @@ tmuxp 1.7.0a1 (2020-11-07)
2424

2525
Thank you @joseph-flinn!
2626

27+
tmuxp 1.6.3 (2020-11-22)
28+
------------------------
29+
- :issue:`647` Adding option to dump `load` output to log file, thank you
30+
@joseph-flinn!
31+
32+
``tmuxp load file.yaml --log-file yourfile.txt``
33+
34+
Adjust log levels:
35+
36+
``tmuxp --log-level DEBUG load file.yaml --log-file yourfile.txt``
37+
2738
tmuxp 1.6.2 (2020-11-08)
2839
------------------------
2940
- :issue:`643` New command ``tmuxp debug-info`` for creating github

Diff for: README.rst

+10-2
Original file line numberDiff line numberDiff line change
@@ -181,8 +181,15 @@ Plugin System
181181
tmuxp has a plugin system to allow for custom behavior. See more about the
182182
`Plugin System`_.
183183
184-
Debug Info
185-
----------
184+
Debugging Helpers
185+
-----------------
186+
187+
The ``load`` command provides a way to log output to a log file for debugging
188+
purposes.
189+
190+
.. code-block:: sh
191+
192+
$ tmuxp load --log-file <log-file-name> .
186193
187194
Collect system info to submit with a Github issue:
188195
@@ -196,6 +203,7 @@ Collect system info to submit with a Github issue:
196203
197204
# ... so on
198205
206+
199207
Docs / Reading material
200208
-----------------------
201209

Diff for: docs/cli.rst

+12-1
Original file line numberDiff line numberDiff line change
@@ -184,12 +184,23 @@ are created, the last session is named from the terminal.
184184
185185
$ tmxup load -s <new_session_name> <filename1> ...
186186
187+
The output of the ``load`` command can be logged to a file for
188+
debugging purposes. the log level can be controlled with the global
189+
``--log-level`` option (defaults to INFO).
190+
191+
.. code-block:: bash
192+
193+
$ tmuxp load <filename> --log-file <log_filename>
194+
$ tmuxp --log-level <LEVEL> load <filename> --log-file <log_filename>
195+
196+
187197
.. _cli_debug_info:
188198

189199
Debug Info
190200
----------
191201

192-
Use to collect all relevant information for submitting an issue to the project.
202+
Use to collect all relevant information for submitting an issue to
203+
the project.
193204

194205
.. code-block:: bash
195206

Diff for: tests/test_cli.py

+27
Original file line numberDiff line numberDiff line change
@@ -413,6 +413,33 @@ def test_load_zsh_autotitle_warning(cli_args, tmpdir, monkeypatch):
413413
assert 'Please set' not in result.output
414414

415415

416+
@pytest.mark.parametrize(
417+
"cli_args",
418+
[
419+
(['load', '.', '--log-file', 'log.txt']),
420+
],
421+
)
422+
def test_load_log_file(cli_args, tmpdir, monkeypatch):
423+
# create dummy tmuxp yaml that breaks to prevent actually loading tmux
424+
tmpdir.join('.tmuxp.yaml').write(
425+
"""
426+
session_name: hello
427+
"""
428+
)
429+
tmpdir.join('.oh-my-zsh').ensure(dir=True)
430+
monkeypatch.setenv('HOME', str(tmpdir))
431+
432+
with tmpdir.as_cwd():
433+
print('tmpdir: {0}'.format(tmpdir))
434+
runner = CliRunner()
435+
436+
# If autoconfirm (-y) no need to prompt y
437+
input_args = 'y\ny\n' if '-y' not in cli_args else ''
438+
439+
runner.invoke(cli.cli, cli_args, input=input_args)
440+
assert 'Loading' in tmpdir.join('log.txt').open().read()
441+
442+
416443
@pytest.mark.parametrize("cli_cmd", ['shell', ('shell', '--pdb')])
417444
@pytest.mark.parametrize(
418445
"cli_args,inputs,env,expected_output",

Diff for: tmuxp/cli.py

+50-29
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,18 @@ def get_cwd():
4343
return os.getcwd()
4444

4545

46+
def tmuxp_echo(message=None, log_level='INFO', style_log=False, **click_kwargs):
47+
"""
48+
Combines logging.log and click.echo
49+
"""
50+
if style_log:
51+
logger.log(log.LOG_LEVELS[log_level], message)
52+
else:
53+
logger.log(log.LOG_LEVELS[log_level], click.unstyle(message))
54+
55+
click.echo(message, **click_kwargs)
56+
57+
4658
def get_config_dir():
4759
"""
4860
Return tmuxp configuration directory.
@@ -247,8 +259,8 @@ def scan_config_argument(ctx, param, value, config_dir=None):
247259
config_dir = config_dir()
248260

249261
if not config:
250-
click.echo("Enter at least one CONFIG")
251-
click.echo(ctx.get_help(), color=ctx.color)
262+
tmuxp_echo("Enter at least one CONFIG")
263+
tmuxp_echo(ctx.get_help(), color=ctx.color)
252264
ctx.exit()
253265

254266
if isinstance(value, string_types):
@@ -358,11 +370,14 @@ def scan_config(config, config_dir=None):
358370
]
359371

360372
if len(candidates) > 1:
361-
click.secho(
362-
'Multiple .tmuxp.{yml,yaml,json} configs in %s' % dirname(config),
363-
fg="red",
373+
tmuxp_echo(
374+
click.style(
375+
'Multiple .tmuxp.{yml,yaml,json} configs in %s'
376+
% dirname(config),
377+
fg="red",
378+
)
364379
)
365-
click.echo(
380+
tmuxp_echo(
366381
click.wrap_text(
367382
'This is undefined behavior, use only one. '
368383
'Use file names e.g. myproject.json, coolproject.yaml. '
@@ -548,6 +563,11 @@ def load_workspace(
548563
# get the canonical path, eliminating any symlinks
549564
config_file = os.path.realpath(config_file)
550565

566+
tmuxp_echo(
567+
click.style('[Loading] ', fg='green')
568+
+ click.style(config_file, fg='blue', bold=True)
569+
)
570+
551571
# kaptan allows us to open a yaml or json file as a dict
552572
sconfig = kaptan.Kaptan()
553573
sconfig = sconfig.import_config(config_file).get()
@@ -570,7 +590,7 @@ def load_workspace(
570590
sconf=sconfig, plugins=load_plugins(sconfig), server=t
571591
)
572592
except exc.EmptyConfigException:
573-
click.echo('%s is empty or parsed no config data' % config_file, err=True)
593+
tmuxp_echo('%s is empty or parsed no config data' % config_file, err=True)
574594
return
575595

576596
session_name = sconfig['session_name']
@@ -590,11 +610,6 @@ def load_workspace(
590610
return
591611

592612
try:
593-
click.echo(
594-
click.style('[Loading] ', fg='green')
595-
+ click.style(config_file, fg='blue', bold=True)
596-
)
597-
598613
builder.build() # load tmux session via workspace builder
599614

600615
if 'TMUX' in os.environ: # tmuxp ran from inside tmux
@@ -631,8 +646,8 @@ def load_workspace(
631646
except exc.TmuxpException as e:
632647
import traceback
633648

634-
click.echo(traceback.format_exc(), err=True)
635-
click.echo(e, err=True)
649+
tmuxp_echo(traceback.format_exc(), err=True)
650+
tmuxp_echo(e, err=True)
636651

637652
choice = click.prompt(
638653
'Error loading workspace. (k)ill, (a)ttach, (d)etach?',
@@ -642,7 +657,7 @@ def load_workspace(
642657

643658
if choice == 'k':
644659
builder.session.kill_session()
645-
click.echo('Session killed.')
660+
tmuxp_echo('Session killed.')
646661
elif choice == 'a':
647662
_reattach(builder)
648663
else:
@@ -658,7 +673,7 @@ def load_workspace(
658673
@click.group(context_settings={'obj': {}})
659674
@click.version_option(__version__, '-V', '--version', message='%(prog)s %(version)s')
660675
@click.option(
661-
'--log_level',
676+
'--log-level',
662677
default='INFO',
663678
help='Log level (DEBUG, INFO, WARNING, ERROR, CRITICAL)',
664679
)
@@ -671,12 +686,12 @@ def cli(log_level):
671686
try:
672687
has_minimum_version()
673688
except TmuxCommandNotFound:
674-
click.echo('tmux not found. tmuxp requires you install tmux first.')
689+
tmuxp_echo('tmux not found. tmuxp requires you install tmux first.')
675690
sys.exit()
676691
except exc.TmuxpException as e:
677-
click.echo(e, err=True)
692+
tmuxp_echo(e, err=True)
678693
sys.exit()
679-
setup_logger(level=log_level.upper())
694+
setup_logger(logger=logger, level=log_level.upper())
680695

681696

682697
def setup_logger(logger=None, level='INFO'):
@@ -695,12 +710,12 @@ def setup_logger(logger=None, level='INFO'):
695710
logger = logging.getLogger()
696711

697712
if not logger.handlers: # setup logger handlers
698-
channel = logging.StreamHandler()
699-
channel.setFormatter(log.DebugLogFormatter())
700-
713+
# channel = logging.StreamHandler()
714+
# channel.setFormatter(log.DebugLogFormatter())
701715
# channel.setFormatter(log.LogFormatter())
716+
702717
logger.setLevel(level)
703-
logger.addHandler(channel)
718+
# logger.addHandler(channel)
704719

705720

706721
def startup(config_dir):
@@ -921,6 +936,7 @@ def command_freeze(session_name, socket_name, socket_path, force):
921936
flag_value=88,
922937
help='Like -2, but indicates that the terminal supports 88 colours.',
923938
)
939+
@click.option('--log-file', help='File to log errors/output to')
924940
def command_load(
925941
ctx,
926942
config,
@@ -930,6 +946,7 @@ def command_load(
930946
answer_yes,
931947
detached,
932948
colors,
949+
log_file,
933950
):
934951
"""Load a tmux workspace from each CONFIG.
935952
@@ -954,6 +971,10 @@ def command_load(
954971
detached mode.
955972
"""
956973
util.oh_my_zsh_auto_title()
974+
if log_file:
975+
logfile_handler = logging.FileHandler(log_file)
976+
logfile_handler.setFormatter(log.LogFormatter())
977+
logger.addHandler(logfile_handler)
957978

958979
tmux_options = {
959980
'socket_name': socket_name,
@@ -965,8 +986,8 @@ def command_load(
965986
}
966987

967988
if not config:
968-
click.echo("Enter at least one CONFIG")
969-
click.echo(ctx.get_help(), color=ctx.color)
989+
tmuxp_echo("Enter at least one CONFIG")
990+
tmuxp_echo(ctx.get_help(), color=ctx.color)
970991
ctx.exit()
971992

972993
if isinstance(config, string_types):
@@ -1008,7 +1029,7 @@ def import_config(configfile, importfunc):
10081029
else:
10091030
sys.exit('Unknown config format.')
10101031

1011-
click.echo(
1032+
tmuxp_echo(
10121033
newconfig + '---------------------------------------------------------------'
10131034
'\n'
10141035
'Configuration import does its best to convert files.\n'
@@ -1030,9 +1051,9 @@ def import_config(configfile, importfunc):
10301051
buf.write(newconfig)
10311052
buf.close()
10321053

1033-
click.echo('Saved to %s.' % dest)
1054+
tmuxp_echo('Saved to %s.' % dest)
10341055
else:
1035-
click.echo(
1056+
tmuxp_echo(
10361057
'tmuxp has examples in JSON and YAML format at '
10371058
'<http://tmuxp.git-pull.com/examples.html>\n'
10381059
'View tmuxp docs at <http://tmuxp.git-pull.com/>'
@@ -1171,4 +1192,4 @@ def format_tmux_resp(std_resp):
11711192
% format_tmux_resp(tmux_cmd('show-window-options', '-g')),
11721193
]
11731194

1174-
click.echo('\n'.join(output))
1195+
tmuxp_echo('\n'.join(output))

0 commit comments

Comments
 (0)