Add a script to dump an AST using docker.
All checks were successful
rust-test Build rust-test has succeeded
clippy Build clippy has succeeded
rustfmt Build rustfmt has succeeded
rust-foreign-document-test Build rust-foreign-document-test has succeeded
rust-build Build rust-build has succeeded

This commit is contained in:
Tom Alexander 2023-10-18 15:33:01 -04:00
parent f19d262825
commit c58b0e7c35
Signed by: talexander
GPG Key ID: D3A179C9A53C0EDE
2 changed files with 81 additions and 2 deletions

58
scripts/dump_ast.bash Executable file
View File

@ -0,0 +1,58 @@
#!/usr/bin/env bash
#
# Dump the AST of an org-mode document from emacs
set -euo pipefail
IFS=$'\n\t'
DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )"
REALPATH=$(command -v uu-realpath || command -v realpath)
MAKE=$(command -v gmake || command -v make)
############## Setup #########################
function die {
local status_code="$1"
shift
(>&2 echo "${@}")
exit "$status_code"
}
function log {
(>&2 echo "${@}")
}
############## Program #########################
function main {
if [ $# -eq 0 ]; then
dump_ast_stdin "${@}"
else
dump_ast_file "${@}"
fi
}
function dump_ast_stdin {
# Until we can find a good way to encode stdin as an elisp string in bash, I cannot operate on stdin.
die 1 "This script only works on files."
}
function dump_ast_file {
local target_file mounted_file elisp_script
target_file=$($REALPATH "$1")
mounted_file="/input${target_file}"
elisp_script=$(cat <<EOF
(progn
(erase-buffer)
(require 'org)
(defun org-table-align () t)
(find-file-read-only "${mounted_file}")
(org-mode)
(message "%s" (pp-to-string (org-element-parse-buffer)))
)
EOF
)
exec docker run --init --rm -i --mount type=tmpfs,destination=/tmp -v "/:/input:ro" --entrypoint "" organic-test emacs -q --no-site-file --no-splash --batch --eval "$elisp_script"
}
main "${@}"

View File

@ -2,7 +2,7 @@ use std::borrow::Cow;
/// Removes all whitespace from a string if any line breaks are present. /// Removes all whitespace from a string if any line breaks are present.
/// ///
/// Example: "foo bar" => "foo bar" but "foo \n bar" => "foobar". /// Example: "foo bar" => "foo bar" but "foo \n bar" => "foobar".
pub(crate) fn remove_whitespace_if_line_break(input: &str) -> Cow<'_, str> { pub(crate) fn remove_whitespace_if_line_break(input: &str) -> Cow<'_, str> {
let mut state = RemoveWhitespaceIfLineBreakState::Normal; let mut state = RemoveWhitespaceIfLineBreakState::Normal;
for (offset, c) in input.char_indices() { for (offset, c) in input.char_indices() {
@ -78,7 +78,7 @@ enum RemoveLineBreakState {
/// Removes all whitespace from a string if any line breaks are present. /// Removes all whitespace from a string if any line breaks are present.
/// ///
/// Example: "foo bar" => "foo bar" but "foo \n bar" => "foobar". /// Example: "foo bar" => "foo bar" but "foo \n bar" => "foo bar".
pub(crate) fn coalesce_whitespace_if_line_break(input: &str) -> Cow<'_, str> { pub(crate) fn coalesce_whitespace_if_line_break(input: &str) -> Cow<'_, str> {
let mut state = CoalesceWhitespaceIfLineBreakState::Normal; let mut state = CoalesceWhitespaceIfLineBreakState::Normal;
for (offset, c) in input.char_indices() { for (offset, c) in input.char_indices() {
@ -515,4 +515,25 @@ mod tests {
assert!(matches!(output, Cow::Borrowed(_))); assert!(matches!(output, Cow::Borrowed(_)));
Ok(()) Ok(())
} }
#[test]
fn test_coalesce_whitespace_if_line_break() -> Result<(), Box<dyn std::error::Error>> {
assert_eq!(coalesce_whitespace_if_line_break("foo bar"), "foo bar");
assert_eq!(coalesce_whitespace_if_line_break("foo \n bar"), "foo bar");
Ok(())
}
#[test]
fn test_remove_whitespace_if_line_break() -> Result<(), Box<dyn std::error::Error>> {
assert_eq!(remove_whitespace_if_line_break("foo bar"), "foo bar");
assert_eq!(remove_whitespace_if_line_break("foo \n bar"), "foobar");
Ok(())
}
#[test]
fn test_remove_line_break() -> Result<(), Box<dyn std::error::Error>> {
assert_eq!(remove_line_break("foo bar"), "foo bar");
assert_eq!(remove_line_break("foo \n bar"), "foo bar");
Ok(())
}
} }