Short version:
--------------
aptitude search '?archive(now)'
matches all packages that are in installed or removed (not purged) states.
Naturally,
aptitude search '?archive(foobar)'
matches 0 packages and
aptitude search '?archive(stable)'
matches (most) of the packages on this machine (not backports.org etc).
So it seems that "now" is a special, undocumented value for the archive
match. I can't see that "now" would have any use and (as below) it makes life
a little harder than it should be to do things.
Long version:
-------------
I was trying to be far too clever for my own good with an aptitude search to
find all packages that don't have a current version in a repository. (Note:
this is a different search to ?obsolete, as packages which have either a
newer or older version in any archive are not considered obsolete, even though
the installed version is not available from any archive. I'd be happy to have
my aptitude-fu improved with suggestions on how else to do this, btw)
I was looking at ?archive() as a search term to spot packages that didn't have
an available archive.
In a squeeze chroot, I installed three packages that are not from testing (one
local package, one package from lenny, one package from sid). The search:
aptitude search '?narrow(?archive(testing),?version(CURRENT))'
correctly finds the packages that are installed and currently available from
the testing repo and doesn't list the archive-less test packages.
Hoping to be able to match packages with no archive set, I tried ?archive(^$)
to no avail. I don't know if this is just another manifestation of ?archive(now)
or if there's some other regular expression that should be used.
So let's try negating that to find the package versions that have no repo:
aptitude search '?narrow(?not(?archive(testing)),?version(CURRENT))'
and this correctly lists the three test packages I have in the chroot that are
not from testing (one local package, one package from lenny, one package from
sid).
Now part of the objective here was to write a recipe that would work across all
releases, rather than having to substitute "testing" in there. This is
particularly relevant for backports.org users as you end up needing:
aptitude search '?narrow(?not(?archive(~(stable~|lenny-backports~))),?version(CURRENT))'
which is starting to look like line noise, and to write an exhaustive list of
archives would be tedious. But all of these archives are just [a-z]+ as a
regular expression, so this should work:
aptitude search '?narrow(?not(?archive([a-z]+)),?version(CURRENT))'
Except that "now" also matched [a-z]+ so this search doesn't return anything.
Perhaps one could construct various assertions against "now" for ?archive():
aptitude search '?narrow(?not(?archive("^[^now]{3}.*$")),?version(CURRENT))'
which works, up to the point where it relies on Debian releases never having
names like "bo".
So, working around "now" seems quite difficult; there's probably an easier way
to achieve this target anyway and I'd be happy to hear suggestions.
cheers
Stuart
On Thu, Apr 29, 2010 at 12:49:03AM +0100, Stuart Prescott <stuart+debian@nanonanonano.net> was heard to say:
The string "now" actually comes directly from apt.
I could filter it in search patterns (it's already filtered in
various parts of the UI), but I know that people use the aptitude
command-line in scripts, and making "now" no longer match anything
would be a backwards-incompatible change. So, +wontfix on that. I'm
not sure if that means this needs the wontfix flag -- it sounds like
you'd be happy to have some other way of doing the same thing.
(you might ask who would use this feature, but I've been amazed at
some of the other stuff people depended on)
As for the rest of your report, I think that you want a ?downloadable
pattern that would apply on a per-version basis, right? I don't think
there's really a way to get at that information via the current set of
patterns, so a new one would make sense. (it's similar to making
?obsolete check per version, but doesn't break backwards compatibility)
Another option would be to implement an idea I've had for a while, to
more fully support more "types" in the search language. So you'd have
something like:
?has-version(?has-archive(?not(?archive(now))))
Daniel
Hi Daniel, yes, I found the filtering for "now" in the source code for the UI parts. I understand not wanting to make a backwards-incompatible change. Perhaps it should be documented for ?archive() in that case to save people spending quite so much time as I did the other day trying to work out why they couldn't negate the match properly. Yes! a ?downloadable would be good. I presume it would automatically limit itself to package-versions that are installed and not return all versions of packages like ?installed does. Not limiting itself like that would require the use of ?narrow() all the time, I think. Would it actually make more sense to be in the negated sense already (something like, ?noarchive), since I would imagine that its primary use will be to find things that *aren't* downloadable. ?noarchive looks a lot nicer to deal with than ?not(?downloadable)?installed which I think is assuming that the ?downloadable package-version set would be equal to ?narrow(?version(CURRENT),?downloadable). If it's not, then there would need to be additional ?narrow statements in there somewhere. [or, more likely, I've misunderstood what you're suggesting here] I know you said "something like", but I'm not quite sure how that will work since '?not(?archive(now))' will provide a list of all packages in a "p" state and not any of the not-downloadable packages. But I can see what you're trying to sketch here. Yes, having the ability to include some sorts of tests in the search language would be nice. Since I presume that these sorts of things won't be available until squeeze+1 at this stage, I'll stick with the monstrosity I included earlier for the time being. I'm sort of glad that there isn't some really easy way to do this that I'd just fundamentally missed. thanks for your thoughts Stuart