review: I would suggest cherry-picking part of the branch
[ikiwiki] / doc / todo / pagespec_expansions.mdwn
1 A couple of suggestions for improving the usefulness of pagespecs:
2
3 * @ to match [^/]* (i.e. all pages exactly one level below this one)
4 * initial ./ to mean "from the page the pagespec is running from".
5   This would require some architectural changes and a change to the
6   interface for pagespec_match. What do you think? I have
7   lots of pages a/b/c.mdwn that inline "a/b/c/*".
8
9 --Ethan
10
11 > I want this too, so that the [[examples]] can use pagespecs that don't
12 > have to be changed when the pages are moved around. I don't know how I
13 > feel about the "@" thing, but "./" seems good. I take it you've looked at
14 > how to implement it?
15 >
16 > It's worth mentioning that there's a bit of an inconsistency; wikilinks
17 > match relative by default and absolute if prefixed with a "/", while
18 > pagespecs match absolute by default. It would be nice to clear up that
19 > inconsistency somehow, it's on my little list of things in ikiwiki that
20 > arn't ideal. :-) --[[Joey]]
21
22 I've looked at how to implement "./", yes, and I was a little hesitant
23 to disturb the elegant implementation of pagespecs as it is now. That's 
24 why I wrote this todo item rather than just a patch. :) As I see it,
25 the simplest thing to do is check globs when building the pagespec 
26 expression and translate "./foo" to "$from.'/foo'" in the resulting
27 expression, and then add the $from paramater to pagespec_match. This does
28 require an API change for all plugins which use pagespecs but hopefully
29 it should be minor. I will work on a patch tomorrow.
30
31 My use case for "@" (which is kind of a crummy symbol, but whatever) is
32 my [projects page](http://www.betacantrips.com/projects/). I want to inline 
33 "summary" or "introduction" pages that are exactly one level below the 
34 inlining page, but not tarballs or other junk that might be in 
35 subdirectories. (The issue is confounded here because of my index.mdwn 
36 patch, but the principle is the same.) I chose "@" because it's similar in 
37 physical shape to "*" but enclosed, suggesting limitations. I also thought
38 it would be useful in simplifying hacks like in [[plugins/map]] but I see
39 now that I was mistaken.. "four or fewer levels deep" would be 
40 "@ or @/@ or @/@/@ or @/@/@/@". Well, I think it has a certain appeal but
41 I can see why it might not be much of an improvement. :) --Ethan
42
43 > Seems to me that ".." would be the natural thing to use, not "@". --[[Joey]]
44
45 >> I don't understand.. "a/b/.." matches a/b/c but not a/b/c/d ? That doesn't 
46 >> seem natural to me at all. --Ethan
47
48 >>> Ah.. in that case, why not use "a/b/* and !a/b/*/*" ? No need for a new
49 >>> symbol. --[[Joey]]
50
51 >>>> I know it's not necessary, but it would be helpful. --Ethan
52
53 >>>>> I don't see the need for a new syntax since it's only a little long
54 >>>>> using the old one. And of course even that can now be shortened: 
55 >>>>> "./* and !./*/*" --[[Joey]]
56
57 OK, I took a shot at implementing the changes. I was thinking about making
58 pagespecs relative by default but I couldn't decide whether page
59 `foo/bar` inlining `*` should match `foo/bar/*` or `foo/*`.
60 So I punted and left things as absolute, with `./*` matching
61 `foo/bar/*`, which I think is pretty clear.
62 The patch is at [ikidev](http://ikidev.betacantrips.com/patches/pagespec_enhancements.patch)
63 and you can see it work at 
64 [this page](http://ikidev.betacantrips.com/one/two/three/index.html) or
65 [this page](http://ikidev.betacantrips.com/one/two/three/princess.html) --Ethan
66
67 > Nice patch, though I see the following problems with it:
68 > * The sole pagespec_match in IkiWiki::Render probably should have `$p`
69 >   as its third parameter. This will allow add_depends to add a
70 >   dependency on a pagespec that matches relative to the page. I made this
71 >   changes and it seems to work, new pages are noticed in updates.
72
73 >> OK, word.
74
75 > * `! $from` fails to match pages named "0" :-)
76
77 >> I don't understand. How did you even get $from into the 
78 >> translated pagespec?
79
80 > * '/./ matches any letter, not just "." :-) :-)
81
82 >> Oof, thanks for catching that.
83
84 > * One other major problem. If you look at the doc/examples/blog/index.mdwn
85 >   I changed it to use relative globs like "./posts/*", but they didn't work,
86 >   because it looked for examples/blog/indexposts/* instead of
87 >   examples/blog/index/posts/*. And, of course, what I really expected it to
88 >   look for was examples/blog/posts/*. I think you may have made the wrong
89 >   choice about that, so I changed it to go the other way. What do you think?
90
91 >> I could have sworn I made a change like that -- I was gonna make a call to
92 >> basename() or something .. wait, I might have decided not to, because it 
93 >> would interfere with my index patch. Yeah, I guess my code was wrong.
94 >> Don't "nice patches" usually work? :) My test cases were mostly "./*",
95 >> so it slipped under the radar.
96
97 >> As for what it should have done, that's much harder! My gut feeling is that
98 >> "a/b/c.mdwn" inlining `./*` wants `a/b/c/*` and not `a/b/*`, and this is 
99 >> what I programmed for. I also feel that "a/b/c" inlining `./d/*` could go
100 >> either way. Ideally we'd check for both, maybe using bestlink?
101
102 >> The issue might be confounded some by your use of an index page, and 
103 >> ikiwiki doesn't have good support for those yet :) .
104 >> I think ideally your index page would be treated as inlining from 
105 >> examples/blog/. To resolve this issue we should consider, for example:
106 >> clothes/pants inlines `./jeans/*` -- probably means clothes/pants/jeans
107 >> vacation/bermuda/blog inlines `./pics/*` -- probably vacation/bermuda/pics
108
109 >>> What strikes me about your examples is that the "right thing" is
110 >>> utterly contect dependent. Unfortunatly, I don't think that using
111 >>> bestlink inside pagespec is possible. bestlinks change as pages are
112 >>> added/removed, and dealing with the matches of a pagespec changing when
113 >>> some page that is added or removed seems Hard.
114 >>>
115 >>> Since it seems we have to arbitrarily pick one of the two behaviors, I
116 >>> prefer the one I picked for two reasons:
117 >>> 1. The other behavior can be obtained easily from it, for example,
118 >>>    use ./c/* to limit the matches to that subdir.
119 >>> 2. The common case is a bunch of pages in a single directory, not lots
120 >>>    of deeply nested subdirs.
121 >>> --[[Joey]]
122
123 >>>> Context-dependence was my conclusion too. My feeling is that inlining
124 >>>> in a subdirectory of the current page is more common, but I don't 
125 >>>> really know. However, I think the changes as written should work OK
126 >>>> with my index patch and allowing inlining from a/b/c/, so I'm
127 >>>> satisfied. --Ethan
128
129 > I've committed support for ./ to ikiwiki now, based on your patch.
130 > [[todo/done]]
131 > --[[Joey]]
132
133 >> Cool! I haven't played with it yet, but looking over the patch, I see that
134 >> you added another parameter to match_glob, which is an approach that didn't
135 >> occur to me. I like it, it's more flexible. --Ethan
136
137 One last thing -- could you either change:
138
139                 $from=~s!/?[^/]+$!!;
140
141 to 
142
143                 $from=~s!/?[^/]*$!!;
144
145 Or could you put in:
146
147                 $glob =~ s!//!/!g;
148
149 somewhere? Or should I just add this to my index patch? --Ethan
150
151 > If it's specific to your index patch, let's put it in there. --[[Joey]]