| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109 |
- package main
-
- import (
- "fmt"
- "strings"
-
- "github.com/traefik/yaegi/interp"
- "github.com/traefik/yaegi/stdlib"
- )
-
- func main() {
-
- calculateSimple("(2+3)*5")
- calculateSimple("15/5")
- // 测试多行代码(使用专门的多行函数)
- code := `x := 10
- if x > 5 {
- return "大于5"
- } else {
- return "小于等于5"
- }`
-
- calculateMultiLine(code)
- // // 获取配置实例
- // cfg := config.GetConfig()
-
- // // 使用配置
- // if cfg.IsDatabaseConfigured() {
- // dbConfig := cfg.GetDatabaseConfig()
- // fmt.Printf("Host: %s\n", dbConfig.Host)
- // fmt.Printf("Port: %d\n", dbConfig.Port)
- // fmt.Printf("Database: %s\n", dbConfig.Database)
- // }
-
- // //authConfig := cfg.GetAuth()
- // //fmt.Printf("token: %s\n", authConfig.Token)
-
- // serviceConfig := cfg.GetServiceConfig()
- // fmt.Printf("ReadTimeout: %d秒\n", serviceConfig.ReadTimeout)
- // fmt.Printf("WriteTimeout: %d秒\n", serviceConfig.WriteTimeout)
- // fmt.Printf("IdleTimeout: %d秒\n", serviceConfig.IdleTimeout)
-
- }
-
- func calculateSimple(expression string) (string, error) {
- i := interp.New(interp.Options{})
- i.Use(stdlib.Symbols)
-
- // 包装成匿名函数立即调用,既简洁又安全
- code := fmt.Sprintf("(func() interface{} { return %s })()", expression)
-
- v, err := i.Eval(code)
- if err != nil {
- fmt.Printf("calculateSimple: err v:%v \n", err)
- return "", err
- }
-
- fmt.Printf("calculateSimple: %s v:%v \n", expression, v)
- return fmt.Sprintf("%v", v), nil
- }
-
- // 专门处理多行代码(if/for/变量声明等)
- func calculateMultiLine(code string) (string, error) {
- i := interp.New(interp.Options{})
- i.Use(stdlib.Symbols)
-
- // 关键:整个代码块作为函数体,最后一行作为返回值
- wrappedCode := fmt.Sprintf(`
- (func() interface{} {
- %s
- })()`, code)
-
- v, err := i.Eval(wrappedCode)
- if err != nil {
- fmt.Printf("calculateMultiLine 错误: %v\n代码: %s\n", err, code)
- return "", err
- }
-
- fmt.Printf("calculateMultiLine 成功: %v\n", v)
- return fmt.Sprintf("%v", v), nil
- }
-
- // 更智能的版本:自动判断使用哪种处理方式
- func calculateAuto(expression string) (string, error) {
- // 如果是纯数学表达式(只有数字和运算符)
- if isPureMath(expression) {
- return calculateSimple(expression)
- }
-
- // 否则当做多行代码处理
- return calculateMultiLine(expression)
- }
-
- func isPureMath(expr string) bool {
- // 移除非空格的空白字符
- cleaned := strings.ReplaceAll(expr, "\n", "")
- cleaned = strings.ReplaceAll(cleaned, "\t", "")
- cleaned = strings.ReplaceAll(cleaned, " ", "")
-
- // 检查是否只包含数字、运算符、括号和小数点
- for _, ch := range cleaned {
- if !((ch >= '0' && ch <= '9') ||
- ch == '+' || ch == '-' || ch == '*' || ch == '/' ||
- ch == '(' || ch == ')' || ch == '.') {
- return false
- }
- }
- return len(cleaned) > 0
- }
|