| #!/usr/bin/env bash | |
| # Copyright 2010 The Go Authors. All rights reserved. | |
| # Use of this source code is governed by a BSD-style | |
| # license that can be found in the LICENSE file. | |
| # Using all the non-test *.go files in the named directory, write | |
| # out a file /tmp/$USER.try.go to evaluate the expressions on the | |
| # command line, perhaps to discover a function or method that | |
| # gives the desired results. See usage message. | |
| # Compile the program and run it. | |
| # Makes egrep,grep work better in general if we put them | |
| # in ordinary C mode instead of what the current language is. | |
| unset LANG | |
| export LC_ALL=C | |
| export LC_CTYPE=C | |
| export GOROOT=${GOROOT:-"@@GOROOT@@"} | |
| eval $(gomake -j1 --no-print-directory -f "$GOROOT"/src/Make.inc go-env) | |
| if [ -z "$O" ]; then | |
| echo 'missing $O - maybe no Make.$GOARCH?' 1>&2 | |
| exit 2 | |
| fi | |
| # Allow overrides | |
| GC="${_GC:-$GC} -I _test" | |
| GL="${GL:-$LD} -L _test" | |
| AS="$AS" | |
| CC="$CC" | |
| LD="$LD" | |
| export GC GL O AS CC LD | |
| # Macros for tab and quotes for easier readability. | |
| T=' ' | |
| BQ='`' | |
| SQ="'" | |
| DQ='"' | |
| SD="$SQ$DQ" | |
| DS="$DQ$SQ" | |
| usage="usage: gotry [packagedirectory] expression ... | |
| Given one expression, gotry attempts to evaluate that expression. | |
| Given multiple expressions, gotry treats them as a list of arguments | |
| and result values and attempts to find a function in the package | |
| that, given the first few expressions as arguments, evaluates to | |
| the remaining expressions as results. If the first expression has | |
| methods, it will also search for applicable methods. | |
| If there are multiple expressions, a package directory must be | |
| specified. If there is a package argument, the expressions are | |
| evaluated in an environment that includes | |
| import . ${DQ}packagedirectory${DQ} | |
| Examples: | |
| gotry 3+4 | |
| # evaluates to 7 | |
| gotry strings ${SD}abc${DS} ${SD}c${DS} 7-5 | |
| # finds strings.Index etc. | |
| gotry regexp ${SQ}MustCompile(${DQ}^[0-9]+${DQ})${SQ} ${SD}12345${DS} true | |
| # finds Regexp.MatchString | |
| " | |
| function fail() { | |
| echo 2>&1 "$@" | |
| exit 2 | |
| } | |
| case $# in | |
| 0) | |
| fail "$usage" | |
| ;; | |
| *) | |
| case "$1" in | |
| -*help|-*'?'|'?') | |
| fail "$usage" | |
| esac | |
| if test -d "$GOROOT/src/pkg/$1" | |
| then | |
| pkg=$(basename $1) | |
| dir=$GOROOT/src/pkg/$1 | |
| importdir=$1 | |
| shift | |
| case "$pkg" in | |
| os|syscall) | |
| fail "gotry: cannot try packages os or syscall; they are too dangerous" | |
| esac | |
| fi | |
| ;; | |
| esac | |
| spaces='[ ][ ]*' | |
| function getFunctions() { | |
| if [ "$pkg" = "" ] | |
| then | |
| return | |
| fi | |
| for file in $dir/*.go | |
| do | |
| case $file in | |
| *_test*) | |
| continue | |
| esac | |
| grep "func$spaces[A-Z]" $file | # TODO: should be Unicode upper case | |
| sed "s/func$spaces//;s/(.*//" | |
| done | sort -u | |
| } | |
| # Generate list of public functions. | |
| functions=$(getFunctions) | |
| # Write file to compile | |
| rm -f /tmp/$USER.try.go | |
| ( | |
| cat <<'!' | |
| package main | |
| import ( | |
| "os" | |
| "try" | |
| ! | |
| if [ "$pkg" != "" ] | |
| then | |
| echo "$T" . '"'$importdir'"' | |
| fi | |
| cat <<! | |
| ) | |
| func main() { | |
| try.Main("$pkg", firstArg, functions, args) | |
| } | |
| var functions = map[string] interface{}{ | |
| ! | |
| for i in $functions | |
| do | |
| echo "$T"'"'$i'": '$i',' | |
| done | |
| echo "}" | |
| echo 'var args = []interface{}{' | |
| if [ $# = 1 ] | |
| then | |
| echo "${T}toSlice($1)", | |
| else | |
| for i | |
| do | |
| echo "$T$i", | |
| done | |
| fi | |
| echo "}" | |
| cat <<! | |
| var firstArg = $BQ$1$BQ | |
| var _ os.Error | |
| func toSlice(a ...interface{}) []interface{} { return a } | |
| ! | |
| )>/tmp/$USER.try.go | |
| $GC -o /tmp/$USER.try.$O /tmp/$USER.try.go && | |
| $GL -o /tmp/$USER.try /tmp/$USER.try.$O && | |
| /tmp/$USER.try "_$@" | |
| rm -f /tmp/$USER.try /tmp/$USER.try.go /tmp/$USER.try.$O |