...

Source file src/jschan/app/jschan.go

Documentation: jschan/app

     1  package jschan
     2  
     3  import (
     4  	"encoding/json"
     5  	"errors"
     6  	"fmt"
     7  	"io/ioutil"
     8  	"net/http"
     9  	"time"
    10  )
    11  
    12  type Client struct {
    13  	BaseURL       string
    14  	SessionCookie string
    15  	CsrfToken     string
    16  	HTTPClient    *http.Client
    17  }
    18  
    19  func NewClient(baseURL string) *Client {
    20  	return &Client{
    21  		BaseURL:       baseURL,
    22  		SessionCookie: "",
    23  		CsrfToken:     "",
    24  		HTTPClient: &http.Client{
    25  			Timeout: time.Minute,
    26  			CheckRedirect: func(req *http.Request, via []*http.Request) error {
    27  				return http.ErrUseLastResponse
    28  			},
    29  		},
    30  	}
    31  }
    32  
    33  type DynamicResponse struct {
    34  	Title    string `json:"title"`
    35  	Message  string `json:"message"`
    36  	Redirect string `json:"redirect,omitempty"`
    37  }
    38  
    39  type ReturnHeaders struct {
    40  	*http.Header
    41  }
    42  
    43  func cookieHeader(rawCookies string) []*http.Cookie {
    44  	header := http.Header{}
    45  	header.Add("Cookie", rawCookies)
    46  	req := http.Request{Header: header}
    47  	return req.Cookies()
    48  }
    49  
    50  func (c *Client) sendRequest(req *http.Request, v interface{}, h *ReturnHeaders) error {
    51  
    52  	if req.Header.Get("Content-Type") == "" {
    53  		if req.Method == http.MethodGet {
    54  			req.Header.Set("Content-Type", "application/json; charset=utf-8")
    55  		} else {
    56  			req.Header.Set("Content-Type", "application/x-www-form-urlencoded")
    57  		}
    58  	}
    59  	req.Header.Set("Accept", "application/json; charset=utf-8")
    60  	req.Header.Set("X-Using-XHR", "true")
    61  	req.Header.Set("Referer", c.BaseURL)
    62  	if c.SessionCookie != "" {
    63  		req.Header.Set("Cookie", fmt.Sprintf("connect.sid=%s", c.SessionCookie))
    64  	}
    65  	if c.CsrfToken != "" {
    66  		req.Header.Set("Csrf-Token", c.CsrfToken)
    67  	}
    68  
    69  	fmt.Printf("%s %s\n", req.Method, req.URL)
    70  
    71  	res, err := c.HTTPClient.Do(req)
    72  	if err != nil {
    73  		return err
    74  	}
    75  
    76  	defer res.Body.Close()
    77  
    78  	if res.StatusCode < http.StatusOK || res.StatusCode >= http.StatusBadRequest {
    79  		var errRes DynamicResponse
    80  		if err = json.NewDecoder(res.Body).Decode(&errRes); err != nil {
    81  			return err
    82  		}
    83  		return errors.New(errRes.Message)
    84  	}
    85  
    86  	h = &ReturnHeaders{
    87  		&res.Header,
    88  	}
    89  	setCookieValue := h.Get("Set-Cookie")
    90  	if setCookieValue != "" {
    91  		parsedSetCookie := cookieHeader(setCookieValue)
    92  		for _, parsedCookie := range parsedSetCookie {
    93  			if parsedCookie.Name == "connect.sid" {
    94  				c.SessionCookie = parsedCookie.Value
    95  			}
    96  		}
    97  	}
    98  
    99  	if v != nil {
   100  		fullResponse := v
   101  		err := json.NewDecoder(res.Body).Decode(&fullResponse)
   102  		if err != nil {
   103  			body, err2 := ioutil.ReadAll(res.Body)
   104  			if err2 != nil {
   105  				return err
   106  			}
   107  			err3 := json.Unmarshal(body, &fullResponse)
   108  			if err3 != nil {
   109  				return err
   110  			}
   111  		}
   112  	}
   113  
   114  	return nil
   115  }
   116  

View as plain text