---- title: XEXPR module – handling XML as scheme s-expressions SPDX-FileCopyrightText: 2024 Norman Gray SPDX-License-Identifier: BSD-2-Clause Scheme s-expressions are a convenient way of wrangling XML, known as x-expressions. The functions in this module will search the content of, and write out, such x-expressions. There are a couple of ways that x-expressions have been defined, in the Scheme world, in the past. I have followed [Racket](https://docs.racket-lang.org/xml/index.html). The following grammar describes expressions that create X-expressions: xexpr = string | (list symbol (list (list symbol string) ...) xexpr ...) | (cons symbol (list xexpr ...)) | symbol | valid-char? | cdata | misc For example: (xexpr-write/xml! '(p "Here is a " (a ((href "http://foo")) "link") " with " (br ((clear "right"))) ". This" amp "that" 33)) produces

Here is a link with
. This&that!

Above, a ‘string’ is literal data, either as a `"string"` or `#[ustring]`. When converted to an XML stream, the characters of the data will be escaped as necessary. A pair represents an element, optionally with attributes. Each attribute’s name is represented by a symbol, and its value is represented by a string. A symbol represents an entity reference. For example, the symbol `'nbsp` represents ` `. These are serialised as such, _unless_ `:expand-entities?` is `#t`, in which case _a subset_ of entities are expanded into the nominated character. It is unspecified just what entities are included in this ‘subset’, but [this list](https://developer.mozilla.org/en-US/docs/Glossary/Entity) is reasonable. A `valid-char?` represents a numeric entity. For example, `#x20` represents ` `. Right now, I don't implement cdata or misc. There is not at present any support for parsing XML into xexprs. Writing ------- The functions [`xexpr-write/md!`](#fn-xexpr-write/md!), [`xexpr-write/python!`](#fn-xexpr-write/python!), [`xexpr-write/sexp!`](#fn-xexpr-write/sexp!), [`xexpr-write/xhtml!`](#fn-xexpr-write/xhtml!), [`xexpr-write/xml!`](#fn-xexpr-write/xml!) will write out an xexpr in one or other format (the function `xexpr-write/xhtml!` is generally the most useful). Examining --------- The function [`xexpr-path-search`](#fn-xexpr-path-search) implements a basic path searcher. Given an xexpr, functions [`xexpr-disassemble`](#fn-xexpr-disassemble), [`xexpr-get-attribute`](#fn-xexpr-get-attribute) and [`xexpr-text`](#fn-xexpr-text) make it convenient to inspect the contents.