Can I run a script that uses 2 different command lines? - linux

Sorry if the title is vague, I am fairly new to Linux and I don't really know how else to put it. I am creating a script and when I run it, I got it to run Sage but after it does so, the next command isn't executed. I presume this is because the first couple were in the standard Terminal (bash?) and everything after ./sage isn't -- here's the script:
#!/bin/bash
cd /home/alex/Desktop/sage-7.6
./sage
#I also tried wait ${!} here but it didn't work
notebook("/home/alex/Desktop/sage-7.6/projects/zero forcing.sagenb")
How might I enter the last command in Sage after it opens (assuming it's possible)? Thanks!
Edit: Here's a picture of my problem. Sage runs but I can't get it to execute the notebook() command after it opens.

You need to run notebook() as sage code using the -c option mentioned [ here ]. Try the below code.
#!/bin/bash
/home/alex/Desktop/sage-7.6/sage # You can run the interactive shell directly
# At this point you have completely exited the sage interactive shell
# Presumably you want to run the below 'notebook()' after every interactive shell
# In that case do
/home/alex/Desktop/sage-7.6/sage -c 'notebook("/home/alex/Desktop/sage-7.6/projects/zero forcing.sagenb")'

I think what you really want is just to have one command that launches a notebook with a given name.
It turns out that in many Linux/Unix applications, there is automatic help at the command line. Try
/home/alex/.../sage -n -h
to get some help on the notebook. In particular,
sage -n -h --notebook=sagenb
gives a very, very long list of options, the first of which shows that
sage --notebook=sagenb directory=tp
will give you a new sage notebook server in the directory tp.sagenb.
All this said, I should also point out that the sagenb (sadly) is slowly becoming a legacy project in favor of the Jupyter notebook. In Sage 8.0 a conversion from sagenb to Jupyter will become the default, and even now you can just do
sage --notebook=jupyter --notebook-dir=/home/foo/bar
for that to start up.

Related

How to execute a shell program taking inputs with python?

First of all, I'm using Ubuntu 20.04 and Python 3.8.
I would like to run a program that takes command line inputs. I managed to start the program from python with the os.system() command, but after starting the program it is impossible to send the inputs. The program in question is a product interface application that uses the CubeSat Space Protocol (CSP) as a language. However, the inputs used are encoded in a .c file with their corresponding .h header.
In the shell, it looks like this:
starting the program
In python, it looks like this:
import os
os.chdir('/home/augustin/workspaceGS/gs-sw-nanosoft-product-interface-application-2.5.1')
os.system('./waf')
os.system('./build/csp-client -k/dev/ttyUSB1')
os.system('cmp ident') #cmp ident is typically the kind of command that does not work on python
The output is the same as in the shell but without the "cmp ident output", that is to say it's impossible for me to use the csp-client#
As you can probably see, I'm a real beginner trying to be as clear and precise as possible. I can of course try to give more information if needed. Thanks for your help !
It sounds like the pexpect module might be what you're looking for rather than using os.system it's designed for controlling other applications and interacting with them like a human is using them. The documentation for it is available here. But what you want will probably look something like this:
import pexpect
p = pexpect.spawnu("/home/augustin/workspaceGS/gs-sw-nanosoft-product-interface-application-2.5.1/build/csp-client -k/dev/ttyUSB1")
p.expect("csp-client")
p.sendline("cmp indent")
print(p.read())
p.close()
I'll try and give you some hints to get you started - though bear in mind I do not know any of your tools, i.e. waf or csp-client, but hopefully that will not matter.
I'll number my points so you can refer to the steps easily.
Point 1
If waf is a build system, I wouldn't keep running that every time you want to run your csp-client. Just use waf to rebuild when you have changed your code - that should save time.
Point 2
When you change directory to /home/augustin/workspaceGS/gs-sw-nanosoft-product-interface-application-2.5.1 and then run ./build/csp-client you are effectively running:
/home/augustin/workspaceGS/gs-sw-nanosoft-product-interface-application-2.5.1/build/csp-client -k/dev/ttyUSB1
But that is rather annoying, so I would make a symbolic link to that that from /usr/local/bin so that you can run it just with:
csp-client -k/dev/ttyUSB1
So, I would make that symlink with:
ln -s /home/augustin/workspaceGS/gs-sw-nanosoft-product-interface-application-2.5.1/build/csp-client /usr/local/bin/csp-client
You MAY need to put sudo at the start of that command. Once you have that, you should be able to just run:
csp-client -k/dev/ttyUSB1
Point 3
Your Python code doesn't work because every os.system() starts a completely new shell, unrelated to the previous line or shell. And the shell that it starts then exits before your next os.system() command.
As a result, the cmp ident command never goes to the csp-client. You really need to send the cmp ident command on the stdin or "standard input" of csp-client. You can do that in Python, it is described here, but it's not all that easy for a beginner.
Instead of that, if you just have aa few limited commands you need to send, such as "take a picture", I would make and test complete bash scripts in the Terminal, till I got them right and then just call those from Python. So, I would make a bash script in your HOME directory called, say csp-snap and put something like this in it:
#/bin/bash
# Extend PATH so we can find "/usr/local/bin/csp-client"
PATH=$PATH:/usr/local/bin
{
# Tell client to take picture
echo "nanoncam snap"
# Exit csp-client
echo exit
} | csp-client -k/dev/ttyUSB1
Now make that executable (only necessary once) with:
chmod +x $HOME/csp-snap
And then you can test it with:
$HOME/csp-snap
If that works, you can copy the script to /usr/local/bin with:
cp $HOME/csp-snap /usr/local/bin
You may need sudo at the start again.
Then you should be able to take photos from anywhere just with:
csp-snap
Then your Python code becomes easy:
os.system('/usr/local/bin/csp-snap')

at job scheduler doesn't work on my Ubuntu

I know there are many linux experts here, I wish to get little help with at command in Ubuntu.
I have been troubled by at command in ubuntu (18.04 and 20.04) for quite a while, but I don't know where I made a mistake. I've tried at on three of my Ubuntu systems and it doesn't work on any of them. at is very handle and nice job scheduler, I really want to get it to work so that I do not have to manually launch programs in the late night on a shared Ubuntu server. I read many tutorials on at command, here is a very good one.
at now + 1 minutes -f ~/myscript.sh, it looks really great and can save me lots of energy. Unfortunately, when myscript.sh is extremely simple,then at now + 1 minutes -f ~/myscript.sh can run smoothly and I get what I expected. Here is everything I have in myscript.sh:
echo $(date) > ~/Desktop/time.txt
On top of that, it never worked for me. For example when I change myscript.sh to
echo $(date) > ~/Desktop/time.txt
pycharm.sh
Basically what myscript.sh does it is noting down the time and to open Pycharm IDE. I can run sh myscript.sh without at , it wroks very well. However, when I run at at now + 1 minutes -f ~/myscript.sh, the time is noted down but Pycharm was not never opened (I can see the process in htop if Pycharm is open). Also at now + 1 minutes -f ~/script.sh does not work with any of my other shell scripts.
Could you please help me understand where I have done wrong and how to make it work. Thank you very much.
PyCharm and other GUI programs need a lot of information from your environment. The atd daemon which runs jobs for at does not have access to this environment. You will need to specify it directly.
I recommend running printenv redirected to a file in an at job. Then compare that to printenv running from a terminal in your GUI session. Find the differences and see if you can set them up the same way at the beginning of your at script.

Double Click Python File to Run Program

I’ve searched and read many posts but none actually describe what I would like to do. Using Debian Stretch, I’ve been trying to create a Python 3 program that runs what would otherwise be a typed command with switches at the gnome terminal. This is how it should run:
Double click the created *.py file that contains the code for the program.
The gnome terminal appears and the command/switches appear after the $ and then the program runs. Some of the switches have zeros (0) which seems to present an issue. Example command:
$ ./binary.bin -j 0 -n 1300
Anyone have any ideas on how I should start to write this program? Any suggestions would be helpful. Thank you.

Want to understand what's going on with linux command

I am installing a virtualenv and want to understand what's going on.
$ curl -O https://raw.github.com/pypa/virtualenv/master/virtualenv.py
- I understand curl fine
$ python virtualenv.py my_new_env
- Understand this, too
$ . my_new_env/bin/activate
- Here's where I get lost. What is the period doing here?
(my_new_env)$ pip install ...
- What does it mean to have the parentheses here? Does this use tell me I'm in a folder?
The dot is a command that means to read and execute the contents of the given script in the current shell (normally running a shell script runs it in a new process.) Evaluating the script in the current shell can change the environment variables of the current shell, so the behavior of subsequent commands is affected.
I don't know for sure about the parentheses, but I don't think they're meant to be syntax you type. As they come before the '$' prompt, perhaps that's literally what you'll get as your new prompt after running the activate script, to show you that your environment has been changed?
The dot is essentially an "execute" command — execute the commands in my_new_env/bin/activate as though they were typed into your prompt, essentially.
The parentheses shown in the prompt (at least in the tutorial instructions) then indicate that you're typing commands in your new virtual environment, and not in your original (real) environment.

Screen and Cygwin: no tab completion?

I'm having some problems working with my development environment. Specifically, after I invoke the screen utility from within Cygwin I lose the ability to do tab completion. Before I invoke screen however tab completion works just fine.
I messed around with setting different values for the TERM env variable (VT100, xterm etc) but without success. It must be something trivial but I have no idea anymore. Does StackOverflow have any suggestions for me?
when you issue 'screen' from inside cygwin it might put you in another shell like /bin/sh instead of /bin/bash (and bash is where you're getting the tab completion from).
To fix the problem you could edit your .screenrc file (found in your home directory) and add in this line:
shell bash
Then try running screen again and you should see tab completion work within this new window.
The problem is that bash needs to be run as a login shell in order to have tab completion in the default cygwin setup. If you run bash in a cygwin bash you won’t have tab completion either. To set screen to run bash in login mode, add this line to your ~/.screenrc file:
shell -bash
I had a similar problem with git autocompletion not working when using screen on a linux machine, but wasn't due to a different shell. I fixed it using this question: Git autocomplete in screen on mac os and doing the following:
Get the git autocompletion script
curl https://raw.github.com/git/git/master/contrib/completion/git-completion.bash -OL
why would you want that hanging around?
mv git-completion.bash .git-completion.bash
add this line to your ./bashrc
source ~/.git-completion.bash
Then in your terminal
source ~/.bashrc
That worked for me.
(I imagine after three years you've probably solved your problem, but I hope this helps someone else)

Resources