feat(options): Add CustomEndpoint and customHeaders clientOptions

This commit is contained in:
Matthieu 'JP' DERASSE 2023-08-12 20:00:35 +00:00
parent a5bf04816e
commit 73aa82a79b
Signed by: mderasse
GPG Key ID: 55141C777B16A705
6 changed files with 49 additions and 11 deletions

View File

@ -26,9 +26,11 @@ type Client struct {
HTTPClient HTTPClient
userAgent string
endpoint string
headers map[string]string
}
// NewClient create a new tesla-stock client with default HTTP Client.
// NewClient create a new tesla-inventory client with default HTTP Client.
func NewClient(options ...ClientOptions) *Client {
client := Client{
@ -36,6 +38,7 @@ func NewClient(options ...ClientOptions) *Client {
lastRequest: &atomic.Value{},
lastResponse: &atomic.Value{},
HTTPClient: http.DefaultClient,
endpoint: inventoryApiEndpoint,
userAgent: defaultUserAgent,
}
@ -120,6 +123,7 @@ func (c *Client) LastAPIResponse() (*http.Response, bool) {
return nil, false
}
//nolint:unused // keeping to respect classical http verb.
func (c *Client) delete(ctx context.Context, path string, payload interface{}, headers map[string]string) (*http.Response, error) {
if payload != nil {
data, err := json.Marshal(payload)
@ -131,6 +135,7 @@ func (c *Client) delete(ctx context.Context, path string, payload interface{}, h
return c.do(ctx, http.MethodDelete, path, nil, headers)
}
//nolint:unused // keeping to respect classical http verb.
func (c *Client) put(ctx context.Context, path string, payload interface{}, headers map[string]string) (*http.Response, error) {
if payload != nil {
data, err := json.Marshal(payload)
@ -142,6 +147,7 @@ func (c *Client) put(ctx context.Context, path string, payload interface{}, head
return c.do(ctx, http.MethodPut, path, nil, headers)
}
//nolint:unused // keeping to respect classical http verb.
func (c *Client) post(ctx context.Context, path string, payload interface{}, headers map[string]string) (*http.Response, error) {
data, err := json.Marshal(payload)
if err != nil {
@ -172,7 +178,8 @@ func dupeRequest(r *http.Request) (*http.Request, error) {
return dreq, nil
}
func (c *Client) Do(r *http.Request, authRequired bool) (*http.Response, error) {
// Do allow anyone to extend sdk.
func (c *Client) Do(r *http.Request) (*http.Response, error) {
c.prepareRequest(r, nil)
return c.HTTPClient.Do(r)
@ -197,7 +204,7 @@ func (c *Client) do(ctx context.Context, method, path string, body io.Reader, he
}()
}
req, err := http.NewRequestWithContext(ctx, method, stockApiEndpoint+path, body)
req, err := http.NewRequestWithContext(ctx, method, c.endpoint+path, body)
if err != nil {
return nil, fmt.Errorf("failed to build request: %w", err)
}
@ -217,6 +224,12 @@ func (c *Client) do(ctx context.Context, method, path string, body io.Reader, he
}
func (c *Client) prepareRequest(req *http.Request, headers map[string]string) {
// set permanent headers provided at the creation of the client
for k, v := range c.headers {
req.Header.Set(k, v)
}
// adding / overiding headers those set for this request
for k, v := range headers {
req.Header.Set(k, v)
}
@ -229,7 +242,7 @@ func (c *Client) checkResponse(resp *http.Response, err error) (*http.Response,
return resp, fmt.Errorf("error calling the API endpoint: %w", err)
}
// Stock API always return a 200
// Inventory API always return a 200
if resp.StatusCode != http.StatusOK {
return resp, c.getErrorFromResponse(resp)
}

View File

@ -9,3 +9,17 @@ func WithUserAgent(userAgent string) ClientOptions {
c.userAgent = userAgent
}
}
// WithCustomEndpoint will allow to overide the default endpoint with a custom one.
func WithCustomEndpoint(endpoint string) ClientOptions {
return func(c *Client) {
c.endpoint = endpoint
}
}
// WithHeaders will add the given headers to every request made by the sdk.
func WithHeaders(headers map[string]string) ClientOptions {
return func(c *Client) {
c.headers = headers
}
}

View File

@ -2,9 +2,9 @@ package teslainventory_sdk
const (
// Version is the current version of the sdk.
Version = "1.0.0"
stockApiEndpoint = "https://www.tesla.com/"
defaultUserAgent = "TeslaApp/" + Version
Version = "1.0.0"
inventoryApiEndpoint = "https://www.tesla.com/inventory/api/"
defaultUserAgent = "TeslaApp/" + Version
)
// DebugFlag represents a set of debug bit flags that can be bitwise-ORed

2
go.mod
View File

@ -1,3 +1,3 @@
module git.dev.m-and-m.ovh/mderasse/teslainventory_sdk
go 1.21
go 1.21.0

View File

@ -8,7 +8,7 @@ import (
)
// GetAvailabilities return the car availabilities matching with the provided characteristics.
func (c *Client) GetAvailabilities(ctx context.Context, params AvailabilityParams) (*AvailabilitiesResponse, error) {
func (c *Client) GetAvailabilities(ctx context.Context, params AvailabilityParams, headers map[string]string) (*AvailabilitiesResponse, error) {
b, err := json.Marshal(params)
if err != nil {
return nil, fmt.Errorf("fail to marshal availability params. Error: %w", err)
@ -20,8 +20,8 @@ func (c *Client) GetAvailabilities(ctx context.Context, params AvailabilityParam
resp, err := c.get(
ctx,
fmt.Sprintf("/inventory/api/v1/inventory-results?%s", queryParams.Encode()),
nil,
fmt.Sprintf("/v1/inventory-results?%s", queryParams.Encode()),
headers,
)
if err != nil {
return nil, err

View File

@ -5,6 +5,7 @@ import "time"
// modelEnum.
type modelEnum string
//nolint:exported // keeping the enum simple and readable.
const (
MODEL_3 modelEnum = "m3"
MODEL_Y modelEnum = "my"
@ -15,6 +16,7 @@ const (
// conditionEnum.
type conditionEnum string
//nolint:exported // keeping the enum simple and readable.
const (
CONDITION_NEW conditionEnum = "new"
CONDITION_USED conditionEnum = "used"
@ -23,6 +25,7 @@ const (
// arrangeByEnum allow to order availabilities by a specific element.
type arrangeByEnum string
//nolint:exported // keeping the enum simple and readable.
const (
ARRANGE_BY_PRICE arrangeByEnum = "Price"
ARRANGE_BY_ODOMETER arrangeByEnum = "Odometer"
@ -33,6 +36,7 @@ const (
// orderByEnum.
type orderByEnum string
//nolint:exported // keeping the enum simple and readable.
const (
ORDER_BY_ASC orderByEnum = "asc"
ORDER_BY_DESC orderByEnum = "desc"
@ -45,6 +49,7 @@ const (
// autopilotEnum.
type autopilotEnum string
//nolint:exported // keeping the enum simple and readable.
const (
AUTOPILOT_AP autopilotEnum = "AUTOPILOT"
AUTOPILOT_ENHANCED autopilotEnum = "ENHANCED_AUTOPILOT"
@ -55,6 +60,7 @@ const (
// cabinConfigEnum.
type cabinConfigEnum string
//nolint:exported // keeping the enum simple and readable.
const (
CABIN_CONFIG_FIVE cabinConfigEnum = "FIVE"
CABIN_CONFIG_SIX cabinConfigEnum = "SIX"
@ -64,6 +70,7 @@ const (
// interiorEnum.
type interiorEnum string
//nolint:exported // keeping the enum simple and readable.
const (
INTERIOR_CREAM interiorEnum = "CREAM"
INTERIOR_WHITE interiorEnum = "WHITE"
@ -73,6 +80,7 @@ const (
// paintEnum.
type paintEnum string
//nolint:exported // keeping the enum simple and readable.
const (
PAINT_RED paintEnum = "RED"
PAINT_WHITE paintEnum = "WHITE"
@ -85,6 +93,7 @@ const (
// steeringWheelEnum.
type steeringWheelEnum string
//nolint:exported // keeping the enum simple and readable.
const (
STEERING_WHEEL_YOKE steeringWheelEnum = "STEERING_YOKE"
STEERING_WHEEL_ROUND steeringWheelEnum = "STEERING_ROUND"
@ -93,6 +102,7 @@ const (
// trimEnum.
type trimEnum string
//nolint:exported // keeping the enum simple and readable.
const (
TRIM_MS_AWD trimEnum = "MSAWD"
TRIM_MS_PLAID trimEnum = "MSPLAID"
@ -109,6 +119,7 @@ const (
// wheelsEnum.
type wheelsEnum string
//nolint:exported // keeping the enum simple and readable.
const (
WHEELS_18 wheelsEnum = "EIGHTEEN"
WHEELS_19 wheelsEnum = "NINETEEN"