package requests import ( "net/http" "net/url" "regexp" ) // Workflow 工作流 type Workflow struct { session *Session ParsedURL *url.URL Method string Body *Params Cookies []*http.Cookie } // NewWorkflow new and init workflow func NewWorkflow(ses *Session) *Workflow { wf := &Workflow{} wf.SwitchSession(ses) wf.Body = &Params{} return wf } // SwitchSession 替换Session func (wf *Workflow) SwitchSession(ses *Session) { wf.session = ses } // AddCookie 添加Cookie func (wf *Workflow) AddCookie(c *http.Cookie) { } // GetStringURL 获取url的string形式 func (wf *Workflow) GetStringURL() string { return wf.ParsedURL.String() } // SetURL 设置 url func (wf *Workflow) SetURL(srcURL string) *Workflow { purl, err := url.ParseRequestURI(srcURL) if err != nil { panic(err) } wf.ParsedURL = purl return wf } // GetURLQuery 获取Query参数 func (wf *Workflow) GetURLQuery() url.Values { if wf.ParsedURL != nil { return wf.ParsedURL.Query() } return nil } // SetURLQuery 设置Query参数 func (wf *Workflow) SetURLQuery(query url.Values) *Workflow { if query == nil { return wf } wf.ParsedURL.RawQuery = query.Encode() return wf } var regexGetPath = regexp.MustCompile("/[^/]*") // GetURLPath 获取Path参数 func (wf *Workflow) GetURLPath() []string { return regexGetPath.FindAllString(wf.ParsedURL.Path, -1) } // GetURLRawPath 获取未分解Path参数 func (wf *Workflow) GetURLRawPath() string { return wf.ParsedURL.Path } // encodePath path格式每个item都必须以/开头 func encodePath(path []string) string { rawpath := "" for _, p := range path { if p[0] != '/' { p = "/" + p } rawpath += p } return rawpath } // SetURLPath 设置Path参数 func (wf *Workflow) SetURLPath(path []string) *Workflow { if path == nil { return wf } wf.ParsedURL.Path = encodePath(path) return wf } // SetURLRawPath 设置Path参数 func (wf *Workflow) SetURLRawPath(path string) *Workflow { wf.ParsedURL.Path = path return wf } // SetBodyParams 参数设置 func (wf *Workflow) SetBodyParams(params ...interface{}) *Workflow { if params == nil { return wf } plen := len(params) defaultContentType := TypeURLENCODED if plen >= 2 { t := params[plen-1] defaultContentType = t.(string) wf.Body.ContentType = defaultContentType } else { wf.Body.ContentType = defaultContentType } if defaultContentType == TypeFormData { // TODO: form-data createMultipart(wf.Body, params) } else { var values url.Values switch param := params[0].(type) { case map[string]string: values := make(url.Values) for k, v := range param { values.Set(k, v) } wf.Body.IOBody = []byte(values.Encode()) case map[string][]string: values = param wf.Body.IOBody = []byte(values.Encode()) case string: wf.Body.IOBody = []byte(param) case []byte: wf.Body.IOBody = param } } return wf } // Execute 执行 func (wf *Workflow) Execute() (*Response, error) { req := buildBodyRequest(wf.Method, wf.GetStringURL(), wf.Body) if wf.Cookies != nil { for _, c := range wf.Cookies { req.AddCookie(c) } } resp, err := wf.session.client.Do(req) if err != nil { return nil, err } return FromHTTPResponse(resp) }