Vim as XML Editor: Setup

Again, this is just one way of setting things up. TMTOWTDI ;) Your local environment is likely to be different, as well as your preferences, and the tools evolve. I'll give a short overview of what I use; please refer to the documentation of the respective tool for instructions on how to best set things up.

If you experience problems with any of the tools featured below please file bug reports directly to the respective project.

General

Linux

Here's my .bashrc:

~/.bashrc


set -o vi
export EDITOR='/usr/bin/vim'

PATH="${HOME}/data/commands:${PATH}"
export PATH

PS1='\u \w \$ '

XML_CATALOG_FILES="${HOME}/data/conf/xml/catalog /etc/xml/catalog"
export XML_CATALOG_FILES

Often it helps to do source .bashrc after having modified .bashrc and after having created new command scripts.

Windows

When creating batch files on Windows (file name suffix .bat) don't forget to make sure that the file format is set correctly. You can check it with :set fileformat? and set it with :set fileformat=dos.

vimrc

The vimrc file is the place where you set your preferences. Here's mine:

vimrc


" Windows:  $VIM/_vimrc (original)
" *n*x   :  ~/.vimrc
" www.pinkjuice.com/vim/vimrc.txt

" for more info check
" www.pinkjuice.com/vim/
" regarding XML related stuff check
" www.pinkjuice.com/howto/vimxml/
" email: tobiasreif pinkjuice com

" The following works for me with Vim 6.2 on Windows
" (most stuff also works on Linux),
" but I don't recommend to blindly copy and use it.
" (check the respective documentation)

""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
" general

set nocompatible

highlight Normal guifg=Black guibg=#ffefd5

set formatoptions=t
set textwidth=70
set encoding=utf-8
set termencoding=latin1
set fileformat=unix
"set guifont=courier_new:h10
set guifont=Courier\ New:h10,Courier,Lucida\ Console,Letter\ Gothic,
 \Arial\ Alternative,Bitstream\ Vera\ Sans\ Mono,OCR\ A\ Extended
set nowrap
set shiftwidth=2
set visualbell
set noerrorbells
set number
set autoindent
set ruler
set expandtab
set whichwrap=<,>,h,l
set guioptions=bgmrL
set backspace=2
set history=50
set backup
set wildmenu
set nrformats=
set foldlevelstart=99
if has("unix")
  set shcf=-ic
endif

let mapleader = ","
let $ADDED = '~/.vim/added/'
if has("win32")
  let $ADDED = $VIM.'/added/'
endif

map <Leader>cd :exe 'cd ' . expand ("%:p:h")<CR>
nmap <F1> :w<CR>
imap <F1> <ESC>:w<CR>a
map <F8> gg"+yG

""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
" Installed

" www.vim.org/scripts/script.php?script_id=301
" $ADDED/xml.vim

" www.vim.org/scripts/script.php?script_id=39
" copied macros/matchit.vim to plugin/

""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
" XML

map <Leader>x :set filetype=xml<CR>
  \:source $VIMRUNTIME/syntax/xml.vim<CR>
  \:set foldmethod=syntax<CR>
  \:source $VIMRUNTIME/syntax/syntax.vim<CR>
  \:colors peachpuff<CR>
  \:source $ADDED/xml.vim<CR>
  \:iunmap <buffer> <Leader>.<CR>
  \:iunmap <buffer> <Leader>><CR>
  \:inoremap \> ><CR>
  \:echo "XML mode is on"<CR>
  " no imaps for <Leader>
  "\:inoremap \. ><CR>

" catalog should be set up
nmap <Leader>l <Leader>cd:%w !xmllint --valid --noout -<CR>
nmap <Leader>r <Leader>cd:%w !rxp -V -N -s -x<CR>
nmap <Leader>d4 :%w !xmllint --dtdvalid 
 \ "http://www.oasis-open.org/docbook/xml/4.2/docbookx.dtd"
 \ --noout -<CR>

vmap <Leader>px !xmllint --format -<CR>
nmap <Leader>px !!xmllint --format -<CR>
nmap <Leader>pxa :%!xmllint --format -<CR>

nmap <Leader>i :%!xsltlint<CR>

" todo:
" check
" http://mugca.its.monash.edu.au/~djkea2/vim/compiler/xmllint.vim

""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
" Ruby

" check
" www.rubygarden.org/ruby?VimExtensions
The latest version is online at www.pinkjuice.com/vim/vimrc.txt.
For example there is
let mapleader = ","
and
nmap <Leader>l <Leader>cd:%w !xmllint --valid --noout -<CR>
which means that whenever I want xmllint to validate the buffer I do , l.

matchit.vim

Jump around the buffer with %, eg between opening and closing angle brackets of XML tags and between opening and closing tags when XML syntax recognition is turned on.

home

www.vim.org/scripts/script.php?script_id=39

For installation instructions enter :help add-local-help. If I remember correctly I simply copied macros/matchit.vim to plugin/ (.vim/plugin/ on Linux).

xmledit

Devin Weaver's xmledit provides some editing features such as closing and deleting tags, and wrapping strings in tag pairs.

Home

www.vim.org/scripts/script.php?script_id=301

Manual

tritarget.com/vim/xml-plugin/doc/xml-plugin.txt (may be outdated, check the above home page)

I don't want it to be turned on automatically, so I created a directory added/. In my vimrc I have
let $ADDED = '~/.vim/added/'
if has("win32")
  let $ADDED = $VIM.'/added/'
endif
and
map <Leader>x :set filetype=xml<CR>
  \:source $VIMRUNTIME/syntax/xml.vim<CR>
  \:set foldmethod=syntax<CR>
  \:source $VIMRUNTIME/syntax/syntax.vim<CR>
  \:colors peachpuff<CR>
  \:source $ADDED/xml.vim<CR>
so I can turn on XML editing mode whenever I want. I don't want it to be turned on automatically because
  • when I open a large file it would slow down editing
  • sometimes I have files with mixed syntax (eg XML snippets in a text file)
  • I prefer to be independent from filename suffixes
When the buffer grows large and changes become slow, try :syn off.

Catalogs

When validating an XML document which references an online DTD in it's doctype declaration,
<!DOCTYPE html
  PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
  "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
this DTD needs to get loaded. Normally it gets downloaded from the web, which can take a while with large schemas such as DocBook. Changing the URL to a local path each time is tedious, especially if there are many documents.

Convenient and fast offline validation can be achieved though setting up a catalog system. When using xmllint, this means nothing more than creating a simple catalog file, and making its path available to xmllint.

A catalog lists the FPIs of document types such as SVG, XHTML, and DBX, and says where to find the corresponding DTDs locally. In the OASIS XML Catalog language, a simple entry looks like this:
<public
  publicId="-//W3C//DTD XHTML 1.0 Strict//EN"
  uri="xhtml/1_0/strict/dtd/xhtml1-strict.dtd"/>
Any XML tool which supports OASIS XML Catalogs (OASIS Catalogs specification) can now see if there is a local copy of the corresponding DTD available. It simply grabs the FPI from the document, and looks it up in the catalog.
OASIS catalogs can also be used to map system identifiers to local paths:
<system
  systemId="http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"
  uri="xhtml/1_0/strict/dtd/xhtml1-strict.dtd"/>
This is useful in cases where there is no FPI available.
The typical location and name for an OASIS XML catalog is /etc/xml/catalog. On Linux I don't edit /etc/xml/catalog because various various installers write to that file. Instead I place my catalog under my home directory so that it doesn't get modified by any automatic process. Tools like rxp, xmllint, and xsltproc support multiple catalogs. In my .bashrc I have
XML_CATALOG_FILES="${HOME}/data/conf/xml/catalog /etc/xml/catalog"
export XML_CATALOG_FILES
and my catalog looks like this:

~/data/conf/xml/catalog

<?xml version="1.0"?>
<!DOCTYPE catalog
PUBLIC "-//OASIS//DTD Entity Resolution XML Catalog V1.0//EN"
"http://www.oasis-open.org/committees/entity/release/1.0/catalog.dtd">
<catalog
xmlns="urn:oasis:names:tc:entity:xmlns:xml:catalog">

<group
prefer="public"
xml:base="file:///home/tobi/bulk/xml/schemas/">
  
<public
publicId="-//OASIS//DTD Entity Resolution XML Catalog V1.0//EN"
uri="oasis_catalogs/1_0/dtd/catalog.dtd"/>
<system
systemId=
"http://www.oasis-open.org/committees/entity/release/1.0/catalog.dtd"
uri="oasis_catalogs/1_0/dtd/catalog.dtd"/>

<public
publicId="-//W3C//DTD XHTML 1.0 Strict//EN"
uri="xhtml/1_0/strict/dtd/xhtml1-strict.dtd"/>
<system
systemId="http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"
uri="xhtml/1_0/strict/dtd/xhtml1-strict.dtd"/>

<public
publicId="-//OASIS//DTD DocBook XML V4.2//EN"
uri="docbook/4_2/dtd/docbookx.dtd"/>
<system
systemId="http://www.oasis-open.org/docbook/xml/4.2/docbookx.dtd"
uri="docbook/4_2/dtd/docbookx.dtd"/>

<public
publicId="-//W3C//DTD SVG 1.0//EN"
uri="svg/1_0/dtd/svg10.dtd"/>
<system
systemId="http://www.w3.org/TR/SVG10/DTD/svg10.dtd"
uri="svg/1_0/dtd/svg10.dtd"/>
<system
systemId="http://www.w3.org/TR/2001/REC-SVG-20010904/DTD/svg10.dtd"
uri="svg/1_0/dtd/svg10.dtd"/>

<public
publicId="-//W3C//DTD SVG 1.1//EN"
uri="svg/1_1/dtd/svg11-flat.dtd"/>
<system
systemId="http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"
uri="svg/1_1/dtd/svg11-flat.dtd"/>
<system
systemId="http://www.w3.org/Graphics/SVG/1.1/DTD/svg11-flat.dtd"
uri="svg/1_1/dtd/svg11-flat.dtd"/>

</group>

<public
publicId="-//Pinkjuice//DTD link-tree 0.1//EN"
uri="../../../public_html/pj/svg/links/link-tree_0_1.dtd"/>
<system
systemId="http://www.pinkjuice.com/svg/links/link-tree_0_1.dtd"
uri="../../../public_html/pj/svg/links/link-tree_0_1.dtd"/>

<system
systemId="http://www.example.org/tobias/reif/contacts.dtd"
uri="../../xml/schemas/contacts/dtd/contacts.dtd"/>

</catalog>
My catalog is not only used by xmllint, but also by the resolvers of some other tools such as validators and XSLT processors.

xmllint

xmllint is part of libxml, the XML C library for GNOME. It's lightning fast and can be used for validation and pretty printing.

home

xmlsoft.org/xmldtd.html

man

www.xmlsoft.org/xmllint.html

On Linux

Most of the following should work analogously on other Unix-like OSs such as BSD.

If you are on Linux xmllint might already be installed on your system. To make sure you have the latest version check
$ xmllint --version
and xmlsoft.org/downloads.html. In order to not risk any conflicts I installed the latest versions under my home directory using the following shell script:

install_libxml

#!/bin/bash -x
# or
#!/usr/bin/env bash

# todo:
#
# refactor, wrap a lot of redundant code in functions
#
# pass --disable-shared to configure?
# or --enable-static, or both? do
# tobi ~/del $ grep AttributeError \
# libxml_cvs_installation.log | wc -l

# this is just an example you could use as basis for your script
# (do not run it without having revised and adjusted it)

# usage: (be online)
# (remove existing identical/redundant commands and logs,
# and empty compilation, (download,) and run directories)
# if not CVS then set versions below
# [as user do:]
# $ cd del
# $ ~/data/run/install_libxml --cvs \
# 2>&1 | tee libxml_cvs_installation.log
# (or &> libxml_cvs_installation.log ?)
# (then run without [...]cvs:
# $ ~/data/run/install_libxml 2>&1 | tee libxml_installation.log
# )
# optionally monitor with lines like
# $ tail -f \
# ~/del/compile_libxml/libxml2-2.6.9/my_xml_make_errors.log

# if the installation succeeded,
# set latest stable versions as defaults
# cd
# cp -i data/commands/xmllint_2.6.9 data/commands/xmllint
# cp -i data/commands/xsltproc_1.1.6 data/commands/xsltproc
# [not necessarily required:]
# source .bashrc
# xmllint --version
# xsltproc --version

# this script is install_libxml
# based on
# http://xmlstar.sourceforge.net/doc/run-xmlstarlet-build
# (any errors are mine :)
# Various lines were contributed by William M. Brack; thanks!

# zlib-devel should be available among other things,
# see libxml2-[version]/INSTALL

my_home=/home/tobi
if [ $HOME != $my_home ]; then
  exit
fi
if [ `whoami` != 'tobi' ]; then
  exit
fi

cd ${HOME}/del

case $# in
  0) ;;
  *)
  for a do
    case $a in
      -c|--cvs)
      cvs=true;;
      *)
      echo "unexpected arg $a"
      exit;;
    esac
  done
esac

# set:
# check for latest versions at ftp://xmlsoft.org/
if [ $cvs ]; then
  ver_libxml='cvs'
  ver_libxslt='cvs'
else
  ver_libxml=2.6.9
  ver_libxslt=1.1.6
fi

uname -a
tools="
  gcc
  make
  automake
  install
"
for tool in $tools ; do
  $tool --version
done
/lib/ld-linux.so.2 /lib/libc.so.6 | head -1

# does it make any sense to scan the files?
av_command="antivir -rs -z"

compile=${HOME}/del/compile_libxml

run_libxml_top=${HOME}/bulk/run/libxml
run_libxml=${run_libxml_top}/${ver_libxml}
run_libxslt_top=${HOME}/bulk/run/libxslt
run_libxslt=${run_libxslt_top}/${ver_libxslt}

if [ ! -d $compile ]; then
  mkdir $compile
fi

if [ ! -d $compile/download ]; then
  mkdir ${compile}/download
fi

if [ -d $run_libxml ]; then
  echo ${run_libxml}' exists, exiting'
  exit
else
  if [ ! -d $run_libxml_top ]; then
    mkdir $run_libxml_top
  fi
  if [ ! -d $run_libxml ]; then
    mkdir $run_libxml
  fi
fi

if [ -d $run_libxslt ]; then
  echo ${run_libxslt}' exists, exiting'
  exit
else
  if [ ! -d $run_libxslt_top ]; then
    mkdir $run_libxslt_top
  fi
  if [ ! -d $run_libxslt ]; then
    mkdir $run_libxslt
  fi
fi

cd $compile

if [ $cvs ]; then
  url_libxml='ftp://xmlsoft.org/libxml2-cvs-snapshot.tar.gz'
  url_libxslt='ftp://xmlsoft.org/libxslt-cvs-snapshot.tar.gz'
else
  url_libxml="ftp://xmlsoft.org/libxml2-${ver_libxml}.tar.gz"
  url_libxslt="ftp://xmlsoft.org/libxslt-${ver_libxslt}.tar.gz"
fi
file_libxml=`basename ${url_libxml}`
file_libxslt=`basename ${url_libxslt}`

if [ ! -f download/$file_libxml ]; then
  cd download
  wget $url_libxml
  # should: exit if download didn't succeed
  if [ ! -e  $file_libxml ]; then
    exit
  fi
  $av_command $file_libxml
  if [ $? != 0 ]; then
    exit
  fi
  cd ../
fi

if [ ! -f download/$file_libxslt ]; then
  cd download
  wget $url_libxslt
  # should: exit if download didn't succeed
  if [ ! -e  $file_libxslt ]; then
    exit
  fi
  $av_command $file_libxslt
  if [ $? != 0 ]; then
    exit
  fi
  cd ../
fi

libxml2_cvs_dir_name=libxml2-cvs
libxslt_cvs_dir_name=libxslt-cvs

if [ $cvs ]; then

  mkdir $libxml2_cvs_dir_name && cd $libxml2_cvs_dir_name
  tar -xzf ../download/${file_libxml}
  cd ../
  # toplevel_xml_dir="${compile}/${libxml2_cvs_dir_name}/*/"
  toplevel_xml_dir_parent="${compile}/${libxml2_cvs_dir_name}"
  toplevel_xml_dir="${toplevel_xml_dir_parent}/$(ls $toplevel_xml_dir_parent)"

  mkdir $libxslt_cvs_dir_name && cd $libxslt_cvs_dir_name
  tar -xzf ../download/${file_libxslt}
  cd ../
  # toplevel_xslt_dir="${compile}/${libxslt_cvs_dir_name}/*/"
  toplevel_xslt_dir_parent="${compile}/${libxslt_cvs_dir_name}"
  toplevel_xslt_dir="${toplevel_xslt_dir_parent}/$(ls $toplevel_xslt_dir_parent)"

else

  toplevel_xml_dir="${compile}/libxml2-${ver_libxml}"
  toplevel_xslt_dir="${compile}/libxslt-${ver_libxslt}"
  tar -xzf download/${file_libxml}
  tar -xzf download/${file_libxslt}

fi

if [ $cvs ]; then
  # configure='autogen.sh'
  configure='configure'
  # --enable-static --disable-shared ?
else
  configure='configure'
  # --enable-static --disable-shared ?
fi

cd $toplevel_xml_dir
if [ $cvs ] && [ -f Makefile ]; then
  make distclean
fi
./${configure} --prefix=${run_libxml} \
  2>&1 | tee my_xml_config.log
# make CFLAGS="-g -O2 -static" \
make \
  2>my_xml_make_errors.log | tee my_xml_make.log
make tests 2>&1 | tee my_xml_tests.log
make install

cd $toplevel_xslt_dir
if [ $cvs ] && [ -f Makefile ]; then
  make distclean
fi
./${configure} --prefix=${run_libxslt} \
  --with-libxml-src=${toplevel_xml_dir} \
  2>&1 | tee my_xslt_config.log
# make CFLAGS="-g -O2 -static" \
make \
  2>my_xslt_make_errors.log | tee my_xslt_make.log
make tests 2>&1 | tee my_xslt_tests.log
make install

command_xmllint=${HOME}/data/commands/xmllint_${ver_libxml}
command_xsltproc=${HOME}/data/commands/xsltproc_${ver_libxslt}

if [ ! -f $command_xmllint ]; then
  cat > $command_xmllint << EOF
#!/usr/bin/env sh
# may get overwritten
${run_libxml}/bin/xmllint "\$@"
EOF
  chmod 700 $command_xmllint
  $command_xmllint --version
fi

if [ ! -f $command_xsltproc ]; then
  cat > $command_xsltproc << EOF
#!/usr/bin/env sh
# may get overwritten
${run_libxslt}/bin/xsltproc "\$@"
EOF
  chmod 700 $command_xsltproc
  $command_xsltproc --version
fi

# email my_*.log files?
# below tgz plus
# del/libxml_cvs_installation.log
# and this script

cd $compile
tar -czf tobilogs${ver_libxml}.tgz \
   -C $toplevel_xml_dir \
     my_xml_config.log my_xml_make.log \
     my_xml_make_errors.log my_xml_tests.log \
   -C $toplevel_xslt_dir \
     my_xslt_config.log my_xslt_make.log \
     my_xslt_make_errors.log my_xslt_tests.log
It's always a good idea to store all schemas that you use locally.
If there is no catalog set up and you need to get started quickly you can validate Vim buffers with commands like this:
:%w !xmllint --noout --dtdvalid /path/to/xhtml1-strict.dtd -
As long as most documents specify their language via doctype declarations it makes sense to set up an OASIS catalog for validation. Most often I put my tool call scripts in ~/data/commands/ but you can use any directory.
$ echo $PATH
might already include ~/bin/ so if you don't want to add a new directory to the system path you can put your calls into /your/home/bin/.
You can set XML_CATALOG_FILES in the rc file of your shell or in a shell script calling xmllint. Here's an example:

~/bin/xmlval

#!/usr/bin/env bash
XML_CATALOG_FILES=/path/to/catalog
export XML_CATALOG_FILES
xmllint --valid --noout "$@"
$ chmod 700 ~/bin/xmlval
If you are in a bash shell,
$ xmlval --version
should return the version of xmllint.
If you get "command not found" when trying to call xmlval you need to ask the shell to search the path again. If
$ echo $SHELL
returns csh or tcsh you can try
$ set path=($path)
and test it with
$ xmlval --version
Now you should be able to use
:%w !xmlval -
to validate documents which have doctype declarations.
Another way is to use xmllint directly, and set the environment variable XML_CATALOG_FILES in the rc file of the shell.
If you use csh or tcsh do
$ vim .cshrc
then append
setenv XML_CATALOG_FILES "/path/to/catalog"
and do
$ source .cshrc
Now
:%w !xmllint --valid --noout -
should work fast and offline if there's a doctype declaration and if the catalog contains a link to a corresponding schema.
If you use bash you can append these lines to your .bashrc:
XML_CATALOG_FILES="/path/to/catalog"
export XML_CATALOG_FILES
then do
$ source .bashrc
and test it with
$ echo $XML_CATALOG_FILES
To validate documents which have a doctype declaration do
:%w !xmllint --valid --noout -
in Vim.

On Windows

Follow the installation instructions on www.zlatkovic.com/libxml.en.html, or try the following:
After having downloaded and unzipped libxml2-version.win32.zip from ftp://ftp.zlatkovic.com/pub/libxml/ (otherwise check xmlsoft.org/sources/win32/), create the following batch file calling xmllint and put it in a directory which you added to the system path; mine is called calls\ and I use it for most tools.

xmllint.bat

@echo off
set XML_CATALOG_FILES=/path/to/catalog
"\path\to\libxml2-version.win32\bin\xmllint" %1 %2 %3 %4 %5
On Win9*-systems you might encounter an error message related to insufficient memory. In this case try increasing the available memory: rename xmllint.bat to xmllint_raw.bat and create the following batch file:

xmllint.bat (Windows 95/98/ME)

@echo off
command.com /e:3000 /c xmllint_raw %1 %2 %3 %4 %5
On NT-based Windows versions such as Windows 2000 the prefix to explicitly pass the command to the shell would be
cmd.exe /c
but it shouldn't be necessary.
Alternatively you could add libxml2-version.win32\bin\ to the system path but you'd have to restart Windows, and if you do this for all the directories of the tools the path can get too long. I don't recommend putting the files into Windows directories such as C:\WINDOWS\ since this can cause conflicts.
To see if it works, try some commands which call xmllint from Vim's command line and ask it to validate some XML. Below are some tiny skeletons you can use. SVG:
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg
  PUBLIC "-//W3C//DTD SVG 1.0//EN"
  "http://www.w3.org/TR/SVG/DTD/svg10.dtd">
<svg>
</svg>
On pinkjuice.com there is a more complete SVG skeleton. XHTML:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE html
  PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
  "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html
  xmlns="http://www.w3.org/1999/xhtml"
  xml:lang="en" lang="en">
  <head>
    <title></title>
  </head>
  <body>
    <h1></h1>
    <div>
    </div>
  </body>
</html>
The following command for example passes the path of the file to xmllint:
:!xmllint --valid --noout %
The --valid option tells xmllint to validate the doc, and the other arguments should be self-explanatory.

Find more command examples in chapter Tasks.

RXP

You can never have enough validators :) The error messages vary in usefulness, and some errors aren't caught when using only one validator. RXP is developed by Richard Tobin who is one of the editors of Namespaces in XML 1.1.

home

www.cogsci.ed.ac.uk/~richard/rxp.html

download

ftp://ftp.cogsci.ed.ac.uk/pub/richard/

man

ftp://ftp.cogsci.ed.ac.uk/pub/richard/rxp.txt

On Linux

Following is how I installed RXP on Linux. The output of make and wget is omitted.
$ cd del
$ mkdir compile_rxp && cd compile_rxp
$ wget ftp://ftp.cogsci.ed.ac.uk/pub/richard/rxp-1.4.0pre10.tar.gz
$ tar xzf rxp-1.4.0pre10.tar.gz
$ cd rxp-1.4.0pre10
$ make
$ mkdir ~/bulk/run/rxp
$ mkdir ~/bulk/run/rxp/1_4_0_pre_10
$ ls | egrep "^[^\.]+$" | \
> xargs cp --target-directory=$HOME/bulk/run/rxp/1_4_0_pre_10
$ ed
a
#!/usr/bin/env sh
${HOME}/bulk/run/rxp/1_4_0_pre_10/rxp "$@"
.
w /home/tobi/data/commands/rxp
61
q
$ chmod 700 ~/data/commands/rxp
$ source ~/.bashrc
$ rxp -v
RXP 1.4.0pre10 Copyright Richard Tobin,
LTG, HCRC, University of Edinburgh
<foo   />
Input encoding UTF-8, output encoding UTF-8
<foo/>
$
If you follow the steps, don't type the > after the line ending with \, and type [ctrl-d] to end input to the rxp -v command.

On Windows

On NT-based Windows versions the following batch file should work:

rxp.bat

@echo off
set XML_CATALOG_FILES=file:///drive:/path/to/catalog
\path\to\rxpversion.exe %1 %2 %3 %4 %5 %6 %7 %8 %9
Put it in a directory which is on the system's path.
On Windows ME/9* you might see an error message related to limited memory. The following batch files should solve this:

rxp_raw.bat (Win9*)

@echo off
set XML_CATALOG_FILES=file:///drive:/path/to/catalog
\path\to\rxpversion.exe %1 %2 %3 %4 %5 %6 %7 %8 %9

rxp.bat (Win9*)

@echo off
command.com /e:3000 /c rxp_raw %1 %2 %3 %4 %5 %6 %7 %8 %9
In order to shorten command lines you can add

rxpval.bat

@echo off
rxp -V -N -s -x %1 %2 %3 %4 %5 %6 %7 %8 %9