I have a bash script that fixes or creates, and syncs the asciidoc attributes and yaml header for blog posts. It does what it is supposed to. But notice I have put sleep
commands in between the sed -i
insert commands. This is because I was getting unusual error messages such as:
sed: -e expression #1, char 40: unknown command: `Y'
But there is no command or any expression containing a Y
in the file. I figured it was perhaps some kind of race condition, and wanted to 'slow' sed
down. This sees to solve the problem but is there a better way to do this?
#!/usr/bin/bash
#Before runing this script ensure the doc has a valid asciidoctor title
#then set the type lang and author defaults
export sectnumlevels=2
export toc="true"
export includedir="include"
[[ -z "1ドル" ]] && { echo "need a file" ; exit 1 ; }
sed -n '/^=\s/q1' "1ドル" && { echo "this looks like it doesn't have a title" ; exit 1 ; }
export file=1ドル
#delete blank lines
sed -i '10,19{/^[[:space:]]*$/d}' "1ドル"-
export title=`sed -n /^\=\ .*/p "1ドル"`-
export author=`awk /author:/{'first = 1ドル; 1ドル=""; print 0ドル'} "1ドル" |sed 's/^ //g'`
export categories=`awk /categories:/{'first = 1ドル; 1ドル=""; print 0ドル'} "1ドル" |sed 's/^ //g'`
export tags=`awk /tags:/{'first = 1ドル; 1ドル=""; print 0ドル'} "1ドル" |sed 's/^ //g'`
[[ -z $author ]] && author="Name AUTHOR"
export date=`awk '/date:/{print 2ドル}' "1ドル" | uniq`-
[[ -z "$date" ]] && date=`date -Im`
export type="post"
export lang="fr"
export draft="true"
[[ -z $categories ]] && categories="[]"
[[ -z $tags ]] && tags="[]"
function yaml {
sed -i '1 i ---' "$file"
sed -i "/^---/a title: $title" "$file"
sed -i "/^title:/a author: $author" "$file"
sed -i "/^author:/a date: $date" "$file"
sed -i "/^date:/a type: $type" "$file"
sed -i "/^type:/a draft: $draft" "$file"
sed -i "/^draft:/a categories: $categories" "$file"
sed -i "/^categories:/a tags: $tags" "$file"
sed -i '/^tags:/a ---' "$file"
#this is the weirdest hack
sed -i '9 a #;' "$file" && sed -i 's/^#;//g' "$file"
}
#call yaml function if no yaml header
sed -r -n '/^---(\s|$)/q1' "1ドル" && yaml-
#but if there is already a header it may be missing stuff
#needs to take care of when the key exists but no value...
sed -n '/^title:\s/q1' "1ドル" && sed -i "/^---/a title: $title" "$file"
sed -n '/^author:\s/q1' "1ドル" && sed -i "/^title:/a author: $author" "$file"
[[ ! $(awk '/^date:/{print 2ドル}' "1ドル") ]] && sed -i "/^author:/a date: $date" "$file"
sed -n '/^type:\s/q1' "1ドル" && sed -i "/^date:/a type: $post" "$file"
#start the asciidoctor attributes
sed -i '/^:author:.*/d' "1ドル" && sed -i "/^=\s/a :author: $author" "1ドル"
#[[ ! $(awk '/^:date:/{print 2ドル}' "1ドル") ]] && sed -i "/^:author:/a :date: $date" "1ドル"
sleep 0.25-
sed -i '/^:date:.*/d' "1ドル" && sed -i "/^:author:/a :date: $date" "1ドル"
sleep 0.25-
sed -i '/^:type:.*/d' "1ドル" && sed -i "/^:date:/a :type: $type" "1ドル"
sleep 0.25-
sed -i '/^:toc:.*/d' "1ドル" && sed -i "/^:type:/a :toc: $toc" "1ドル"-
sleep 0.25-
sed -i '/^:experimental:.*/d' "1ドル" && sed -i '/^:toc:/a :experimental:' "1ドル"-
sleep 0.25-
sed -i '/^:sectnums:.*/d' "1ドル" && sed -i '/^:experimental:/a :sectnums:' "1ドル"
sleep 0.25-
sed -i '/^:sectnumlevels:.*/d' "1ドル" && sed -i "/^:sectnums:/a :sectnumlevels: $sectnumlevels" "1ドル"-
if [ ! $lang = "en" ]; then
sed -n '/^:lang:\s/q1' "1ドル" && sed -i "/^:sectnumlevels:/a :lang: $lang" "1ドル"-
sleep 0.25-
sed -i '/:includedir:.*/d' "1ドル" && sed -i "/^:lang:/i :includedir: content/$lang/$includedir" "1ドル"
sleep 0.25-
sed -i '/include::locale/d' "1ドル" && sed -i '/^:lang:/a include::locale/attributes.adoc[]' "1ドル"-
sleep 0.25-
sed -i "/^include::locale/a #;" "1ドル" && sed -i 's/^#;//g' "1ドル"
fi
1 Answer 1
export sectnumlevels=2 export toc="true" export includedir="include"
It's not clear why any of these need to be exported
[[ -z "1ドル" ]] && { echo "need a file" ; exit 1 ; }
Error messages should go to stderr, not stdout: echo >&2
. And we could use portable shell [
instead of [[
, rather than making the script Bash-specific.
sed -i '1 i ---' "$file" sed -i "/^---/a title: $title" "$file" sed -i "/^title:/a author: $author" "$file" sed -i "/^author:/a date: $date" "$file" sed -i "/^date:/a type: $type" "$file" sed -i "/^type:/a draft: $draft" "$file" sed -i "/^draft:/a categories: $categories" "$file" sed -i "/^categories:/a tags: $tags" "$file" sed -i '/^tags:/a ---' "$file"
It's inefficient to repeatedly open and write $file
. Replace all this with a single sed
program that inserts all of the required lines before line 1.
-
\$\begingroup\$ Ah but the point is there are old posts that may or may not have some or any of those lines. So the script searches for what exists already and inserts what is needed. \$\endgroup\$Boyd– Boyd2021年05月25日 22:54:47 +00:00Commented May 25, 2021 at 22:54
-
\$\begingroup\$ And your test cases verify that it does that correctly? As I commented on the question, you'll get better reviews if you can show some inputs and expected outputs (or better still, your complete test harness). \$\endgroup\$Toby Speight– Toby Speight2021年05月26日 07:16:46 +00:00Commented May 26, 2021 at 7:16
-
added at the end. I assume they are not in your actual script? Could you edit to fix them? \$\endgroup\$