Recursive dependencies, recursive uninstall, variants
Ryan Schmidt
ryandesign at macports.org
Fri Apr 25 22:15:17 PDT 2008
On Apr 25, 2008, at 12:59 PM, Shreevatsa R wrote:
> Hi MacPorts developers,
>
> I was planning to write some non-trivial code before posting to this
> list, but I thought I would first check if I was doing anything
> stupid.
>
> I found that the "port deps" command only lists the explicit
> dependencies of a port, and not everything that the port actually
> depends on ("recursive dependencies"). This meant that often
> installing something trivial looking would start pulling in something
> enormous that I didn't want to install, and I would have to kill it,
> or wait hours. Contrast this to something like Debian's apt (used by
> Fink too), which when you try to install something, gives a message
> like:
> # apt-get install nautilus
> Reading Package Lists... Done
> Building Dependency Tree... Done
> The following extra packages will be installed:
> bonobo libmedusa0 libnautilus0
> The following NEW packages will be installed:
> bonobo libmedusa0 libnautilus0 nautilus
> 0 packages upgraded, 4 newly installed, 0 to remove and 1 not
> upgraded.
> Need to get 8329kB of archives. After unpacking 17.2MB will be
> used.
> Do you want to continue? [Y/n]
>
> So deciding that at least knowing all dependencies of a port
> beforehand would help, I tried writing a command for recursive
> dependencies. The proc action_deps does a lot of stuff, and it's not
> easy getting just the list of dependencies with no extra output, so I
> wrote my own "bare" proc that does the actual dependencies, etc., and
> rdeps that recursively calls it:
>
> proc add_to_set {set_var item} {
> upvar $set_var var
> if {[lsearch -exact $var $item] == -1} { lappend var $item }
> }
>
> proc actdeps {portname depstype} {
> array unset portinfo
> array set portinfo [lindex [mportsearch $portname no exact] 1]
>
> #set deps [map {x {lindex [split $x :] end}} $portinfo($depstype)]
> set deps []
> if {[info exists portinfo($depstype)]} {
> foreach i $portinfo($depstype) {
> lappend deps [lindex [split $i :] end]
> }
> }
> return $deps
> }
>
> proc rdeps {portname {depth 0}} {
> global shownports
> if [info exists shownports] { } else { set shownports [] }
> add_to_set shownports $portname
>
> set depstypes {depends_build depends_lib depends_run}
> set depstypes_descr {"build" "library" "runtime"}
>
> foreach depstype $depstypes depsdecr $depstypes_descr {
> foreach port [actdeps $portname $depstype] {
> if {[lsearch $shownports $port] == -1} {
> puts "[string repeat \t $depth]$port"
> rdeps $port [expr {$depth + 1}]
> }
> }
> }
> }
>
> proc action_rdeps {action portlist opts} {
> foreachport $portlist {
> rdeps $portname
> }
> }
>
> And "rdeps action_rdeps" in action_array. Yeah, it uses a global
> variable to avoid printing the same ports again, but it works:
>
> ~$ port rdeps subversion
> expat
> neon
> gettext
> libiconv
> gperf
> ncurses
> ncursesw
> openssl
> zlib
> apr
> apr-util
> db44
> sqlite3
> gawk
> gmake
> readline
>
> This is not great code, but it does what I want. (It is also the only
> Tcl I have ever written, so please tell me what I'm doing stupidly.)
> I was planning to do the same for variants (because I install
> something and later discover I should have installed one of its
> dependencies with a different variant), and for uninstall (because it
> is a real pain to uninstall ports).
> More specifically, I was planning to
> (1) make a general (simple) function for getting a specific port's
> "tree of dependencies" (and/or tree of dependents) and then something
> to act on it. Uninstall would then be trivial.
> (2) Also, putting something to return the list of dependencies of a
> port in the MacPorts API itself.
> (3) Also, looking at action_deps, it seems to share a lot in common
> with other functions (searching for ports, etc.), so that part can be
> cleaned up...
>
> Comments?
Being able to get a recursive list of dependencies would certainly be
useful. I wrote a PHP web page [1] to display a graph of this
information, because I also wanted to see it. Would be handy to have
the main logic in the port command. Should make it faster.
[1] http://www.ryandesign.com/tmp/portviz.tar.bz2
More information about the macports-dev
mailing list