github.com/voedger/voedger@v0.0.0-20240520144910-273e84102129/pkg/state/impl_http_storage.go (about)

     1  /*
     2   * Copyright (c) 2022-present unTill Pro, Ltd.
     3   */
     4  
     5  package state
     6  
     7  import (
     8  	"context"
     9  	"io"
    10  	"net/http"
    11  	"time"
    12  
    13  	"github.com/voedger/voedger/pkg/appdef"
    14  	"github.com/voedger/voedger/pkg/istructs"
    15  )
    16  
    17  type httpStorage struct {
    18  	customClient IHttpClient
    19  }
    20  
    21  type IHttpClient interface {
    22  	Request(timeout time.Duration, method, url string, body io.Reader, headers map[string]string) (statusCode int, resBody []byte, resHeaders map[string][]string, err error)
    23  }
    24  
    25  func (s *httpStorage) NewKeyBuilder(appdef.QName, istructs.IStateKeyBuilder) istructs.IStateKeyBuilder {
    26  	return newHttpKeyBuilder()
    27  }
    28  func (s *httpStorage) Read(key istructs.IStateKeyBuilder, callback istructs.ValueCallback) (err error) {
    29  	kb := key.(*httpKeyBuilder)
    30  
    31  	if s.customClient != nil {
    32  		resStatus, resBody, resHeaders, err := s.customClient.Request(kb.timeout(), kb.method(), kb.url(), kb.body(), kb.headers)
    33  		if err != nil {
    34  			return err
    35  		}
    36  		return callback(nil, &httpValue{
    37  			body:       resBody,
    38  			header:     resHeaders,
    39  			statusCode: resStatus,
    40  		})
    41  	}
    42  
    43  	ctx, cancel := context.WithTimeout(context.Background(), kb.timeout())
    44  	defer cancel()
    45  
    46  	req, err := http.NewRequestWithContext(ctx, kb.method(), kb.url(), kb.body())
    47  	if err != nil {
    48  		return err
    49  	}
    50  
    51  	for k, v := range kb.headers {
    52  		req.Header.Add(k, v)
    53  	}
    54  
    55  	res, err := http.DefaultClient.Do(req)
    56  	if err != nil {
    57  		return err
    58  	}
    59  	defer res.Body.Close()
    60  
    61  	bb, err := io.ReadAll(res.Body)
    62  	if err != nil {
    63  		return err
    64  	}
    65  
    66  	return callback(nil, &httpValue{
    67  		body:       bb,
    68  		header:     res.Header,
    69  		statusCode: res.StatusCode,
    70  	})
    71  }