5

I use Byobu with zsh when working on my research. I have many windows open, and often each of them is running a different experiment. When I run an experiment, the experiment executable creates a new folder for the experiment results, which looks like $MELFI0/.polina/2024-09-08-10-09-32-056727, and it outputs it to stdout.

When I browse through the different windows in Byobu, I want to be able to immediately copy that results folder path $MELFI0/.polina/2024-09-08-10-09-32-056727 that was written to stdout in that window. The catch is that the experiment executable is writing a lot of data to stdout, so if I want to find the results folder path, I have to scroll up a lot, and then manually mark it with the caret to copy it. That's quite laborious.

Is there a quicker way to do this? I want to have a setup where I can easily press some kind of key binding (like Ctrl-A R) and the results folder path of the experiment running in the current window is automatically found and copied to Byobu's clipboard.

5
  • If the terminal has a Status line capability: ref: $ man terminfo as the man -page is visible, type: / +Status Lines and /status - that might be one way; display the filename within a "status", i.e. on a not-scrolling line. Commented Sep 8, 2024 at 8:30
  • One might also investigate "scroll region" possibilities. All of this might be available as ANSI-sequences or by terminfo / termcap $ tput <command> use. Commented Sep 8, 2024 at 8:36
  • Related; ncurses Commented Sep 8, 2024 at 8:50
  • Tip: github.com/pdanford/TerminalScrollRegionsDisplay Commented Sep 8, 2024 at 8:52
  • Your terminal may have the possibility to search for a string, so if you prefix the path with some marker, the terminal can search it for your. Other possibility: Have your script copy the path to your clipboard. Yet another possibility: Have your script the path written to , for instance (using zsh syntax here:), /tmp/melfi$TTY:t). You can then retrieve the path easily from within every window. Commented Sep 10, 2024 at 8:36

1 Answer 1

0
+200

Hello,

my solution consists of the following parts:

  • saving the results folder path to a variable, local to the window that the binary runs in
  • creating key bind to copy said variable's contents to the clipboard.

  1. Note: to quickly test the idea with variables you can do:

    export results_path="$(env | grep -o $HOME | head -n 1)"
    echo $results_path
    

    Do I have to clarify what the output should look like? :]


  2. To save some part of STDOUT to a variable after running your_script binary the easiest solution (IMO!) is to add to your ~/.zshrc (or /etc/zsh/zshrc for global sourcing) the following (trivial ;]) function:

    capture_results_path() {
        results_path="$(your_script | grep -o $MELFI0/.polina/.* | head -n 1)"
        # OR - for capturing STDERR (choose ONE!): 
        results_path="$(your_script 2>&1 | grep -o $MELFI0/.polina/.* | head -n 1)"
    }
    
    • if it's possible that the output will sometimes produce more paths starting at $MELFI0/.polina/ and leading to other locations than your results folder you'd have to add some regex instead of .*, for example:

      results_path="$(your_script | grep -o "$MELFI0/.polina/[0-9]\{4\}-[0-9]\{2\}-[0-9]\{2\}-[0-9]\{2\}-[0-9]\{2\}-[0-9]\{2\}-[0-9]\{1,10\}" | head -n 1)"
      
    • also note, that to utilize the new functionality you'll have to run your experiment by invoking capture_results_path (which will execute whatever you put instead of your_script) - so I'd suggest to use something short, like qaz:

      qaz() {
          results_path="$(your_script | grep -o "$MELFI0/.polina/[0-9]\{4\}-[0-9]\{2\}-[0-9]\{2\}-[0-9]\{2\}-[0-9]\{2\}-[0-9]\{2\}-[0-9]\{1,10\}" | head -n 1)"
      }
      

  3. To create the shortcut that'll copy the focused-on windows' variable to the clipboard you'll need to invoke xclip (to install: apt-get install xclip / yum install xclip / dnf install xclip - or whatever else your distro uses). Then its another one-liner, that you have to add to your ~/.zshrc or /etc/zsh/zshrc:

    bindkey -s '^q' 'echo $results_path | xclip -selection clipboard\n'
    

    The above command binds copying the variable from the currently focused-on window to the shortcut CTRL+q. It should work for both foreground and background executables.


  1. Bonus1: to quickly debug simple regex - execute (for the different user change /root/ to /home/username/:

    export HOME1=/root/2024-09-08-10-09-32-056727 # so we have $HOME1 in "env"
    export results_path="$(env | grep -o "$HOME/[0-9]\{4\}-[0-9]\{2\}-[0-9]\{2\}-[0-9]\{2\}-[0-9]\{2\}-[0-9]\{2\}-[0-9]\{1,10\}")"
    echo $results_path
    

    The output of echo should be: /root/2024-09-08-10-09-32-056727 - or whatever else you exported as $HOME1. For the more advanced regex-es I recommend regex101.com


  1. Bonus2: To check if Byobu uses the same key combination (like CTRL+q), you can list Byobu’s key bindings using the following command:
    byobu-ctrl-a-keys
    

Enjoy! And feel free to ask in case of unclearness ;]

3
  • Thank you. I'd rather not launch my executable from a function. I want my executable to write this data to a window-specific place. Is that possible? Commented Sep 17, 2024 at 14:46
  • @RamRachum well, the function is trivial and shouldn't interfere in any way, but if you insist I think you can achieve it. Note, that the goal is to catch the instance-specific, newly generated path to a variable. Depending on your executable: if it's some kind of script you could simply add the appropriate command at the bottom of it, if it's a binary (which I suspect it is) - it may be problematic. The purpose of closing the command in a function is TO PREVENT IT FROM RUNNING every time you spawn new terminal - I just tested few options and all of them regrettably run the executable. Commented Sep 18, 2024 at 13:15
  • @RamRachum you could try running your executable directly using the command results_path="$(your_script | grep -o "$MELFI0/.polina/[0-9]\{4\}-[0-9]\{2\}-[0-9]\{2\}-[0-9]\{2\}-[0-9]\{2\}-[0-9]\{2\}-[0-9]\{1,10\}" | head -n 1)". Commented Sep 18, 2024 at 13:31

You must log in to answer this question.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.