This question already has answers here:
Why should there be spaces around '[' and ']' in Bash?
(5 answers)
Closed 5 years ago.
this should be a simple answer but I haven't been able to find a simple solution. I'm trying to create a bash script that runs the reindent.py tool scrip but I want to be able to get user input on whether or not he wants to write the file back to disk. Basically I want to type reindent_python -n FILE_PATH or reindent_python FILE_PATH. So far I got the following:
function reindent_python () {
if ["$1" = "n"]; then
./reindent.py -n $2
else
./reindent.py $2
fi
}
Since this is my first shell script I'm not sure how to get whether or not the first parameter is -n and is $1 the n parameter and $2 the FILE_PATH? How would I got about creating this script?
Thank you!
First off, what you display is a function, not a script. Your function could be as simple as:
function reindent_python () {
./reindent.py "$#"
}
given the fact that your Python script appear to take the same arguments as your function. You can simply pass them all to the Python script with the above construct.
As #CharlesDuffy mentions in the comment, the function keyword is not necessary:
reindent_python () {
./reindent.py "$#"
}
That aside, the if part should be
[ "$1" = "-n" ];
with a space around the brackets and a dash before the n.
You're very close, just add the -. the string comparison is simplistic and does no other processing, it doesn't remove the hyphen for you.
function reindent_python () {
if [ "$1" = "-n" ]; then
./reindent.py -n "$2"
else
./reindent.py "$2"
fi
}
or remove it when calling the function:
reindent_python n FILE_PATH
Related
This question already has answers here:
What's the difference between "here string" and echo + pipe
(1 answer)
Redirector "<<<" in Ubuntu?
(3 answers)
Closed 3 months ago.
Hello guys i wanna write a Shell script that runs Python code saved in variable called $code.
So i save the script in variable $code with this command:
$ export CODE='print("Hello world")'
To resolve the problem
I write the following script in a file called run:
#!/bin/bash
echo "$CODE" > main.py
python3 main.py
To running the shell script i use:
./run
and its work but
I found another answer which I don't understand:
python3 <<< $CODE
so what do we mean by using <<<?
In a lot of shells <<< denotes a here string and is a way to pass standard input to commands. <<< is used for strings, e.g.
$ python3 <<< 'print("hi there")'
hi there
It passes the word on the right to the standard input of the command on the left.
whereas << denotes a here document, e.g.
command <<MultiLineDoc
Standard Input
That
Streches many
Lines and preserves
indentation and
linebreaks
which is useful for passing many arguments to a command,
e.g. passing text to a program and preserving its indentation.
The beginning and ending _MultiLineDoc_ delimiter can be named any way wanted,
it can be considered the name of the document.
Important is that it repeats identically at
both beginning and end and nowhere else in the
document, everything between that delimiter is passed.
MultiLineDoc
< is used for passing the contents of a file, e.g. command < filename.txt
As for your example with <<< :
You could do the same with | but that's only OK if all your variables are defined in what you are passing. If you do have other variables that you have defined in your environment and which you wish to cross reference you would use a here-string as in your example, that lets you reference other variables within the content you are passing.
Please see: https://en.wikipedia.org/wiki/Here_document
https://linuxhint.com/bash-heredoc-tutorial/
In Bash, zsh (and some other shells) <<< is the here string operator. The code you’ve posted is roughly equivalent to
echo "$PYCODE" | python3
Normally I work with Python but I have a project in Perl. So: What is the process for directing the results of an snmpwalk to a string? I would like to search the string to see if it contains a smaller string.
Here is what I have so far:
foreach (#list){
chomp($_);
system("snmpwalk -v 2c -c community-string $_ oid-hidden");
if (index($string, $substring) != -1) {
print "'$string' contains '$substring'\n";
}
}
system function doesn't return the function output, use qx// or backticks, so your snmpwalk call line will look like this:
my $output = qx/snmpwalk -v 2c -c community-string $_ oid-hidden/;
And then you do with the output variable what you need, for more info I'd refer you to http://perldoc.perl.org/perlop.html#Quote-Like-Operators
However in more general terms I'd follow the advice in #ThisSuitIsBlackNot's comment...
Hello all I was wondering what the option is for the python based version of youtube-dl for this argument in terminal --restrict-filenames? What does the options in python does the tuple need to have added to it?
Thanks in advance, Ondeckshooting
Per the documentation, that option does not require an argument. So a command
such as this will suffice:
youtube-dl --restrict-filenames 73VCKpU9ZnA
Here is the option detail:
Restrict filenames to only ASCII characters, and avoid "&" and spaces in
filenames
As far as what ASCII is, this script will reveal:
#!/usr/bin/awk -f
BEGIN {
while (z++ < 0x7e) {
$0 = sprintf("%c", z)
if (/[[:graph:]]/) printf $0
}
}
Result
!"#$%&'()*+,-./0123456789:;<=>?#ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~
This question already has answers here:
How to use python variable in os.system? [duplicate]
(2 answers)
Closed 1 year ago.
I am new to python and I need to use a variable in the os.system command, here's my code so far
import os , sys
s = raw_input('test>')
then i want to use the varable s in an os.system command so I was thinking something like os.system("shutdown -s -t 10 -c" 's')
I don't want answers for that specific command I just want to know in general but if you are going to use an example use shutdown
then i want to use the varable s in an os.system
Use string.format function.
os.system("shutdown -s -t 10 -c {}".format(s))
You can use os.system to execute the particular command, in which case you can join the two strings either by using the + operator, string formatting (.format()), string substitution or some other method.
However, consider the case when the user enters the command 5; rm -rf / or some other malicious command. Instead of using os.system you might want to take a look at subprocess
If you use subprocess you might find the following example handy:
import subprocess
s = raw_input('test>')
subprocess.call(["shutdown", "-s", "-t", "10", "-c", s])
Use subprocess.check_call, pass a list of args and you can add the variable wherever you like:
from subprocess import check_call
check_call(["shutdown", some_var ,"-s", "-t" "10", "-c"])
os.system takes a string as the argument, so you can use anything that modifies a string. For example, string formatting:
os.system('shutdown -s -t 10 -c {0}'.format(s))
Passing place-holder "%s string alongside os.system" should work.
os.system() will execute the command in shell.
import os
var = raw_input('test>') # changed "s" variable to "var" to keep clean
os.system("shutdown -%s -t 10 -c", %(var)) # "var" will be passed to %s place holder
os.system("shutdown -s -t 10 -c" + s)
The plus sign joins two strings
No quotes are used around s. That way you get the value the user entered and not just a literal "s".
)I have confirmed my Linux command works in the terminal, however when I try to call it from python it breaks.
The command is a bit long and has lots of single quotes, so I wrapped it around three double quotes (""") so python can interpret as a raw string (or so I thought). However, when I run it I am getting
sh: -c: line 0: unexpected EOF while looking for matching `''
sh: -c: line 1: syntax error: unexpected end of file
but I have double and tripple checked my single and double quotes and I have no idea where to go from here.
See the test script below
import os
os.system("""awk -F ' *[[:alnum:]_]*: *' 'BEGIN {h="insert_job;box_name;command;owner;permission;condition;description;std_out_file;std_err_file;alarm_if_fail"; print h; n=split(h,F,/;/)} function pr() {if(F[1] in A) {for(i=1;i<=n;i++)printf "%s%s",A[F[i]],(i<n)?";":RS}} /insert_job/ {pr(); delete A} {for(i in F){if($0~"^"F[i])A[F[i]]=$2}} END {pr()}' ./output/JILS/B7443_dev_jil_20140306104313.csv > /trvapps/autosys/admin/EPS/output/JILS/testout.txt""")
FYI I am using Python 2.4.3, hence why I am using os instead of subprocess.
For your own sanity, try using pipes.quote (or something similar if that doesn't exist in 2.4), ' '.join(words) and '\n'.join(lines) to be able to build up the command rather than using a single complex string if you have to put it in Python. A better solution would be to call a script like #kojiro suggested.
It looks like you are doing some simple CSV munging. How about checking SO for tips on doing that in Python?
In any case, 400+ characters of awk on a single line is enough to make anyone squirm, and doing it in Python, which already has excellent string handling features, is just passing the pain to the next developer. Which will be very angry.
Cramming the awk script into one huge line is awful, and makes it nearly impossible to read and maintain. Don't do that -- if you really must use awk (a dubious claim), write it out on multiple lines, with proper indentation, like you would any other script.
To fix the bug with sh -c interpreting things wrong, use the subprocess module (passing an argument array and not setting shell=True) instead of os.system().
import subprocess
awk_script = r'''
*[[:alnum:]_]*: *
BEGIN {
h="insert_job;box_name;command;owner;permission;condition;description;std_out_file;std_err_file;alarm_if_fail";
print h;
n=split(h,F,/;/)
}
function pr() {
if(F[1] in A) {
for(i=1;i<=n;i++)
printf "%s%s", A[F[i]], (i<n) ? ";" : RS
}
}
/insert_job/ {
pr();
delete A;
}
{
for(i in F) {
if($0~"^"F[i])
A[F[i]]=$2
}
}
END {pr()}
'''
exit_status = subprocess.call(['awk', '-F', awk_script],
stdin=open('./output/JILS/B7443_dev_jil_20140306104313.csv', 'r'),
stdout=open('/trvapps/autosys/admin/EPS/output/JILS/testout.txt', 'w'))
if exit_status != 0:
raise RuntimeException('awk failed')