|
1 | | -# Expr [](https://travis-ci.org/antonmedv/expr) [](https://goreportcard.com/report/github.com/antonmedv/expr) [](https://scrutinizer-ci.com/g/antonmedv/expr/?branch=master) <a href="https://stars.medv.io/antonmedv/expr"><img src="https://stars.medv.io/antonmedv/expr.svg" alt="Sparkline" height="24"></a> |
2 | 1 |
|
3 | | -Expr is an engine that can evaluate expressions. |
4 | | - |
5 | | -The purpose of the package is to allow users to use expressions inside configuration for more complex logic. |
6 | | -It is a perfect candidate for the foundation of a _business rule engine_. |
7 | | -The idea is to let configure things in a dynamic way without recompile of a program: |
8 | | - |
9 | | -```coffeescript |
10 | | -# Get the special price if |
11 | | -user.Group in ["good_customers", "collaborator"] |
12 | | - |
13 | | -# Promote article to the homepage when |
14 | | -len(article.Comments) > 100 and article.Category not in ["misc"] |
15 | | - |
16 | | -# Send an alert when |
17 | | -product.Stock < 15 |
18 | | -``` |
19 | | - |
20 | | -Inspired by |
21 | | -* Symfony's [The ExpressionLanguage](https://github.com/symfony/expression-language) component, |
22 | | -* Rob Pike's talk [Lexical Scanning in Go](https://talks.golang.org/2011/lex.slide). |
23 | | - |
24 | | -## Features |
25 | | - |
26 | | -* Works with any valid Go object (structs, maps, etc) |
27 | | -* Static and dynamic typing ([example](https://godoc.org/github.com/antonmedv/expr#example-Define)) |
28 | | - ```go |
29 | | - code := "groups[0].Title + user.Age" |
30 | | - p, err := expr.Parse(code, expr.Define("groups", []Group{}), expr.Define("user", User{})) |
31 | | - // err: invalid operation: groups[0].Name + user.Age (mismatched types string and int) |
32 | | - ``` |
33 | | -* User-friendly error messages |
34 | | - ``` |
35 | | - unclosed "(" |
36 | | - (boo + bar] |
37 | | - ----------^ |
38 | | - ``` |
39 | | -* Reasonable set of basic operators |
40 | | -* Fast (faster otto and goja, see [bench](https://github.com/antonmedv/expr/wiki/Benchmarks)) |
| 2 | +# Expr |
| 3 | +[](https://circleci.com/gh/datasweet/datatable) [](https://godoc.org/github.com/datasweet/expr) [](https://github.com/datasweet/expr/stargazers) |
| 4 | +[](https://github.com/datasweet/expr/blob/master/LICENSE) |
41 | 5 |
|
42 | | -## Install |
| 6 | +[](http://www.datasweet.fr) |
43 | 7 |
|
44 | | -``` |
45 | | -go get -u github.com/antonmedv/expr |
46 | | -``` |
47 | | - |
48 | | -<a href="https://www.patreon.com/antonmedv"> |
49 | | - <img src="https://c5.patreon.com/external/logo/become_a_patron_button@2x.png" width="160"> |
50 | | -</a> |
51 | | - |
52 | | -## Documentation |
53 | | - |
54 | | -* See [](https://godoc.org/github.com/antonmedv/expr) for developer documentation, |
55 | | -* See [The Expression Syntax](https://github.com/antonmedv/expr/wiki/The-Expression-Syntax) page to learn the syntax of the Expr expressions. |
56 | | - |
57 | | -## Examples |
| 8 | +Expr is an engine that can evaluate expressions. |
| 9 | +Expr is a fork from https://github.com/antonmedv/expr |
58 | 10 |
|
59 | | -Executing arbitrary expressions. |
| 11 | +We used the initial package to add custom formula in our package https://github.com/datasweet/datatable. |
| 12 | +We forked the initial project to fit our needs: operators and functions must process scalar or slices. |
60 | 13 |
|
61 | 14 | ```go |
62 | | -env := map[string]interface{}{ |
63 | | - "foo": 1, |
64 | | - "bar": struct{Value int}{1}, |
65 | | -} |
66 | | - |
67 | | -out, err := expr.Eval("foo + bar.Value", env) |
| 15 | +column + 1 |
68 | 16 | ``` |
| 17 | +with column = [1,2,3,4,5] |
| 18 | +output = [2,3,4,5,6] |
69 | 19 |
|
70 | | -Static type checker with struct as environment. |
| 20 | +Also, we removed the map nodes (ie {"foo": "bar}), the struct evaluation, and the type checking before evaluation. |
71 | 21 |
|
| 22 | +## Installation |
72 | 23 | ```go |
73 | | -type env struct { |
74 | | - Foo int |
75 | | - Bar bar |
76 | | -} |
77 | | - |
78 | | -type bar struct { |
79 | | - Value int |
80 | | -} |
81 | | - |
82 | | -p, err := expr.Parse("Foo + Bar.Value", expr.Env(env{})) |
83 | | - |
84 | | -out, err := expr.Run(p, env{1, bar{2}}) |
| 24 | +go get github.com/datasweet/expr |
85 | 25 | ``` |
86 | 26 |
|
87 | | -Using env's methods as functions inside expressions. |
88 | | - |
89 | | -```go |
90 | | -type env struct { |
91 | | - Name string |
92 | | -} |
93 | | - |
94 | | -func (e env) Title() string { |
95 | | - return strings.Title(e.Name) |
96 | | -} |
| 27 | +## Who are we ? |
| 28 | +We are Datasweet, a french startup providing full service (big) data solutions. |
97 | 29 |
|
| 30 | +## Questions ? problems ? suggestions ? |
| 31 | +If you find a bug or want to request a feature, please create a [GitHub Issue](https://github.com/datasweet/expr/issues/new). |
98 | 32 |
|
99 | | -p, err := expr.Parse("'Hello ' ~ Title()", expr.Env(env{})) |
100 | | - |
101 | | -out, err := expr.Run(p, env{"world"}) |
| 33 | +## License |
102 | 34 | ``` |
103 | | - |
104 | | -Using embedded structs to construct env. |
105 | | - |
106 | | -```go |
107 | | -type env struct { |
108 | | - helpers |
109 | | - Name string |
110 | | -} |
111 | | - |
112 | | -type helpers struct{} |
113 | | - |
114 | | -func (h helpers) Title(s string) string { |
115 | | - return strings.Title(s) |
116 | | -} |
117 | | - |
118 | | - |
119 | | -p, err := expr.Parse("'Hello ' ~ Title(Name)", expr.Env(env{})) |
120 | | - |
121 | | -out, err := expr.Run(p, env{"world"}) |
| 35 | +MIT License |
| 36 | +
|
| 37 | +Copyright (c) 2018 Anton Medvedev |
| 38 | +Portions Copyright (c) 2019 Datasweet |
| 39 | +
|
| 40 | +Permission is hereby granted, free of charge, to any person obtaining a copy |
| 41 | +of this software and associated documentation files (the "Software"), to deal |
| 42 | +in the Software without restriction, including without limitation the rights |
| 43 | +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell |
| 44 | +copies of the Software, and to permit persons to whom the Software is |
| 45 | +furnished to do so, subject to the following conditions: |
| 46 | +
|
| 47 | +The above copyright notice and this permission notice shall be included in all |
| 48 | +copies or substantial portions of the Software. |
| 49 | +
|
| 50 | +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR |
| 51 | +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, |
| 52 | +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE |
| 53 | +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER |
| 54 | +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, |
| 55 | +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE |
| 56 | +SOFTWARE. |
122 | 57 | ``` |
123 | 58 |
|
124 | | -## License |
125 | | - |
126 | | -MIT |
0 commit comments