LinuxQuestions.org
Welcome to the most active Linux Forum on the web.
Go Back   LinuxQuestions.org > Forums > Linux Forums > Linux - Newbie
User Name
Password
Linux - Newbie This Linux forum is for members that are new to Linux.
Just starting out and have a question? If it is not in the man pages or the how-to's this is the place!

Notices


Reply
  Search this Thread
Old 02-19-2010, 08:22 AM   #1
Softsmid
LQ Newbie
 
Registered: Feb 2010
Location: Netherlands
Distribution: Ubuntu, OpenSUSE
Posts: 8

Rep: Reputation: 0
bash interactive installation script


Hi, for an exercise I need to write a script that will ask the user about each package in a (local) repository and install it or not according to the user's input.

I am fairly new to scripting, so I did not get very far. Here is what I came up with. I really appreciate your help.


Code:
#!/bin/bash 
#Checks if you are root or not 
if test "`id -u`" -ne 0
then
echo "You need to run this script as root!"
exit
fi #here needs to start a loop that lists all the packages like dpkg -l does #one for one and asks for user input. I thought of a variable that #would then be echoed. How do I do that? appl=application echo "Do you wish to install $appl ?" select yn in "Yes" "No"; do
case $yn in
Yes ) apt-get install $appl; break;;
No ) exit;;
esac
done

Last edited by Softsmid; 02-19-2010 at 08:30 AM.
 
Old 02-19-2010, 08:28 AM   #2
i92guboj
Gentoo support team
 
Registered: May 2008
Location: Lucena, Córdoba (Spain)
Distribution: Gentoo
Posts: 4,072

Rep: Reputation: 384Reputation: 384Reputation: 384Reputation: 384
Code:
#!/bin/bash 
#Checks if you are root or not 
if test "`id -u`" -ne 0[INDENT] then
This can be done with a simpler check:

Code:
if [[ "$UID" -ne "0" ]]; then
Quote:
#here needs to start a loop that lists all the packages like dpkg -l does one for one and asks for user input. I thought #of a variable that would then be echoed. How do I do that?
You probably want to research about "arrays" in bash if you truly want to go that way. However you could as well do something like:

Code:
<command to list pkgs> | while read package
do
  <do something with> "$package"
done
That way you don't need to store everything into an array.
 
Old 02-19-2010, 09:49 AM   #3
Softsmid
LQ Newbie
 
Registered: Feb 2010
Location: Netherlands
Distribution: Ubuntu, OpenSUSE
Posts: 8

Original Poster
Rep: Reputation: 0
I found another way but not fully satisfactory yet. The script does not stop yet to ask after every file, any suggestions?


Code:
#!/bin/bash 
#Checks if you are root or not 
if test "`id -u`" -ne 0
	then 
	echo "You need to run this script as root!" 
	exit 
fi
#here needs to start a loop that lists all the packages like dpkg -l does one for one and
#asks for user input. I got as far as the code below. But the script does not stop yet to ask
#after every file, any suggestions?
for pkg in `dpkg -l`
do
	echo Found package: $pkg
done
		echo "Do you wish to install $pkg ?"
		select yn in "Yes" "No"
		do
		    case $yn in
		        Yes ) apt-get -d install $apl; break;;
		        No ) exit;;
		    esac
		done
	# continue...
 
Old 02-19-2010, 09:53 AM   #4
Softsmid
LQ Newbie
 
Registered: Feb 2010
Location: Netherlands
Distribution: Ubuntu, OpenSUSE
Posts: 8

Original Poster
Rep: Reputation: 0
Quote:
You probably want to research about "arrays" in bash if you truly want to go that way. However you could as well do something like:

Code:
<command to list pkgs> | while read package
do
  <do something with> "$package"
done
That way you don't need to store everything into an array.
I have tried it with your code but did not get further either. That is because I don't understand pipelines yet and arrays neither.
 
Old 02-19-2010, 10:08 AM   #5
i92guboj
Gentoo support team
 
Registered: May 2008
Location: Lucena, Córdoba (Spain)
Distribution: Gentoo
Posts: 4,072

Rep: Reputation: 384Reputation: 384Reputation: 384Reputation: 384
A pipe connects the standard output from a process to the standard input (which usually is attached to the console/keyboard) of another process. In this case, it connects the output of dpkg (or whatever else) to the input of the while construct. On each iteration of the while sentence the read command will get a string and store it as $package, you can do whatever you need to do with that variable inside the while loop, and so on for each value of $package (all the values listed by your dpkg sentence).

Arrays are truly not necessary since you are not needing to save the data to do something else after this. They would be a waste of resources and time in this case. For me, anyway.

If you can't use pipes because this is homework then that's a different issue though.
 
Old 02-19-2010, 10:10 AM   #6
i92guboj
Gentoo support team
 
Registered: May 2008
Location: Lucena, Córdoba (Spain)
Distribution: Gentoo
Posts: 4,072

Rep: Reputation: 384Reputation: 384Reputation: 384Reputation: 384
Code:
for pkg in `dpkg -l`
do
	echo Found package: $pkg
done
This ensures that your script will run "echo" for all the found packages.

Code:
		echo "Do you wish to install $pkg ?"
		select yn in "Yes" "No"
		do
		    case $yn in
		        Yes ) apt-get -d install $apl; break;;
		        No ) exit;;
		    esac
		done
But this is outside that loop...
 
Old 02-19-2010, 11:09 AM   #7
Softsmid
LQ Newbie
 
Registered: Feb 2010
Location: Netherlands
Distribution: Ubuntu, OpenSUSE
Posts: 8

Original Poster
Rep: Reputation: 0
Quote:
Originally Posted by i92guboj View Post
Code:
for pkg in `dpkg -l`
do
    echo Found package: $pkg
done
This ensures that your script will run "echo" for all the found packages.

Code:
        echo "Do you wish to install $pkg ?"
        select yn in "Yes" "No"
        do
            case $yn in
                Yes ) apt-get -d install $pkg; break;;
                No ) exit;;
            esac
        done
But this is outside that loop...
Yes, I know. If I put it inside the loop I do not get a list of packages but this output from running the script:

Code:
debian:/home/volker# ./test2.sh
: integer expression expected
Found package: Desired=Unknown/Install/Remove/Purge/Hold
Do you wish to install Desired=Unknown/Install/Remove/Purge/Hold ?
1) Yes
2) No
#? 1
Reading package lists... Done
Building dependency tree       
Reading state information... Done
E: Couldn't find package Desired
Desired is of course not a package but a comment from apt-get, I guess. How could I wrap a loop around dpkg so that it stops after each package that was found?
 
Old 02-19-2010, 11:27 AM   #8
Softsmid
LQ Newbie
 
Registered: Feb 2010
Location: Netherlands
Distribution: Ubuntu, OpenSUSE
Posts: 8

Original Poster
Rep: Reputation: 0
Quote:
Originally Posted by i92guboj View Post
A pipe connects the standard output from a process to the standard input (which usually is attached to the console/keyboard) of another process. In this case, it connects the output of dpkg (or whatever else) to the input of the while construct. On each iteration of the while sentence the read command will get a string and store it as $package, you can do whatever you need to do with that variable inside the while loop, and so on for each value of $package (all the values listed by your dpkg sentence).

Arrays are truly not necessary since you are not needing to save the data to do something else after this. They would be a waste of resources and time in this case. For me, anyway.

If you can't use pipes because this is homework then that's a different issue though.
Oh no, I could use pipes. But I am literately learning Bash as I am writing this. I did get a confusing result, so I stayed with my first approach. Any further suggestion about your approach is welcome.
 
Old 02-19-2010, 11:37 AM   #9
i92guboj
Gentoo support team
 
Registered: May 2008
Location: Lucena, Córdoba (Spain)
Distribution: Gentoo
Posts: 4,072

Rep: Reputation: 384Reputation: 384Reputation: 384Reputation: 384
Quote:
Originally Posted by Softsmid View Post
Yes, I know. If I put it inside the loop I do not get a list of packages but this output from running the script:

Code:
debian:/home/volker# ./test2.sh
: integer expression expected
This is the "if" sentence complaining. Check my post above to see how to properly do the comparison. Also, quote variables and values "...." unless you have a good reason not to. It will save you a lot of pain.

Quote:
Code:
Found package: Desired=Unknown/Install/Remove/Purge/Hold
Do you wish to install Desired=Unknown/Install/Remove/Purge/Hold ?
1) Yes
2) No
#? 1
Reading package lists... Done
Building dependency tree       
Reading state information... Done
E: Couldn't find package Desired
Desired is of course not a package but a comment from apt-get, I guess. How could I wrap a loop around dpkg so that it stops after each package that was found?
Instead of doing the whole thing I suggest you to do something simple, then add functionality step by step.

You should really start by reading the list and printing it.

Code:
for token in `<command>`; do
  echo "Next token is: \"$token\""
done
Once done that, and only if it works, add the select sentence:

Code:
for token in $(<whatever command>); do
  echo "Next token is: \"$token\""
  echo "Do you like this token?"
  select answer in Yes No Quit
  do
    case "$answer" in
      Yes|y ) echo "Yes. I like $token"; break;;
      No|n ) echo "Ughh, take $token away"; break;;
      Quit|q ) echo "Quit this nonsense, I want to go out."; exit 0;;
      *) echo "I didn't understand, try again."; continue;;
    esac
  done
done
Once you have dominated the echo command you can start worrying about the actual functionality. Your main problem right now is that you don't seem to understand the way that most basic structures work, besides not respecting some basic syntax rules as variable quoting either.

Last edited by i92guboj; 02-19-2010 at 11:38 AM.
 
Old 02-21-2010, 07:26 PM   #10
chrism01
LQ Guru
 
Registered: Aug 2004
Location: Sydney
Distribution: Centos 6.9, Centos 7.3
Posts: 17,356

Rep: Reputation: 2367Reputation: 2367Reputation: 2367Reputation: 2367Reputation: 2367Reputation: 2367Reputation: 2367Reputation: 2367Reputation: 2367Reputation: 2367Reputation: 2367
Good bash tutorials

http://rute.2038bug.com/index.html.gz
http://tldp.org/LDP/Bash-Beginners-G...tml/index.html
http://www.tldp.org/LDP/abs/html/
 
  


Reply


Thread Tools Search this Thread
Search this Thread:

Advanced Search

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is Off
HTML code is Off



Similar Threads
Thread Thread Starter Forum Replies Last Post
Is there anyway to execute bash as interactive and run a command? nfirvine Linux - Software 6 06-23-2009 11:19 PM
setting a timeout in an interactive bash shell script steven.c.banks Linux - General 2 01-23-2009 04:07 PM
BASH - How to open an interactive script from a non interactive script..... OldGaf Programming 4 06-29-2008 04:34 PM
bash script works when interactive, endless loop when started via cron dguy Linux - General 5 04-10-2006 11:39 AM
make bash interactive and change prompt DropSig Linux - Newbie 3 05-17-2004 08:16 AM


All times are GMT -5. The time now is 09:37 AM.

Main Menu
Advertisement
My LQ
Write for LQ
LinuxQuestions.org is looking for people interested in writing Editorials, Articles, Reviews, and more. If you'd like to contribute content, let us know.
Main Menu
Syndicate
RSS1  Latest Threads
RSS1  LQ News
Twitter: @linuxquestions
Facebook: linuxquestions Google+: linuxquestions
Open Source Consulting | Domain Registration