On Sat, Nov 12, 2011 at 12:45 PM, Eric Blake <ebl...@redhat.com> wrote: > On 11/12/2011 09:16 AM, Peng Yu wrote: >> Hi, >> >> coreutils can give abspaths ('readlink -f -e'). But I'm not able to >> find a command for relative paths. > > I had to go chase down python documentation to see what you wanted, > since you didn't give an example: > >> >> print os.path.relpath(path, start) > > http://docs.python.org/library/os.path.html >>> os.path.relpath(path[, start]) >>> >>> Return a relative filepath to path either from the current directory or >>> from an optional start point. > > Ah, so the idea is that python has a function that computes a relative > pathname to one path given a starting point: > > $ relpath /usr/bin /tmp > ../usr/bin > $ relpath /usr/bin /usr/share > ../bin > > This seems like you could do it in shell without resorting to python, by > computing a canonical name for both the destination and the starting > point, then comparing common prefixes, and for every directory component > that differs after the common prefix, replacing the directory with > '../'. This has been done before; for example, this is from gnulib-tool: > > # func_relativize DIR1 DIR2 > # computes a relative pathname RELDIR such that DIR1/RELDIR = DIR2. > # Input: > # - DIR1 relative pathname, relative to the current directory > # - DIR2 relative pathname, relative to the current directory > # Output: > # - reldir relative pathname of DIR2, relative to DIR1 > func_relativize () > { > dir0=`pwd` > dir1="$1" > dir2="$2" > sed_first='s,^\([^/]*\)/.*$,\1,' > sed_rest='s,^[^/]*/*,,' > sed_last='s,^.*/\([^/]*\)$,\1,' > sed_butlast='s,/*[^/]*$,,' > while test -n "$dir1"; do > first=`echo "$dir1" | sed -e "$sed_first"` > if test "$first" != "."; then > if test "$first" = ".."; then > dir2=`echo "$dir0" | sed -e "$sed_last"`/"$dir2" > dir0=`echo "$dir0" | sed -e "$sed_butlast"` > else > first2=`echo "$dir2" | sed -e "$sed_first"` > if test "$first2" = "$first"; then > dir2=`echo "$dir2" | sed -e "$sed_rest"` > else > dir2="../$dir2" > fi > dir0="$dir0"/"$first" > fi > fi > dir1=`echo "$dir1" | sed -e "$sed_rest"` > done > reldir="$dir2" > } > > Doing it in fewer processes seems possible with something like a single > awk script, although I haven't tried writing one; at any rate, awk would > be more portable than python for the same task. > > But yes, providing this as an alternative mode of coreutils' realpath > instead of scripting it in shell or awk seems like a useful addition - > would you care to submit a patch?
Sure. Should this be added to an existing coreutils' command or add a new command to coreutils? Personally I'd prefer to add a command called relpath. But I'm not sure the standard organization in coreutils. -- Regards, Peng