How do I parse a cmd line variable into 2-parts? - bash

This is my first post here. Absolute newbie here - plz be gentle :)
(%2=mydomain.ddns.net and mydomain.com into $SUB_DOMAIN . DOMAIN
./test.sh <name> <dydomain.com>
./test.sh <name> <mysub.domain.com>
would both produce the same result.
var1=<name>
var2=<subdomain> # if present
var3=<domain>
url=<$var1.$var2.$var3>
Regardless of the existance of a subdomain or not, I need $url to be complete with
<name>.(subdomain).<domain>
UPDATE: Thanks everyone for prompt responses, I am currently reading through the answers provided and testing. This script will be run remotely on a VPS HOST so I would need the script to fail and exit if there are unbound variables. I could not prompt for user input.
Thank you.

boo="mydomain.ddns.net"
using '-d .' with 'cut' , given string divided in multiple fields with '.' as delimiter.
'-f1' with cut displays only field 1 and '-f2,3' displays 2 and 3 fields.
echo $boo | cut -f1 -d.
mydomain
echo $boo | cut -f2,3 -d.
ddns.net
var1=$(echo $boo | cut -f1 -d.)
var2=$(echo $boo | cut -f2,3 -d.)
echo $var1
mydomain
echo $var2
ddns.net

Related

Retreive Domain name from a PHP variable

I have a PHP config file which I retrieved from SSH.
Here is the sample config file in PHP :
<?php
$url_root='https://google.fr';
$document_root='/usr/share/nginx/html';
The command I use to retrieve the url :
grep -oE '\$url_root=.*;' conf.php | tail -1 | sed 's/$url_root=//g;s/;//g'
Output:
'https://google.fr'
But I expect to retrieve only google.fr
Then I need to implement this command line into ssh like :
domain=$(ssh -oStrictHostKeyChecking=no root#127.0.0.1 '
COMMAND HERE;
')
In order to accomodate for unpredictable data (aka you can find complete urls including other routes / files and not only domain names) I would go for:
your_str='https://google.fr/somedir/someotherdir/index.html'
echo $your_str | cut -d'/' -f3
Output:
google.fr
In your ssh command:
'grep -oE '\''\$url_root=.*;'\'' conf.php | tail -1 | sed '\''s/$url_root=//g;s/;//g'\'' | cut -d'\''/'\'' -f3'
Try this:
DOMAIN_NAME=$(grep -oE '\$url_root=.*;' conf.php | tail -1| sed "s/\$url_root='//g;s/^[a-z]*:\/\///g;s/';//")
echo "Domain name is: $DOMAIN_NAME";
# ssh user#$DOMAIN_NAME etc...
The portion of code s/^[a-z]*:\/\///g; looks for one or more occurrences of a-z followed by :// and removes it if it exists.

What's wrong with this bash script using cut and sed (cut: command not found)?

I'm getting server and path from an NFS location in bash as follows:
#!/bin/bash
ST="/net/10.111.111.111/path/to/some/dir"
echo $ST
SERVER=$(echo $ST | cut -d'/' -f3)
echo $SERVER
PATH=$(echo $ST | cut -d'/' -f4-)
echo $PATH
PATH=$(echo $ST | cut -d'/' -f4-)
echo $PATH
The same 2 lines are repeated above on purpose. The output is:
/net/10.111.111.111/path/to/some/dir
10.111.111.111
path/to/some/dir
./nn.sh: line 9: cut: command not found
I'm getting what I want but I don't understand why the second call to PATH= produces the above error. What am I missing?
PATH is a system variable which the bash shell uses to find where
your binaries(eg cut) are.
So, till :
PATH=$(echo $ST | cut -d'/' -f4-)
things work as expected. But after the command substitution ie $(...), PATH points to a non-standard directory where bash could not find the standard binaries.
So the subsequent command :
PATH=$(echo $ST | cut -d'/' -f4-)
gave you the error :
./nn.sh: line 9: cut: command not found
Moral
Never use uppercase variables for your scripts as they are reserved for the system.

How to compare a file to a list in linux with one line code?

Hey so got another predicament that I am stuck in. I wanted to see approximately how many Indian people are using the stampede computer. So I set up an indian txt file in vim that has about 50 of the most common surnames in india and I want to compare those names in the file to the user name list.
So far this is the code I have
getent passwd | cut -f 5 -d: | cut -f -d' '
getent passwd gets the userid list which is going to look like this
tg827313:x:827313:8144474:Brandon Williams
the cut functions will get just the last name so the output of the example will be
Williams
Now can use the grep function to compare files but how do I use it to compare the getent passwd list with the file?
To count how many of the last names of computer users appear in the file namefile, use:
getent passwd | cut -f 5 -d: | cut -f -d' ' | grep -wFf namefile | wc -l
How it works
getent passwd | cut -f 5 -d: | cut -f -d' '
This is your code which I will assume works as intended for you.
grep -wFf namefile
This selects names that match a line in namefile. The -F option tells grep not to use regular expressions for the names. The names are assumed to be fixed strings. The option -f tells grep to read the strings from file. -w tells grep to match whole words only.
wc -l
This returns a count of the lines in the output.

How to handle variables that contain ";"?

I have a configuration file that contains lines like "hallo;welt;" and i want to do a grep on this file.
Whenever i try something like grep "$1;$2" my.config or echo "$1;$2 of even line="$1;$2" my script fails with something like:
: command not found95: line 155: =hallo...
How can i tell bash to ignore ; while evaluating "..." blocks?
EDIT: an example of my code.
# find entry
$line=$(grep "$1;$2;" $PERMISSIONSFILE)
# splitt line
reads=$(echo $line | cut -d';' -f3)
writes=$(echo $line | cut -d';' -f4)
admins=$(echo $line | cut -d';' -f5)
# do some stuff on the permissions
# replace old line with new line
nline="$1;$2;$reads;$writes;$admins"
sed -i "s/$line/$nline/g" $TEMPPERM
my script should be called like this: sh script "table" "a.b.*.>"
EDIT: another, simpler example
$test=$(grep "$1;$2;" temp.authorization.config)
the temp file:
table;pattern;read;write;stuff
the call sh test.sh table pattern results in: : command not foundtable;pattern;read;write;stuff
Don't use $ on the left side of an assignment in bash -- if you do it'll substitute the current value of the variable rather than assigning to it. That is, use:
test=$(grep "$1;$2;" temp.authorization.config)
instead of:
$test=$(grep "$1;$2;" temp.authorization.config)
Edit: also, variable expansions should be in double-quotes unless there's a good reason otherwise. For example, use:
reads=$(echo "$line" | cut -d';' -f3)
instead of:
reads=$(echo $line | cut -d';' -f3)
This doesn't matter for semicolons, but does matter for spaces, wildcards, and a few other things.
A ; inside quotes has no meaning at all for bash. However, if $1 contains a doublequote itself, then you'll end up with
grep "something";$2"
which'll be parsed by bash as two separate commands:
grep "something" ; other"
^---command 1----^ ^----command 2---^
Show please show exactly what your script is doing around the spot the error is occurring, and what data you're feeding into it.
Counter-example:
$ cat file.txt
hello;welt;
hello;world;
hell;welt;
$ cat xx.sh
grep "$1;$2" file.txt
$ bash -x xx.sh hello welt
+ grep 'hello;welt' file.txt
hello;welt;
$
You have not yet classified your problem accurately.
If you try to assign the result of grep to a variable (like I do) your example breaks.
Please show what you mean. Using the same data file as before and doing an assignment, this is the output I get:
$ cat xx.sh
grep "$1;$2" file.txt
output=$(grep "$1;$2" file.txt)
echo "$output"
$ bash -x xx.sh hello welt
+ grep 'hello;welt' file.txt
hello;welt;
++ grep 'hello;welt' file.txt
+ output='hello;welt;'
+ echo 'hello;welt;'
hello;welt;
$
Seems to work for me. It also demonstrates why the question needs an explicit, complete, executable, minimal example so that we can see what the questioner is doing that is different from what people answering the question think is happening.
I see you've provided some sample code:
# find entry
$line=$(grep "$1;$2;" $PERMISSIONSFILE)
# splitt line
reads=$(echo $line | cut -d';' -f3)
writes=$(echo $line | cut -d';' -f4)
admins=$(echo $line | cut -d';' -f5)
The line $line=$(grep ...) is wrong. You should omit the $ before line. Although it is syntactically correct, it means 'assign to the variable whose name is stored in $line the result of the grep command'. That is unlikely to be what you had in mind. It is, occasionally, useful. However, those occasions are few and far between, and only for people who know what they're doing and who can document accurately what they're doing.
For safety if nothing else, I would also enclose the $line values in double quotes in the echo lines. It may not strictly be necessary, but it is simple protective programming.
The changes lead to:
# find entry
line=$(grep "$1;$2;" $PERMISSIONSFILE)
# split line
reads=$( echo "$line" | cut -d';' -f3)
writes=$(echo "$line" | cut -d';' -f4)
admins=$(echo "$line" | cut -d';' -f5)
The rest of your script was fine.
It seems like you are trying to read a semicolon-delimited file, identify a line starting with 'table;pattern;' where table is a string you specify and pettern is a regular expression grep will understand. Once the line is identified you wish to replaced the 3rd, 4th and 5th fields with different data and write the updated line back to the file.
Does this sound correct?
If so, try this code
#!/bin/bash
in_table="$1"
in_pattern="$2"
file="$3"
while IFS=';' read -r -d$'\n' tuple pattern reads writes admins ; do
line=$(cut -d: -f1<<<"$tuple")
table=$(cut -d: -f2<<<"$tuple")
# do some stuff with the variables
# e.g., update the values
reads=1
writes=2
admins=12345
# replace the old line with the new line
sed -i'' -n $line'{i\
'"$table;$pattern;$reads;$writes;$admins"'
;d;}' "$file"
done < <(grep -n '^'"${in_table}"';'"${in_pattern}"';' "${file}")
I chose to update by line number here to avoid problems of unknown characters in the left hand of the substitution.

Given a string I want to retrieve sections of the string based on delimiters using a cut command?

I have the following string:
MrRelatedTests/ubsr064412_01.tst,GREEN,verified skipped,lwks08,31s,1
I want to retrieve it into the following three subsections:
MrRelatedTests/ubsr064412_01.tst
GREEN,verified skipped
lwks08,31s,1
I have to use this stuff in a shell script. Thus if
$string=MrRelatedTests/ubsr064412_01.tst,GREEN,verified skipped,lwks08,31s,1 I should be able to retrieve the following
$a=MrRelatedTests/ubsr064412_01.tst
$b=GREEN,verified skipped
$c=lwks08,31s,1
Thanks for the help in advance.
a=$(echo ${STR} | cut -d, -f1)
b=$(echo ${STR} | cut -d, -f2-3)
c=$(echo ${STR} | cut -d, -f4-6)

Resources