Comments (3)
Indeed, this is a serious problem.
I've thought about it for a while and come up with a re-written, simpler (but more powerful) way to declare and assign parameters. It comes with a new syntax though (two options, comma separated or new line starting with :
), but I'm sure it will be possible to make backwards-compatible aliases.
It looks like this:
# syntax with commas:
function example { args : @required string firstName , string lastName , integer age } {
echo "My name is ${firstName} ${lastName} and I am ${age} years old."
}
# syntax with colons and new lines:
function example {
args
: @required string firstName
: string lastName
: integer age
: string[] ...favoriteHobbies
echo "My name is ${firstName} ${lastName} and I am ${age} years old."
echo "My favorite hobbies include: ${favoriteHobbies[*]}"
}
# normal usage:
example Mark McDonald 32 singing jumping
Try playing around with this snippet and feel free to give me your feedback:
#!/usr/bin/env bash
shopt -s expand_aliases
function echo_stderr {
echo "$*" >&2
}
function assignTrap {
local evalString
local -i paramIndex=${__paramIndex-0}
local initialCommand="${1-}"
if [[ "$initialCommand" != ":" ]]
then
echo "trap - DEBUG; eval \"${__previousTrap}\"; unset __previousTrap; unset __paramIndex;"
return
fi
while [[ "${1-}" == "," || "${1-}" == "${initialCommand}" ]] || [[ "${#@}" -gt 0 && "$paramIndex" -eq 0 ]]
do
shift # first colon ":" or next parameter's comma ","
paramIndex+=1
local -a decorators=()
while [[ "${1-}" == "@"* ]]
do
decorators+=( "$1" )
shift
done
local declaration=
local wrapLeft='"'
local wrapRight='"'
local nextType="$1"
local length=1
case ${nextType} in
string | boolean) declaration="local " ;;
integer) declaration="local -i" ;;
reference) declaration="local -n" ;;
arrayDeclaration) declaration="local -a"; wrapLeft= ; wrapRight= ;;
assocDeclaration) declaration="local -A"; wrapLeft= ; wrapRight= ;;
"string["*"]") declaration="local -a"; length="${nextType//[a-z\[\]]}" ;;
"integer["*"]") declaration="local -ai"; length="${nextType//[a-z\[\]]}" ;;
esac
if [[ "${declaration}" != "" ]]
then
shift
local nextName="$1"
local handleless=
for decorator in "${decorators[@]}"
do
case ${decorator} in
@readonly) declaration+="r" ;;
@required) evalString+="[[ ! -z \$${paramIndex} ]] || echo_stderr \"Parameter '$nextName' ($nextType) is marked as required by '${FUNCNAME[1]}' function.\"; " ;;
@handleless) handleless=1 ;;
@global) declaration+="g" ;;
esac
done
local paramRange="$paramIndex"
if [[ -z "$length" ]]
then
# ...rest
paramRange="{@:$paramIndex}"
# trim leading ...
nextName="${nextName//\./}"
if [[ "${#@}" -gt 1 ]]
then
echo_stderr "Unexpected arguments after a rest array ($nextName) in '${FUNCNAME[1]}' function."
fi
elif [[ "$length" -gt 1 ]]
then
paramRange="{@:$paramIndex:$length}"
paramIndex+=$((length - 1))
fi
evalString+="${declaration} ${nextName}=${wrapLeft}\$${paramRange}${wrapRight}; "
# if [[ "$handleless" != 1 ]]
# then
# evalString+="Type::CreateHandlerFunction \"$nextName\"; "
# fi
# continue to the next param:
shift
fi
done
# echo_stderr "evaling $evalString"
echo "${evalString} local -i __paramIndex=${paramIndex};"
}
alias args='local __previousTrap=$(trap -p DEBUG); trap "eval \"\$(assignTrap \$BASH_COMMAND)\";" DEBUG;'
# syntax with commas:
function example { args : @required string firstName , string lastName , integer age } {
echo "My name is ${firstName} ${lastName} and I am ${age} years old."
}
# syntax with colons and new lines:
function example {
args
: @required string firstName
: string lastName
: integer age
: string[] ...favoriteHobbies
echo "My name is ${firstName} ${lastName} and I am ${age} years old."
echo "My favorite hobbies include: ${favoriteHobbies[*]}"
}
example Mark McDonald 32 singing jumping
from bash-oo-framework.
alias args='local __previousTrap=$(trap -p DEBUG); trap "eval "$(assignTrap $BASH_COMMAND)";" DEBUG;'
This line missing from the current version had me spending 3 hours of going through thousands of set -x
output lines. 😛 .
There is also the issue of the functrace
option being set which might break things (it does in the current version and I think it will cause problems here as well when local __previousTrap=$(trap -p DEBUG);
gets run a second time, ie when a second argument is being evaluated).
I find this implementation to be awesome! I cannot decide if I like the new syntax more or not. I would still like to explore the possibility of having the old aliases work.
My only objection is the comma syntax. I think it breaks the bash function "signature", ie instead of
[function] func_name[()] {.*}
we now have:
[function] func_name[()] {.*}{.*}
This might break existing tools that rely on the first "signature" to scan the code and identify function definitions, etc.
from bash-oo-framework.
Thanks for the feedback!
I think old aliases could be ported - I was thinking how to do it and it shouldn't be too hard to add.
As for the comma signature, it shouldn't break. Here's why: the second }
and {
are really just arguments passed to the first command (args
), formatted on the same line as the opening brace {
.
function example {
args : @required string firstName , string lastName , integer age } {
echo "My name is ${firstName} ${lastName} and I am ${age} years old."
}
The curly braces really just there as a decoration, as they're ignored by assignTrap
.
At least when I've tried with shellcheck, it worked.
No idea about how it might work with functrace
-- worth checking. There's probably a way to workaround any problems, too.
from bash-oo-framework.
Related Issues (20)
- Is the project dead? HOT 3
- Sorry, a bit cheeky/impolite... HOT 2
- error handling with throw / command_not_found_handle HOT 3
- Unbound variables cause a crash when running examples with 'set -u' HOT 3
- [bug?] `throw` is said to be 'undefined command' when `import` fail HOT 5
- Catch exception from Classes doesn't work HOT 7
- Inconsistent array assignments HOT 3
- Translating README into Japanese
- for people who want to use Bpkg to install this framework HOT 1
- example/trycatch.sh doesn't work as expected
- Make wiki page
- [Question] Does value of '__primitive_extension_fingerprint' have special meaning?
- update readme instructions for namedParameters
- util/exception.sh shows stack trace as expected but don't exit on Ctrl+C HOT 2
- False boolean not working HOT 1
- Referring this in Human example class doesn't work as described HOT 1
- Exception messages are invisible in light theme mode in Shell console.
- [Question] Is this project still alive? HOT 6
- [Discussion] Log API
- Using a variable for an Object name
Recommend Projects
-
React
A declarative, efficient, and flexible JavaScript library for building user interfaces.
-
Vue.js
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
-
Typescript
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
-
TensorFlow
An Open Source Machine Learning Framework for Everyone
-
Django
The Web framework for perfectionists with deadlines.
-
Laravel
A PHP framework for web artisans
-
D3
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
-
Recommend Topics
-
javascript
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
-
web
Some thing interesting about web. New door for the world.
-
server
A server is a program made to process requests and deliver data to clients.
-
Machine learning
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
-
Visualization
Some thing interesting about visualization, use data art
-
Game
Some thing interesting about game, make everyone happy.
Recommend Org
-
Facebook
We are working to build community through open source technology. NB: members must have two-factor auth.
-
Microsoft
Open source projects and samples from Microsoft.
-
Google
Google ❤️ Open Source for everyone.
-
Alibaba
Alibaba Open Source for everyone
-
D3
Data-Driven Documents codes.
-
Tencent
China tencent open source team.
from bash-oo-framework.