Linux shell: why is "open" required in this telnet command - linux

I tried to process telnet output in bash and i stumbled upon this syntax to send telnet commands to a server
( echo open $host $port
sleep 1
echo $cmd1
sleep 1
) | telnet
What i would like to know is why the "open" command is required and why
( echo $host $port
...
) | telnet
results in a "?Invalid command" error.

...because a hostname is not a valid command name? There is a big difference between
$ telnet host port
and
$ telnet
telnet> host port
Where the latter is what your echo command is effectively doing.
The one-liner automatically runs an open command, so it is basically equivalent to this:
$ telnet
telnet> open host port
But I'm not at all sure why you wouldn't just run telnet host port in the first place.

Related

How to capture the output of telnet command in a variable in Shell script

I need to run the telnet command on a remote server using shell script and have to capture the output. When i execute the below, it is not getting completed but instead getting hung. Can someone please advise how to terminate or timeout the telnet command using shell script once it is executed.
telnet_output=`telnet $server $port`
echo "Output is $telnet_output"
I tried writing it to a file as well. But this is also getting hung when executed in remote server.
opfile="telop.log"
telnet_output=`telnet $server $port | tee $opfile`
op=`cat $opfile`
echo "$op"
Try this :
telnet_output="$({ sleep 1; echo $'\e'; } | telnet $server $port 2>&1)"
printf "Output is\n%s\n" "$telnet_output"
echo $'\e' sends an escape character to telnet to terminate it.

Linux script to write data from telnet message into a file while a period

I am connecting to a telnet listener. Telnet server sends some data for every second. I want to read the messages while X seconds and write it into a file (we'll take 6 seconds for the example).
Note: The IP address has been changed to 'IP' for the example. Same for 'Port'.
I already tried some things:
#!/bin/bash
#myScript.sh
telnet IP Port >> myFile.txt
sleep 6
pkill myScript.sh
This solution write in my file but my script never ends.
Here my 2nd proposition:
#!/bin/bash
#myScript.sh
timeout 6 telnet IP Port >> myFile.txt
Here, it's another issue, timeout is respected, the script ends after 6 seconds but in 'myFile.txt', I have
Trying IP...
Connected to IP.
Escape character is '^]'
How can I make this script right?
Note: I must use Telnet.
In your first solution you could try try:
telnet IP Port 2>&1 | tee myFile.txt &
sleep 6
exit
This will send the telnet command to a background process and then exit after 6 seconds.
In your second solution you could try:
timeout 6 telnet IP Port 2>&1 | tee myFile.txt
This sends stderr and stdoutt to myFile.txt
https://www.gnu.org/software/libc/manual/html_node/Standard-Streams.html
Or, as others have suggested, use netcat:
timeout 6 nc -vz IP Port 2>&1 | tee myFile.txt
http://netcat.sourceforge.net/

Shell script to find out if a port is being listened to using netstat?

I have a server where a certain port (9999) is being listened to by a PHP socket server. What happens is that devices can connect to the socket and send messages. The code works fine right now, however, I noticed that the socket would sometimes close or die off, and I need to be able to put it back up online automatically without me having to log in and run it again.
What I'm thinking of is writing a Shell script that would check via netstat if there's a process running on port 9999, and if there's none, the script would trigger the PHP socket server to go online again. This Shell script would then be called by Cron every 1 or 2 minutes to check if the PHP socket is running.
I have bare minimum knowledge about Shell scripting, and so far, this was the only other thing I wrote in Shell:
#!/bin/sh
if pidof "my process name here" >/dev/null; then
echo "Process already running"
else
echo "Process NOT running!"
sh /fasterthancron.sh
fi
I think I should be able to reuse this code to some degree but I'm not sure what to replace the if condition with.
I have the idea that I'm supposed to use netstat -tulpn to figure out what processes are running, but I'm not sure how to filter through that list to find if a specific process is running on port 9999.
If you use netstat -tlpn (or its replacement ss -tpln), you can grep for 9999 and look for processes listening on it under "Local Address".
ss -tpln | awk '{ print $4 }' | grep ':9999'
Alternatively, if you can, use netcat or telnet instead e.g. nc -v localhost 9999.
if echo -n "\cD" | telnet ${host} ${port} 2>/dev/null; then
...
fi
I wrote something similar a while back: docker-wait
This was forked from aanand's docker-wait
You can use famous netstat -tupln with a simple if/else logic to do this.
if [ -z "$(sudo netstat -tupln | grep 9999)" ];
then
echo notinuse;
else
echo inuse;
fi

ssh "port 22: no route to host" error in bash script

I wrote a scipt to execute a couple of ssh remote comands relating to apache storm. When I execute the script it says:
ssh: connect to host XXX.XXX.XXX.XXX port 22: No route to host
ssh: connect to host XXX.XXX.XXX.XXX port 22: No route to host
ssh: connect to host XXX.XXX.XXX.XXX port 22: No route to host
ssh: connect to host XXX.XXX.XXX.XXX port 22: Connection refused
If I execute the commands manually it works out well and I can ping the machine. So that there has to be something wrong with this code:
while [ $i -le $numVM ]
do
if [ $i -eq 1 ];then
ssh -i file root#IP1 './zookeeper-3.4.6/bin/zkServer.sh start'
else
ssh -i file root#IP2 'sed -i '"'"'s/#\ storm.zookeeper.servers.*/storm.zookeeper.servers:/'"'"' /root/apache-storm-0.9.3/conf/storm.yaml'
ssh -i file root#IP2 'sed -i '"'"'0,/^#[[:space:]]*-[[:space:]]*\"server1\".*/s//" - \"'${IParray[1]}'\""/'"'"' /root/apache-storm-0.9.3/conf/storm.yaml'
ssh -i file root#IP2 'sed -i '"'"'s/#\ nimbus.host:.*/"nimbus.host: \"'${IParray[2]}'\""/'"'"' /root/apache-storm-0.9.3/conf/storm.yaml'
ssh -i file root#IP2 './zookeeper-3.4.6/bin/zkCli.sh -server ${IParray[1]} &'
sleep 10
ssh -i file root#IP2 './apache-storm-0.9.3/bin/storm nimbus &' &
sleep 10
ssh -i file root#IP2 './apache-storm-0.9.3/bin/storm ui &' &
sleep 10
ssh -i file root#IP2 './apache-storm-0.9.3/bin/storm supervisor &' &
fi
((i++))
done
I'm starting several processes on 2 virtual machines that are deployed from the same image, so that they are identical in general. The confusing part is, that the first ssh command (zkServer.sh start) is working well but if I the script tries to execute the three "sed"-ssh-commands I get the error message above. But then the last four ssh-commands are working out well again. That does not make any sense to me...
Several things I can think of:
Most sshd daemons won't allow root access. Heck, many versions of Unix/Linux no longer allow root login. If you need root access, you need to use sudo.
The sshd daemon on the remote machine isn't running. Although rare, some sites may never had it setup, or purposefully shut it off as a security issue.
Your ssh commands themselves are incorrect.
Instead of executing the ssh commands in your shell script, modify the shell script just to print out what you're attempting to execute. Then, see if you can execute the command outside of the shell script. This way you can determine whether the problem is the shell script, or the problem is with the ssh command itself.
If your ssh commands don't work outside from the command line, you can then simplify them and see if you can determine what the issue could be. You have ssh -i file root#IP2. Is this suppose to be ssh -i $file root#$IP2? (i.e., you're missing the leading sigil).
$ ssh -i file root#$IP2 ls # Can't get simpler than this...
$ ssh -i file root#IPS # See if you can remotely log on...
$ ssh root#IP2 # Try it without an 'identity file'
$ ssh bob#IP2 # Try it as a user other than 'root'
$ telnet IP2 22 # Is port 22 even open on the remote machine?
If these don't work, then you have some very basic issue with the setup of your remote machine's sshd command.

How can I check to see if an SSH server is listening on a host without actually attempting a login

I am trying to make a bash script which checks to see if a host exists and then attempts to ssh into it if an SSH server is listening on the host. The command would default to telnet if an SSH server is not listening.
What would be the best way to do this? I was thinking about using something like ssh-keyscan to just grab the public key from the ssh server, but ssh-keyscan is not on this jumpserver. Nmap is not on this server either. I'm not able to copy those binaries onto the jump server, nor am I able to compile/build anything on the jumpserver.
What would be the best way to go about checking for an SSH server? I think expect might work, though I would like to avoid using that if possible.
Just check your ability to connect to it, if your bash has the necessary (/dev/tcp) extension; this requires no external commands whatsoever:
if (exec 2>/dev/null 4>/dev/tcp/"$hostname"/22); then
echo "port is open"
else
echo "unable to connect"
fi
Note that your script will need to start with #!/bin/bash, not #!/bin/sh, for this to work.
You can write a shell script and use telnet command to find remote port status
[root#box ~]# telnet remote.example.com 22
Trying 192.168.100.1...
Connected to remote.example.com.
Escape character is '^]'.
SSH-2.0-OpenSSH_5.3
Sample script:
TELNET=`echo "quit" | telnet $SERVER $PORT | grep "Escape character is"`
if [ "$?" -ne 0 ]; then
echo "Connection to $SERVER on port $PORT failed"
exit 1
else
echo "Connection to $SERVER on port $PORT succeeded"
exit 0
fi
I love oneliners :)
if nc "server" "port" </dev/null >/dev/null 2>&1;then echo yeah;else echo no;fi
works on my router and on my rpi

Resources