difference between execute shell script directly and through pipe - shell

my shell script called mongoLogin.sh as below:
#!/bin/sh
mongo
use demo
show tables
the function of above is logining mongo and show tables of database called demo.
if I execute it directly by:
sh mongoLogin.sh
it works. however if I execute it by this way as below:
cat mongoLogin.sh | sh
compared with execute directly, it will exit automatically, as well as I ctrl+c after execute it directly. It seemed the sh command after pipe will create a new subprocess, and this subprocess finish due to some reason.
Do there exist some method that I can achieve same result by execute script through pipe?
update:
when execute directly it seemed only the first command make effect, because following commands are mongo operations rather than shell commands. And when I execute it by pipe, all commands make effect, but it exit automatically.
the output of executing it through pipe as below:
xxx#xxxMacBook-Pro:~/Downloads$cat mongoLogin.sh | sh
MongoDB shell version v4.0.3
connecting to: mongodb://127.0.0.1:27017
Implicit session: session { "id" : UUID("43c55950-f9e2-49ca-a458-
611f8c71eae4") }
MongoDB server version: 4.0.3
switched to db demo
test
bye

Both variants don't work, because use demo is not a valid shell command.
I have not worked with mongo, but if the command accepts is input from stdin, you can try
mongo <<OGNOM
use demo
show tables
OGNOM
Make sure that the final OGNOM starts in the first column of your line!

Related

Snowsql script not executed when run as here document from bash script

I have a bash script that contains something like this:
snowsql -a <account> -u <user> --authenticator externalbrowser -d <dbname> -o quiet=false <<-EOF
!source foo.sql
EOF
When I run it I don't see any of the output from the commands in foo.sql on the screen. It also appears that none of the SQL in foo.sql is executed (not reflected in state of database). Terminal output is:
* SnowSQL * v1.2.13
Type SQL statements or !help
Goodbye!
If I run foo.sql from an interactive Snowsql session the output from foo.sql is shown and the database is updated accordingly.
Why is foo.sql not executed when called in batch mode from the bash script?
Can you try to run it using -f parameter?
https://docs.snowflake.com/en/user-guide/snowsql-use.html#running-while-connecting-f-connection-parameter
As #Gokhan says this looks to be down to the authentication method. Authentication via a non-browser method makes the problem go away.

Proper syntax for bash script line

Writing a script to retrieve various environment parameters back from a list of servers. My script returns no value when ran but the same command returns the desired value outside of a script.
I have tried using a couple of variations to retrieve the same data. One of the commands fails because of restrictions placed on the accounts I have access to. The second command works but only if executed in an elevated mode.
This fails with access denied (pwdx is restricted)
dzdo pgrep -f /some/path | xargs pwdx
This works outside of a script but returns no value within a script
dzdo /bin/readlink -e /proc/"$(pgrep -f /some/path)"/cwd
When using "bash -x" to execute my scriipt, I see the "readlink" code is blank.
Ideally, I would like to return the PID and path of the process running as the "pgrep" command does. I can work with the path alone as returned by the "readlink" version returns. The end goal is to gather the information from several servers for audit purposes. (version, etc.)
Am I using the wrong syntax for the "readlink" command? I'm fairly new to coding bash scripts so I appreciate any guidance to help understand when to to what if I'm using a command in a script vs command line.
If pwdx is the restricted program, you need to run that with dzdo, not pgrep.
pgrep -f /some/path | dzdo xargs pwdx

bash call is creating a new process.I want to the next command in same process

I am logging into a remote server using SSH client. I have written a script that will execute two commands on the server.But, as the first command executes a bash script that calls "bash" command at the end. This results in execution of only one command not the other.
I cannot edit the first script to comment or remove the bash call.
i have written following script:
abc.sh
#!/bin/bash
command1="sudo -u user_abc -H /abc/xyz/start_shell.sh"
command2=".try1.sh"
$command1 && $command2
Only command 1 is getting executed not the second as the "bash" call is creating a new process the second command is not executing.
Solution 1
Since you can execute start_shell.sh you must have read permissions. Therefore, you could copy the script, modify it such that it doesn't call bash anymore, and execute the modified version.
I think this would be the best solution. If you really really really have to use start_shell.sh as is, then you could try one of the following solutions.
Solution 2
Try closing stdin using <&-. An interactive bash session will exit immediately if there is no stdin.
sudo -u user_abc -H /abc/xyz/start_shell.sh <&-; ./try1.sh
Solution 3
Change the order if both commands are independent.
./try1.sh; sudo -u user_abc -H /abc/xyz/start_shell.sh

sqlplus does not execute the query if it is called by a ssh external connection

I have a script lying into a Unix server which looks like this:
mainScript.sh
#some stuff here
emailScript.sh $PARAM_1 $PARAM_2
#some other stuff here
As you can see, mainScript.sh is calling another script called emailScript.sh.
The emailScript.sh is supposed to perform a query via sqlplus, then parse the results and return them via email if any.
The interesting part of the code in emailScript.sh is this:
DB_SERVER=$1
USERNAME=$2
PASSWORD=$3
EVENT_DATE=$4
LIST_AUTHORIZED_USERS=$5
ENVID=$6
INTERESTED_PARTY=$7
RAW_LIST=$(echo "select distinct M_OS_USER from MX_USER_CONNECTION_DBF where M_EVENT_DATE >= to_date('$EVENT_DATE','DD-MM-YYYY') and M_OS_USER is not null and M_OS_USER not in $LIST_AUTHORIZED_USERS;" | sqlplus -s $USERNAME/$PASSWORD#$DB_SERVER)
As you can see, all I do is just creating the variable RAW_LIST executing a query with sqlplus.
The problem is the following:
If I call the script mainScript.sh via command line (PuTTy / KiTTy), the sqlplus command works fine and returns something.
If I call the script mainScript.sh via an external job (a ssh connection opened on the server via a Jenkins job), the sqlplus returns nothing and takes 0 seconds, meaning it doesn't even try to execute itself.
In order to debug, I've printed all the variables, the query itself in order to check if something wasn't properly set: everything is correctly set.
It really seems that the command sqlplus is not recognized, or something like this.
Would you please have any idea on how I can debug this? Where should I look the issue?
You need to consider few things here. While you are running the script, from which directory location you are executing the script? And while you are executing the script from your external application from which directory location it is executing the script. Better use full path to the script like /path/to/the/script/script.sh or use cd /path/to/the/script/ command to go to the script directory first and execute the script. Also check execute permission for your application. You as an user might have permission to execute the script or sql command but your application does not have that permission. Check the user id for your application and add that into the proper group.

mongo shell script won't let me include "use <database>"

32-bit mongo 2.0.1 on a windows XP machine
//script filename: test.js (one line shell script file to store a person)
db.cTest.save({Name: "Fred", Age:21});
run against database dbTest by entering the following 2 shell commands:
> use dbTest
switched to dbTest
> load("test.js")
So far, so good.
But if I try and include the "use" statement in the script it fails:
//script filename: test.js (including "use" statement)
use dbTest;
db.cTest.save({Name: "Fred", Age:21});
fails with error msg as follows:
> load("test.js")
SyntaxError: missing ; before statement
Mon Dec 19 11:56:31: Error: error loading js file temp.js (shell):1
Adding or removing semicolons to test.js doesn't seem to matter.
So how do you put a "use" directive into a mongo shell script?
In a mongo script you can use the db.getSiblingDB('new_db_name') to get a reference of a new database. So, it it not mandatory to give the database name in the command line. You can use the script.js:
db = db.getSiblingDB('new_db_name');
print(db);
// the rest of your code for database "new_db_name"
and the output of this script is (invoked with mongo script.js):
MongoDB shell version: 2.2.2
connecting to: test
sag
http://www.mongodb.org/display/DOCS/Scripting+the+shell
use dbname
This command does not work in scripted mode. Instead you will need to explicitly define the database in the connection (/dbname in the example above).
Alternately, you can also create a connection within the script:
db2 = connect("server:27017/otherdbname")
Well, it still is unfortunate that "load('file.js')" and "mongo file.js" don't actually use the same script interpreter as the interactive mongo shell. Opening the connection explicitly in the script is potentially a violation of the DRY principle because mongo already knows that information. What does work, though, is piping the file into mongo rather than passing its name on the command line:
mongo <file.js

Resources