2dee3018 by Lunny Xiao

add structmap function for controller

1 parent 4fc49b58
Showing 1 changed file with 68 additions and 0 deletions
1 package beego 1 package beego
2 2
3 import ( 3 import (
4 "errors"
4 "fmt" 5 "fmt"
5 "net/http" 6 "net/http"
6 "net/url" 7 "net/url"
7 "reflect" 8 "reflect"
8 "regexp" 9 "regexp"
9 "runtime" 10 "runtime"
11 "strconv"
10 "strings" 12 "strings"
11 ) 13 )
12 14
...@@ -183,6 +185,69 @@ func (p *ControllerRegistor) FilterPrefixPath(path string, filter http.HandlerFu ...@@ -183,6 +185,69 @@ func (p *ControllerRegistor) FilterPrefixPath(path string, filter http.HandlerFu
183 }) 185 })
184 } 186 }
185 187
188 func structMap(vc reflect.Value, params *map[string]string) error {
189 for k, v := range *params {
190 names := strings.Split(k, ".")
191 var value reflect.Value = vc
192 for i, name := range names {
193 if i != len(names)-1 {
194 if value.Kind() != reflect.Struct {
195 return errors.New("arg error")
196 }
197 value := value.FieldByName(name)
198 if !value.IsValid() {
199 return errors.New("arg error")
200 }
201 } else {
202 tv := value.FieldByName(name)
203 fmt.Println(name, tv, tv.Kind())
204 if !tv.IsValid() {
205 return errors.New("arg error")
206 }
207 if !tv.CanSet() {
208 return errors.New("can not set " + name)
209 }
210 var l interface{}
211 switch k := tv.Kind(); k {
212 case reflect.String:
213 l = v
214 case reflect.Bool:
215 l = (v == "true")
216 case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32:
217 x, err := strconv.Atoi(v)
218 if err != nil {
219 return errors.New("arg " + v + " as int: " + err.Error())
220 }
221 l = x
222 case reflect.Int64:
223 x, err := strconv.ParseInt(v, 10, 64)
224 if err != nil {
225 return errors.New("arg " + v + " as int: " + err.Error())
226 }
227 l = x
228 case reflect.Float32, reflect.Float64:
229 x, err := strconv.ParseFloat(v, 64)
230 if err != nil {
231 return errors.New("arg " + v + " as float64: " + err.Error())
232 }
233 l = x
234 case reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64:
235 x, err := strconv.ParseUint(v, 10, 64)
236 if err != nil {
237 return errors.New("arg " + v + " as int: " + err.Error())
238 }
239 l = x
240 case reflect.Struct:
241 fmt.Println("can not set an struct")
242 }
243
244 tv.Set(reflect.ValueOf(l))
245 }
246 }
247 }
248 return nil
249 }
250
186 // AutoRoute 251 // AutoRoute
187 func (p *ControllerRegistor) ServeHTTP(rw http.ResponseWriter, r *http.Request) { 252 func (p *ControllerRegistor) ServeHTTP(rw http.ResponseWriter, r *http.Request) {
188 defer func() { 253 defer func() {
...@@ -351,6 +416,9 @@ func (p *ControllerRegistor) ServeHTTP(rw http.ResponseWriter, r *http.Request) ...@@ -351,6 +416,9 @@ func (p *ControllerRegistor) ServeHTTP(rw http.ResponseWriter, r *http.Request)
351 init := vc.MethodByName("Init") 416 init := vc.MethodByName("Init")
352 in := make([]reflect.Value, 2) 417 in := make([]reflect.Value, 2)
353 ct := &Context{ResponseWriter: w, Request: r, Params: params} 418 ct := &Context{ResponseWriter: w, Request: r, Params: params}
419
420 structMap(vc.Elem(), &params)
421
354 in[0] = reflect.ValueOf(ct) 422 in[0] = reflect.ValueOf(ct)
355 in[1] = reflect.ValueOf(runrouter.controllerType.Name()) 423 in[1] = reflect.ValueOf(runrouter.controllerType.Name())
356 init.Call(in) 424 init.Call(in)
......
Styling with Markdown is supported
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!