// Code generated by goa v3.16.1, DO NOT EDIT.
//
// tools HTTP client encoders and decoders
//
// Command:
// $ goa gen github.com/arduino/arduino-create-agent/design

package client

import (
	"bytes"
	"context"
	"io"
	"net/http"
	"net/url"

	tools "github.com/arduino/arduino-create-agent/gen/tools"
	toolsviews "github.com/arduino/arduino-create-agent/gen/tools/views"
	goahttp "goa.design/goa/v3/http"
)

// BuildAvailableRequest instantiates a HTTP request object with method and
// path set to call the "tools" service "available" endpoint
func (c *Client) BuildAvailableRequest(ctx context.Context, v any) (*http.Request, error) {
	u := &url.URL{Scheme: c.scheme, Host: c.host, Path: AvailableToolsPath()}
	req, err := http.NewRequest("GET", u.String(), nil)
	if err != nil {
		return nil, goahttp.ErrInvalidURL("tools", "available", u.String(), err)
	}
	if ctx != nil {
		req = req.WithContext(ctx)
	}

	return req, nil
}

// DecodeAvailableResponse returns a decoder for responses returned by the
// tools available endpoint. restoreBody controls whether the response body
// should be restored after having been read.
func DecodeAvailableResponse(decoder func(*http.Response) goahttp.Decoder, restoreBody bool) func(*http.Response) (any, error) {
	return func(resp *http.Response) (any, error) {
		if restoreBody {
			b, err := io.ReadAll(resp.Body)
			if err != nil {
				return nil, err
			}
			resp.Body = io.NopCloser(bytes.NewBuffer(b))
			defer func() {
				resp.Body = io.NopCloser(bytes.NewBuffer(b))
			}()
		} else {
			defer resp.Body.Close()
		}
		switch resp.StatusCode {
		case http.StatusOK:
			var (
				body AvailableResponseBody
				err  error
			)
			err = decoder(resp).Decode(&body)
			if err != nil {
				return nil, goahttp.ErrDecodingError("tools", "available", err)
			}
			p := NewAvailableToolCollectionOK(body)
			view := "default"
			vres := toolsviews.ToolCollection{Projected: p, View: view}
			if err = toolsviews.ValidateToolCollection(vres); err != nil {
				return nil, goahttp.ErrValidationError("tools", "available", err)
			}
			res := tools.NewToolCollection(vres)
			return res, nil
		default:
			body, _ := io.ReadAll(resp.Body)
			return nil, goahttp.ErrInvalidResponse("tools", "available", resp.StatusCode, string(body))
		}
	}
}

// BuildInstalledheadRequest instantiates a HTTP request object with method and
// path set to call the "tools" service "installedhead" endpoint
func (c *Client) BuildInstalledheadRequest(ctx context.Context, v any) (*http.Request, error) {
	u := &url.URL{Scheme: c.scheme, Host: c.host, Path: InstalledheadToolsPath()}
	req, err := http.NewRequest("HEAD", u.String(), nil)
	if err != nil {
		return nil, goahttp.ErrInvalidURL("tools", "installedhead", u.String(), err)
	}
	if ctx != nil {
		req = req.WithContext(ctx)
	}

	return req, nil
}

// DecodeInstalledheadResponse returns a decoder for responses returned by the
// tools installedhead endpoint. restoreBody controls whether the response body
// should be restored after having been read.
func DecodeInstalledheadResponse(decoder func(*http.Response) goahttp.Decoder, restoreBody bool) func(*http.Response) (any, error) {
	return func(resp *http.Response) (any, error) {
		if restoreBody {
			b, err := io.ReadAll(resp.Body)
			if err != nil {
				return nil, err
			}
			resp.Body = io.NopCloser(bytes.NewBuffer(b))
			defer func() {
				resp.Body = io.NopCloser(bytes.NewBuffer(b))
			}()
		} else {
			defer resp.Body.Close()
		}
		switch resp.StatusCode {
		case http.StatusOK:
			return nil, nil
		default:
			body, _ := io.ReadAll(resp.Body)
			return nil, goahttp.ErrInvalidResponse("tools", "installedhead", resp.StatusCode, string(body))
		}
	}
}

// BuildInstalledRequest instantiates a HTTP request object with method and
// path set to call the "tools" service "installed" endpoint
func (c *Client) BuildInstalledRequest(ctx context.Context, v any) (*http.Request, error) {
	u := &url.URL{Scheme: c.scheme, Host: c.host, Path: InstalledToolsPath()}
	req, err := http.NewRequest("GET", u.String(), nil)
	if err != nil {
		return nil, goahttp.ErrInvalidURL("tools", "installed", u.String(), err)
	}
	if ctx != nil {
		req = req.WithContext(ctx)
	}

	return req, nil
}

// DecodeInstalledResponse returns a decoder for responses returned by the
// tools installed endpoint. restoreBody controls whether the response body
// should be restored after having been read.
func DecodeInstalledResponse(decoder func(*http.Response) goahttp.Decoder, restoreBody bool) func(*http.Response) (any, error) {
	return func(resp *http.Response) (any, error) {
		if restoreBody {
			b, err := io.ReadAll(resp.Body)
			if err != nil {
				return nil, err
			}
			resp.Body = io.NopCloser(bytes.NewBuffer(b))
			defer func() {
				resp.Body = io.NopCloser(bytes.NewBuffer(b))
			}()
		} else {
			defer resp.Body.Close()
		}
		switch resp.StatusCode {
		case http.StatusOK:
			var (
				body InstalledResponseBody
				err  error
			)
			err = decoder(resp).Decode(&body)
			if err != nil {
				return nil, goahttp.ErrDecodingError("tools", "installed", err)
			}
			p := NewInstalledToolCollectionOK(body)
			view := "default"
			vres := toolsviews.ToolCollection{Projected: p, View: view}
			if err = toolsviews.ValidateToolCollection(vres); err != nil {
				return nil, goahttp.ErrValidationError("tools", "installed", err)
			}
			res := tools.NewToolCollection(vres)
			return res, nil
		default:
			body, _ := io.ReadAll(resp.Body)
			return nil, goahttp.ErrInvalidResponse("tools", "installed", resp.StatusCode, string(body))
		}
	}
}

// BuildInstallRequest instantiates a HTTP request object with method and path
// set to call the "tools" service "install" endpoint
func (c *Client) BuildInstallRequest(ctx context.Context, v any) (*http.Request, error) {
	u := &url.URL{Scheme: c.scheme, Host: c.host, Path: InstallToolsPath()}
	req, err := http.NewRequest("POST", u.String(), nil)
	if err != nil {
		return nil, goahttp.ErrInvalidURL("tools", "install", u.String(), err)
	}
	if ctx != nil {
		req = req.WithContext(ctx)
	}

	return req, nil
}

// EncodeInstallRequest returns an encoder for requests sent to the tools
// install server.
func EncodeInstallRequest(encoder func(*http.Request) goahttp.Encoder) func(*http.Request, any) error {
	return func(req *http.Request, v any) error {
		p, ok := v.(*tools.ToolPayload)
		if !ok {
			return goahttp.ErrInvalidType("tools", "install", "*tools.ToolPayload", v)
		}
		body := NewInstallRequestBody(p)
		if err := encoder(req).Encode(&body); err != nil {
			return goahttp.ErrEncodingError("tools", "install", err)
		}
		return nil
	}
}

// DecodeInstallResponse returns a decoder for responses returned by the tools
// install endpoint. restoreBody controls whether the response body should be
// restored after having been read.
func DecodeInstallResponse(decoder func(*http.Response) goahttp.Decoder, restoreBody bool) func(*http.Response) (any, error) {
	return func(resp *http.Response) (any, error) {
		if restoreBody {
			b, err := io.ReadAll(resp.Body)
			if err != nil {
				return nil, err
			}
			resp.Body = io.NopCloser(bytes.NewBuffer(b))
			defer func() {
				resp.Body = io.NopCloser(bytes.NewBuffer(b))
			}()
		} else {
			defer resp.Body.Close()
		}
		switch resp.StatusCode {
		case http.StatusOK:
			var (
				body InstallResponseBody
				err  error
			)
			err = decoder(resp).Decode(&body)
			if err != nil {
				return nil, goahttp.ErrDecodingError("tools", "install", err)
			}
			p := NewInstallOperationOK(&body)
			view := "default"
			vres := &toolsviews.Operation{Projected: p, View: view}
			if err = toolsviews.ValidateOperation(vres); err != nil {
				return nil, goahttp.ErrValidationError("tools", "install", err)
			}
			res := tools.NewOperation(vres)
			return res, nil
		default:
			body, _ := io.ReadAll(resp.Body)
			return nil, goahttp.ErrInvalidResponse("tools", "install", resp.StatusCode, string(body))
		}
	}
}

// BuildRemoveRequest instantiates a HTTP request object with method and path
// set to call the "tools" service "remove" endpoint
func (c *Client) BuildRemoveRequest(ctx context.Context, v any) (*http.Request, error) {
	var (
		packager string
		name     string
		version  string
	)
	{
		p, ok := v.(*tools.ToolPayload)
		if !ok {
			return nil, goahttp.ErrInvalidType("tools", "remove", "*tools.ToolPayload", v)
		}
		packager = p.Packager
		name = p.Name
		version = p.Version
	}
	u := &url.URL{Scheme: c.scheme, Host: c.host, Path: RemoveToolsPath(packager, name, version)}
	req, err := http.NewRequest("DELETE", u.String(), nil)
	if err != nil {
		return nil, goahttp.ErrInvalidURL("tools", "remove", u.String(), err)
	}
	if ctx != nil {
		req = req.WithContext(ctx)
	}

	return req, nil
}

// EncodeRemoveRequest returns an encoder for requests sent to the tools remove
// server.
func EncodeRemoveRequest(encoder func(*http.Request) goahttp.Encoder) func(*http.Request, any) error {
	return func(req *http.Request, v any) error {
		p, ok := v.(*tools.ToolPayload)
		if !ok {
			return goahttp.ErrInvalidType("tools", "remove", "*tools.ToolPayload", v)
		}
		body := NewRemoveRequestBody(p)
		if err := encoder(req).Encode(&body); err != nil {
			return goahttp.ErrEncodingError("tools", "remove", err)
		}
		return nil
	}
}

// DecodeRemoveResponse returns a decoder for responses returned by the tools
// remove endpoint. restoreBody controls whether the response body should be
// restored after having been read.
func DecodeRemoveResponse(decoder func(*http.Response) goahttp.Decoder, restoreBody bool) func(*http.Response) (any, error) {
	return func(resp *http.Response) (any, error) {
		if restoreBody {
			b, err := io.ReadAll(resp.Body)
			if err != nil {
				return nil, err
			}
			resp.Body = io.NopCloser(bytes.NewBuffer(b))
			defer func() {
				resp.Body = io.NopCloser(bytes.NewBuffer(b))
			}()
		} else {
			defer resp.Body.Close()
		}
		switch resp.StatusCode {
		case http.StatusOK:
			var (
				body RemoveResponseBody
				err  error
			)
			err = decoder(resp).Decode(&body)
			if err != nil {
				return nil, goahttp.ErrDecodingError("tools", "remove", err)
			}
			p := NewRemoveOperationOK(&body)
			view := "default"
			vres := &toolsviews.Operation{Projected: p, View: view}
			if err = toolsviews.ValidateOperation(vres); err != nil {
				return nil, goahttp.ErrValidationError("tools", "remove", err)
			}
			res := tools.NewOperation(vres)
			return res, nil
		default:
			body, _ := io.ReadAll(resp.Body)
			return nil, goahttp.ErrInvalidResponse("tools", "remove", resp.StatusCode, string(body))
		}
	}
}

// unmarshalToolResponseToToolsviewsToolView builds a value of type
// *toolsviews.ToolView from a value of type *ToolResponse.
func unmarshalToolResponseToToolsviewsToolView(v *ToolResponse) *toolsviews.ToolView {
	res := &toolsviews.ToolView{
		Name:     v.Name,
		Version:  v.Version,
		Packager: v.Packager,
	}

	return res
}
