- Published on
Running a Screen Session with Multiple Tabs and Long Running Tasks
- Authors
- Name
- Yair Mark
- @yairmark
Example dApp Monorepo Structure
In my post about monorepos, I spoke about how one advantage of a monorepo is that you can have scripts in the root of the project to help streamline your development process.
To illustrate how this works pretend I have an Ethereum decentralized app (dApp) monorepo that has the following structure:
makefile
server
-> package.json
-> App.js
-> ...
chain
-> contracts
-> SomeContract1.sol
-> SomeContract2.sol
-> ...
-> tests
-> SomeContract1-test.js
-> SomeContract2-test.js
-> ...
package.json
ui -> package.json
-> App.js
-> ...
Makefile to Streamline the Process
An example of such a makefile that can help streamline my dev process by starting up all the pieces would look like below:
start-all-locally:
screen -AdmS my-session-name -t tab0 bash
screen -S my-session-name -X screen -t server -m yarn --cwd ./server run restart
screen -S my-session-name -X screen -t ganache -m ganache-cli -p 8545
screen -S my-session-name -X screen -t scripts-1 -m sleep 1000; yarn --cwd ./chain run clean-migrate; yarn --cwd ./server run bulkinsert
screen -S my-session-name -X screen -t ui -m yarn --cwd ./ui run start
In the above:
screen -AdmS my-session-name -t tab0 bash
:- this creates a new screen session (
-S
) calledmy-session-name
. - adds a tab (
-t
) calledtab0
to this session and runsbash
in it. - detaches from the session
-d
.
- this creates a new screen session (
screen -S my-session-name -X screen -t tab-name -m some-shell-command
.- executes a command (
-X
) in our session calledmy-session-name
.- The command executed is
screen -t tab-name -m some-shell-command
.- This calls the screen command to add a new tab called
tab-name
and runsome-shell-command
in that tab. - Commands are executed from the root of where screen is run, in our case this is the root of the monorepo.
- This calls the screen command to add a new tab called
- The command executed is
- executes a command (
yarn --cwd ./some-directory-in-my-project
: I found thatcd some-directory-in-my-project && yarn run some-script
does not work in screen.--cwd
changes the working directory for yarn and makes it run against the specified directory.
screen -t scripts-1 -m sleep 1000; yarn --cwd ./chain run clean-migrate; yarn --cwd ./server run bulkinsert
:sleep 1000
: After starting Ganache I've found you need to force the migration steps to wait to give Ganache enough time to start.yarn --cwd ./chain run clean-migrate
: As mentioned before I had issues usingcd
with screen and I could not work out how to get truffle to run from a specified path. A simple workaround was to add a script to thechain
directory'spackage.json
file which does this for me and use yarn to run it:
...
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1",
"clean-migrate": "rm -fr build || true && truffle migrate"
},
...
.screenrc file to Make Screen More User-Friendly
To make screen more useable I use the following .screenrc
file which I place in my home directory:
startup_message off
vbell off
hardstatus alwayslastline "%{=b}%{G} %{b}%w %=%{kG}%C%A %D,%d/%m/%y"
shelltitle "Shell"
# Window numbering starts at 1, not 0.
bind c screen 1
bind 0 select 10
# Look and feel
caption always "%{= 2m}%{+b w}Screen: %n | %h %=%t %D %d/%m/%y %c:%s"
hardstatus alwayslastline "%-Lw%{= BW}%50>%n%f* %t%{-}%+Lw%< %=% [%{=b)%{Y}%l%{g}]"
# Left Right meta key mods
# ALT-,. and ALT-<>
bindkey "^[<" eval number !echo $WINDOW-1|bc
bindkey "^[>" eval number !echo $WINDOW+1|bc
bindkey "^[," prev
bindkey "^[." next
select 1
termcapinfo xterm* ti@:te@
Conclusion
While screen is not necessarily the newest tool to run multiple things in different tabs I tend to use it as it is available on most Unix/Linux environments new and old. If it is not available it is almost certainly in the given environment's package manager and easy to install.