safe => 0,
rebuild => 0,
},
- getctime => {
+ gettime => {
type => "internal",
default => 0,
- description => "running in getctime mode",
+ description => "running in gettime mode",
safe => 0,
rebuild => 0,
},
$hooks{rcs}{rcs_getctime}{call}->(@_);
}
+sub rcs_getmtime ($) {
+ $hooks{rcs}{rcs_getmtime}{call}->(@_);
+}
+
sub rcs_receive () {
$hooks{rcs}{rcs_receive}{call}->();
}
hook(type => "rcs", id => "rcs_recentchanges", call => \&rcs_recentchanges);
hook(type => "rcs", id => "rcs_diff", call => \&rcs_diff);
hook(type => "rcs", id => "rcs_getctime", call => \&rcs_getctime);
+ hook(type => "rcs", id => "rcs_getmtime", call => \&rcs_getmtime);
}
sub checkconfig () {
return $ctime;
}
+sub rcs_getmtime ($) {
+ error "rcs_getmtime is not implemented for bzr\n"; # TODO
+}
+
1
hook(type => "rcs", id => "rcs_recentchanges", call => \&rcs_recentchanges);
hook(type => "rcs", id => "rcs_diff", call => \&rcs_diff);
hook(type => "rcs", id => "rcs_getctime", call => \&rcs_getctime);
+ hook(type => "rcs", id => "rcs_getmtime", call => \&rcs_getmtime);
}
sub genwrapper () {
return $date;
}
+sub rcs_getmtime ($) {
+ error "rcs_getmtime is not implemented for cvs\n"; # TODO
+}
+
1
hook(type => "rcs", id => "rcs_recentchanges", call => \&rcs_recentchanges);
hook(type => "rcs", id => "rcs_diff", call => \&rcs_diff);
hook(type => "rcs", id => "rcs_getctime", call => \&rcs_getctime);
+ hook(type => "rcs", id => "rcs_getmtime", call => \&rcs_getmtime);
}
sub silentsystem (@) {
return $date;
}
+sub rcs_getmtime ($) {
+ error "rcs_getmtime is not implemented for darcs\n"; # TODO
+}
+
1
hook(type => "rcs", id => "rcs_recentchanges", call => \&rcs_recentchanges);
hook(type => "rcs", id => "rcs_diff", call => \&rcs_diff);
hook(type => "rcs", id => "rcs_getctime", call => \&rcs_getctime);
+ hook(type => "rcs", id => "rcs_getmtime", call => \&rcs_getmtime);
hook(type => "rcs", id => "rcs_receive", call => \&rcs_receive);
}
return $ctime;
}
+sub rcs_getmtime ($) {
+ error "rcs_getmtime is not implemented for git\n"; # TODO
+}
+
sub rcs_receive () {
# The wiki may not be the only thing in the git repo.
# Determine if it is in a subdirectory by examining the srcdir,
hook(type => "rcs", id => "rcs_recentchanges", call => \&rcs_recentchanges);
hook(type => "rcs", id => "rcs_diff", call => \&rcs_diff);
hook(type => "rcs", id => "rcs_getctime", call => \&rcs_getctime);
+ hook(type => "rcs", id => "rcs_getmtime", call => \&rcs_getmtime);
}
sub checkconfig () {
return $ctime;
}
+sub rcs_getmtime ($) {
+ error "rcs_getmtime is not implemented for mercurial\n"; # TODO
+}
+
1
hook(type => "rcs", id => "rcs_recentchanges", call => \&rcs_recentchanges);
hook(type => "rcs", id => "rcs_diff", call => \&rcs_diff);
hook(type => "rcs", id => "rcs_getctime", call => \&rcs_getctime);
+ hook(type => "rcs", id => "rcs_getmtime", call => \&rcs_getmtime);
}
sub checkconfig () {
return $date;
}
+sub rcs_getmtime ($) {
+ error "rcs_getmtime is not implemented for monotone\n"; # TODO
+}
+
1
hook(type => "rcs", id => "rcs_recentchanges", call => \&rcs_recentchanges);
hook(type => "rcs", id => "rcs_diff", call => \&rcs_diff);
hook(type => "rcs", id => "rcs_getctime", call => \&rcs_getctime);
+ hook(type => "rcs", id => "rcs_getmtime", call => \&rcs_getmtime);
}
sub getsetup () {
}
sub rcs_getctime ($) {
- error gettext("getctime not implemented");
+ return 0;
+}
+
+sub rcs_getmtime ($) {
+ return 0;
}
1
hook(type => "rcs", id => "rcs_recentchanges", call => \&rcs_recentchanges);
hook(type => "rcs", id => "rcs_diff", call => \&rcs_diff);
hook(type => "rcs", id => "rcs_getctime", call => \&rcs_getctime);
+ hook(type => "rcs", id => "rcs_getmtime", call => \&rcs_getmtime);
}
sub checkconfig () {
return $date;
}
+sub rcs_getmtime ($) {
+ error "rcs_getmtime is not implemented for svn\n"; # TODO
+}
+
1
hook(type => "rcs", id => "rcs_recentchanges", call => \&rcs_recentchanges);
hook(type => "rcs", id => "rcs_diff", call => \&rcs_diff);
hook(type => "rcs", id => "rcs_getctime", call => \&rcs_getctime);
+ hook(type => "rcs", id => "rcs_getmtime", call => \&rcs_getmtime);
}
sub checkconfig () {
return $date;
}
+sub rcs_getmtime ($) {
+ error "rcs_getmtime is not implemented for tla\n"; # TODO
+}
+
1
}
else {
push @new, $file;
- if ($config{getctime} && -e "$config{srcdir}/$file") {
+ if ($config{gettime} && -e "$config{srcdir}/$file") {
eval {
- my $time=rcs_getctime("$config{srcdir}/$file");
- $pagectime{$page}=$time;
+ my $ctime=rcs_getctime("$config{srcdir}/$file");
+ if ($ctime > 0) {
+ $pagectime{$page}=$ctime;
+ }
};
if ($@) {
print STDERR $@;
}
+ my $mtime;
+ eval {
+ my $mtime=rcs_getmtime("$config{srcdir}/$file");
+ };
+ if ($@) {
+ print STDERR $@;
+ }
+ elsif ($mtime > 0) {
+ utime($mtime, $mtime, "$config{srcdir}/$file");
+ }
}
}
$pagecase{lc $page}=$page;
* conditional: Fix bug that forced "all" mode off by default.
* calendarmonth.tmpl: The month calendar is now put in a sidebar.
* calendar: Improved display of arrows.
+ * Rename --getctime to --gettime. (The old name still works for
+ backwards compatability.)
+ * --gettime now also looks up last modification time.
+ * Add rcs_getmtime to plugin API; currently only implemented
+ for git.
-- Joey Hess <joeyh@debian.org> Sun, 04 Apr 2010 12:17:11 -0400
> Some VCS, like git, set the file mtimes to the current time
> when making a new checkout, so they will be lost if you do that.
> The creation times can be retrived using the `--getctime` option.
-> I suppose it might be nice if there were a `--getmtime` that pulled
-> true modification times out of the VCS, but I haven't found it a big
-> deal in practice for the last modification times to be updated to the
-> current time when rebuilding a wiki like this. --[[Joey]]
+> --[[Joey]]
>
> > Thanks for the clarification. I ran some tests of my own to make sure I understand it right, and I'm satisfied
> > that the order of posts in my blog can be retrieved from the VCS using the `--getctime` option, at least if I
> > choose to order my posts by creation time rather than modification time. But I now know that I can't rely on
> > page modification times in ikiwiki as these can be lost permanently.
+>
+> > > Update: It's now renamed to `--gettime`, and pulls both the creation
+> > > and modification times. Also, per [[todo/auto_getctime_on_fresh_build]],
+> > > this is now done automatically the first time ikiwiki builds a
+> > > srcdir. So, no need to worry about this any more! --[[Joey]]
> >
> > I would suggest that there should at least be a `--getmtime` option like you describe, and perhaps that
> > `--getctime` and `--getmtime` be _on by default_. In my opinion the creation times and modification times of
> A quick workaround for me to get modification times right is the following
> little zsh script, which unfortunately only works for git:
- #!/usr/bin/env zsh
-
- set +x
-
- for FILE in **/*(.); do
- TIMES="`git log --pretty=format:%ai $FILE`"
- MTIME="`echo $TIMES | head -n1`"
-
- if [ ! -z $MTIME ]; then
- echo touch -m -d "$MTIME" $FILE
- touch -m -d "$MTIME" $FILE
- fi
-
- done
+>> Elided; no longer needed since --gettime does that, and much faster! --[[Joey]]
> --[[David_Riebenbauer]]
> recreate the ikiwiki srcdir
> 3. `git clone` from the bare git repository a second time,
> to create a checkout you can manually edit (optional)
-> 4. run `ikiwiki --getctime --setup your.setup`
-> The getctime will ensure page creation times are accurate
-> by putting the info out of the git history,
-> and only needs to be done once.
>
> If you preserved your repository, but not the setup file,
> the easiest way to make one is probably to run
It's ok if this is not implemented, and throws an error.
+#### `rcs_getmtime($)`
+
+This is used to get the page modification time for a file from the RCS, by
+looking it up in the history.
+
+It's ok if this is not implemented, and throws an error.
+
#### `rcs_receive()`
This is called when ikiwiki is running as a pre-receive hook (or
Lack of support in [[ikiwiki-makerepo]] or auto.setup can make it harder to
set up a wiki using that revision control system. The `rcs_commit_staged`
hook is needed to use [[attachments|plugins/attachment]] or
-[[plugins/comments]]. And so on. The table below summarises this for each
-revision control system and links to more information about each.
+[[plugins/comments]]. `rcs_getctime` may be implemented in a fast way
+(ie, one log lookup for all files), or very slowly (one lookup per file).
+And so on. The table below summarises this for each revision control
+system and links to more information about each.
[[!table data="""
feature |[[git]]|[[svn]]|[[bzr]] |[[monotone]]|[[mercurial]]|[[darcs]]|[[tla]] |[[cvs]]
`rcs_rename` |yes |yes |yes |yes |no |yes |no |yes
`rcs_remove` |yes |yes |yes |yes |no |yes |no |yes
`rcs_diff` |yes |yes |yes |yes |no |yes |yes |yes
+`rcs_getctime` |fast |slow |slow |slow |slow |slow |slow |slow
+`rcs_getmtime` |fast |no |no |no |no |no |no |no
anonymous push |yes |no |no |no |no |no |no |no
conflict handling |yes |yes |yes |buggy |yes |yes |yes |yes
"""]]
Use case: You want to move away from Wordpress to Ikiwiki as your blogging/website platform, but you want to retain your old posts.
-[This](http://git.chris-lamb.co.uk/?p=ikiwiki-wordpress-import.git) is a simple tool that generates [git-fast-import](http://www.kernel.org/pub/software/scm/git/docs/git-fast-import.html)-compatible data from a WordPress export XML file. It retains creation time of each post, so you can use Ikiwiki's <tt>--getctime</tt> to get the preserve creation times on checkout.
+[This](http://git.chris-lamb.co.uk/?p=ikiwiki-wordpress-import.git) is a simple tool that generates [git-fast-import](http://www.kernel.org/pub/software/scm/git/docs/git-fast-import.html)-compatible data from a WordPress export XML file. It retains creation time of each post, so you can use Ikiwiki's <tt>--gettime</tt> to get the preserve creation times on checkout.
WordPress categories are mapped onto Ikiwiki tags. The ability to import comments is planned.
No idea how this happened. I've blown it away and recreated it but, for future reference, is there any less violent way to recover from this situation? I miss having the correct created and last edited times. --[[sabr]]
> update: fixed ctimes and mtimes using [these instructions](http://u32.net/Mediawiki_Conversion/Git_Import/#Correct%20Creation%20and%20Last%20Edited%20time) --[[sabr]]
-> That's overly complex. Just run `ikiwiki -setup your.setup -getctime`.
+> That's overly complex. Just run `ikiwiki -setup your.setup -gettime`.
> BTW, I'd be interested in examining such a corrupt storable file to try
> to see what happened to it. --[[Joey]]
->> --getctime appears to only set the last edited date. It's not supposed to set the creation date, is it? The only place that info is stored is in the git repo.
+>> --gettime appears to only set the last edited date. It's not supposed to set the creation date, is it? The only place that info is stored is in the git repo.
>>> Pulling the page creation date out of the git history is exactly what
->>> --getctime does. --[[Joey]]
+>>> --gettime does. (It used to be called --getctime, and only do that; now
+>>> it also pulls out the last modified date). --[[Joey]]
>> Alas, I seem to have lost the bad index file to periodic /tmp wiping; I'll send it to you if it happens again. --[[sabr]]
[[!tag wishlist]]
-It might be a good idea to enable --getctime when `.ikiwiki` does not
+It might be a good idea to enable --gettime when `.ikiwiki` does not
exist. This way a new checkout of a `srcdir` would automatically get
-ctimes right. (Running --getctime whenever a rebuild is done would be too
+ctimes right. (Running --gettime whenever a rebuild is done would be too
slow.) --[[Joey]]
Could this be too annoying in some cases, eg, checking out a large wiki
that needs to get set up right away? --[[Joey]]
+
+> Not for git with the new, optimised --getctime. For other VCS.. well,
+> pity they're not as fast as git ;), but it is a one-time expense...
+> [[done]] --[[Joey]]
intercepted. If you enable this option then you must run at least the
CGI portion of ikiwiki over SSL.
-* --getctime
+* --gettime
- Pull creation time for each new page out of the revision control
- system. This rarely used option provides a way to get the real creation
- times of items in weblogs, such as when building a wiki from a new
- VCS checkout. It is unoptimised and quite slow. It is best used
- with --rebuild, to force ikiwiki to get the ctime for all pages.
+ Extract creation and modification times for each new page from the
+ the revision control's log. This is done automatically when building a
+ wiki for the first time, so you normally do not need to use this option.
* --set var=value
"wrappergroup=s" => \$config{wrappergroup},
"usedirs!" => \$config{usedirs},
"prefix-directives!" => \$config{prefix_directives},
- "getctime" => \$config{getctime},
+ "getctime" => \$config{gettime},
+ "gettime" => \$config{gettime},
"numbacklinks=i" => \$config{numbacklinks},
"rcs=s" => \$config{rcs},
"no-rcs" => sub { $config{rcs}="" },
+++ /dev/null
-#!/bin/sh
-# Sets mtimes of all files in the tree their last change date
-# based on git's log. Useful to avoid too new dates after a
-# fresh checkout, which lead to ikiwiki unnecessarily rebuilding
-# basewiki files on upgrade.
-if [ -d .git ]; then
- for file in $(git ls-files); do
- date="$(git log -1 --date=rfc "$file" | grep ^Date: | sed -e 's/Date://')"
- if [ -n "$date" ]; then
- echo "$date $file"
- touch -d"$date" $file
- fi
- done
-fi