And one port to install them all!
Today I was setting up a new box and wanted to get all my favorite ports installed with a minimum
of fuss. My first thoughts of were of a shell script. But then I thought of using a port to install
ports. After all, some ports have dependencies, and they install the ports they need. Why can’t I write
a port which just installs ports?
So I asked around. And I was told to use a meta-port. I was pointed at
misc/instant-workstation
. That is what I used as the basis for this
example meta-port.
The Makefile
All the files for this port are available in the samples directory.
You can download the files for this port from
newbox-checklist.tgz.
The Makefile is pretty simple. Here is it:
# New ports collection makefile for: newbox-checklist # Date created: 13 January 2002 # Whom: Dan Langille # # $Id: meta-ports.php,v 1.6 2007/08/27 16:34:47 dan Exp $ # PORTNAME= newbox-checklist PORTVERSION= 1.0 CATEGORIES= misc MASTER_SITES= # none DISTFILES= # none MAINTAINER= ports@freebsddiary.org RUN_DEPENDS= bash:${PORTSDIR}/shells/bash2 \ joe:${PORTSDIR}/editors/joe \ screen:${PORTSDIR}/misc/screen \ sudo:${PORTSDIR}/security/sudo \ xtail:${PORTSDIR}/misc/xtail \ ${PREFIX}/distributed.net/dnetc:${PORTSDIR}/misc/dnetc \ ${PREFIX}/etc/logcheck.sh:${PORTSDIR}/security/logcheck NO_WRKSUBDIR= YES NO_BUILD= YES do-install: # empty .include <bsd.port.mk>
Here are a few comments on the various parts of this Makefile.
- MASTER_SITES
-
The master site is where the distfile (distribution file) is downloaded from.
This file contains the source code, patches, etc, for the port. For our
meta-port, we don’t have any source ourselves. We are just using other ports.
This is why we have no master site. - DISTFILES
- As mentioned in the previous item, we have no distfile. Therefore this is emtpy.
- MAINTAINER
- Put your email address here
- RUN_DEPENDS
-
These are the ports which must be installed in order for our port to run. Well,
actually, *our* port never runs. But that is not relevant to our task. We will
exploit this feature for the ports tree for our our purpose. Namely, to install
the ports we want.- bash:${PORTSDIR}/shells/bash2
-
This entry consists of two fields. First, we have bash, the name of
the executable we are installing. We have not supplied a path name. Just
the file name of the executable. Next, we have the port which should be installed
if the executable is not found. We use the predefined value ${PORTSDIR}
in case our ports tree is not installed in /usr/ports. This format will work
well for most ports. - ${PREFIX}/distributed.net/dnetc:${PORTSDIR}/misc/dnetc
-
In this case, we are not installing an executable which can be found in the normal
places (as determined by your $PATH variable). Therefore, we provide the full
pathname to the file in question. I determined this path by inspecting
/var/db/pkg/dnetc-2.8010.462_1,1/+CONTENTS. Because it starts
with a /, the ports system will know this is the name of a file, not an executable.
Therefore, it will not search your $PATH.
- NO_WRKSUBDIR
- This prevents the creation of any subdirectories.
- NO_BUILD
- We have nothing to build, so let’s not build anything.
- do-install
- We have nothing to install when it comes to installing, so let’s not install anything.
For more information on the RUN_DEPENDS, or any other entry in a Makefile, please read
/usr/ports/Mk/bsd.port.mk
Using the makefile
To use the port, download it from newbox-checklist.tgz.
Then unpack the tarball and install it.
fetch http://www.FreeBSDDiary.org/samples/ports/tarballs/newbox-checklist.tgz
tar xvfz newbox-checklist.tgz
cd newbox-checklist
make install
make clean
cd ..
rm -rf newbox-checklist newbox-checklist.tgz
pkg_delete newbox-checklist-1.0
Do not be concerned if you see the following error:
$ sudo pkg_delete newbox-checklist-1.0>
pkg_delete: couldn't open dependency file /var/db/pkg/sudo-1.6.3.7_2/+REQUIRED_BY'
That is to be expected. This is the ports tree attempting to do the right thing.
We told the ports tree with our RUN_DEPENDS entry that sudo
was required by our port. But because we already had sudo installed before I ran
this port, this dependency is not registered with sudo.
Other uses for metaports
In this example, all that we have done with this port is install other ports.
But you an also use the ports tree for system administration. You could
distribute configuration files for example. A good template to use might be
misc/instant-workstation. This port installs
several ports, modifies /etc/rc.conf, and adds
/etc/ntp.conf, amongst other things.
<me banging head on keyboard>
Just use an /stand/sysinstall’s unattended install script. If you specify your CDROM as the installation media and don’t install XFree86 – you get a brand new box in just over 5 minutes. Play around with the script, it ain’t all that bad if you have a huge cluster to roll out. 🙂 And yes, you can use DHCP if you wanted to…
——————————————————–
debug=yes
hostname=your.host.here
domainname=your.domain
nameserver=primary_dns_ip_here
nameserver=secondary_dns_ip_here
defaultrouter=your_gateway_ip_here
ipaddr=your_ip_here
netmask=your_netmask_here
_ftpPath=ftp://ftp3.freebsd.org/pub/FreeBSD
netDev=ed0
mediaSetFTPActive
dists=bin crypto
distSetCustom
disk=ad0
partition=all
bootManager=standart
diskPartitionEditor
ad0s1-1=ufs 204800 /
ad0s1-2=swap 786432 none
ad0s1-3=ufs 104857 /var 1
ad0s1-4=ufs 0 /usr 1
diskLabelEditor
diskPartitionWrite
diskLabelCommit
installCommit
command=mount -t msdos /dev/fd0 /mnt
system
command=cp /mnt/etc/rc.conf /etc
system
command=cp /mnt/etc/resolv.conf /etc
system
command=cp /mnt/etc/XF86Config /etc/X11
system
package=bash-2.05
packageAdd
package=XFree86-4.1.0_6
packageAdd
package=linux_base-6.1
packageAdd
package=linux-navigator-4.78
packageAdd
command=/usr/sbin/tzsetup
system
command=/usr/bin/passwd
system
command=pw user add -n new_username_here -d /usr/home/new_username_here -g wheel -L wheel -m -s /usr/local/bin/bash -w random
| mail -s "new_username_here password" email_address_here
system
shutdown
This is interesting. Given the above script, how do you invoke it with/from /stand/sysinstall?
I think the meta-port is a better option since chances are your ports directory will be more up-to-date than any of the files on the original CD. On a side note though this would be much quicker than compiling from ports
James A. Peltier wrote:
>
> On a side note though this
> would be much quicker than compiling from ports
But the meta-port <I>does</I> compile from ports. The meta-port is just a short hand way of doing:
is port x/y installed?
no, cd /usr/ports/x/y && make install
is port a/by installed?
no, cd /usr/ports/a/b && make install
etc.
can you have the script automatically run another script ie. if I install BIND 9.2.0 from the ports directory can I have it automatically run /usr/local/sbin/bind9-enable ??? same with qmail or anything else???
Yes, you can have the script run another script/program. If you look at the bottom of it, that’s how a new user is created. You call command="you script here without the quotes" and then do a ‘system’ call. From man sysinstall:
system Execute an arbitrary command with system(3)
Variables:
command
The name of the command to execute.
actually i was referring to the meta-port example regarding running the script. but it’s my fault i didn’t post it in the correct area.
You wrote "I determined this path by inspecting /var/db/pkg/dnetc-2.8010.462_1,1/+CONTENTS. Because it starts with a /, the ports system will know this is the name of a file, not an executable. Therefore, it will not search your $PATH. " All files, even executable ones, have names that start with a / , for the ports system to "know" that files with such names are not executable may be some restriction placed on users of the ports system, but it is not an inherent condition of a UNIX-like system. Once a / is involved in the name of the first file on a command line, the PATH is not searched.
Gerald Stoller wrote:
>
> You wrote "I determined this path by inspecting
> /var/db/pkg/dnetc-2.8010.462_1,1/+CONTENTS. Because it starts
> with a /, the ports system will know this is the name of a
> file, not an executable. Therefore, it will not search your
> $PATH. "
Yes, I did write that.
> All files, even executable ones, have names that
> start with a / , for the ports system to "know" that files
> with such names are not executable may be some restriction
> placed on users of the ports system, but it is not an
> inherent condition of a UNIX-like system.
Note: I did not say system. I said "the ports system". I maintain my statement is correct. However, I did not state where I obtained this information. Sorry about that. The following extract is from /usr/ports/Mk/bsd.port.mk
# FETCH_DEPENDS – A list of "path:dir[:target]" tuples of other ports this
# package depends in the "fetch" stage. "path" is the
# name of a file if it starts with a slash (/), an
# executable otherwise. make will test for the
# existence (if it is a full pathname) or search for
# it in your $PATH (if it is an executable) and go
# into "dir" to do a "make all install" if it’s not
# found. If the third field ("target") exists, it will
> Once a / is
> involved in the name of the first file on a command line,
> the PATH is not searched.
I think we are talking about two different things here.