// Code generated by go-swagger; DO NOT EDIT.

// Copyright 2018 The go-netbox Authors.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//   http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package secrets

// This file was generated by the swagger tool.
// Editing this file might prove futile when you re-run the swagger generate command

import (
	"net/http"
	"time"

	"golang.org/x/net/context"

	"github.com/go-openapi/errors"
	"github.com/go-openapi/runtime"
	cr "github.com/go-openapi/runtime/client"

	strfmt "github.com/go-openapi/strfmt"
)

// NewSecretsGenerateRsaKeyPairListParams creates a new SecretsGenerateRsaKeyPairListParams object
// with the default values initialized.
func NewSecretsGenerateRsaKeyPairListParams() *SecretsGenerateRsaKeyPairListParams {

	return &SecretsGenerateRsaKeyPairListParams{

		timeout: cr.DefaultTimeout,
	}
}

// NewSecretsGenerateRsaKeyPairListParamsWithTimeout creates a new SecretsGenerateRsaKeyPairListParams object
// with the default values initialized, and the ability to set a timeout on a request
func NewSecretsGenerateRsaKeyPairListParamsWithTimeout(timeout time.Duration) *SecretsGenerateRsaKeyPairListParams {

	return &SecretsGenerateRsaKeyPairListParams{

		timeout: timeout,
	}
}

// NewSecretsGenerateRsaKeyPairListParamsWithContext creates a new SecretsGenerateRsaKeyPairListParams object
// with the default values initialized, and the ability to set a context for a request
func NewSecretsGenerateRsaKeyPairListParamsWithContext(ctx context.Context) *SecretsGenerateRsaKeyPairListParams {

	return &SecretsGenerateRsaKeyPairListParams{

		Context: ctx,
	}
}

// NewSecretsGenerateRsaKeyPairListParamsWithHTTPClient creates a new SecretsGenerateRsaKeyPairListParams object
// with the default values initialized, and the ability to set a custom HTTPClient for a request
func NewSecretsGenerateRsaKeyPairListParamsWithHTTPClient(client *http.Client) *SecretsGenerateRsaKeyPairListParams {

	return &SecretsGenerateRsaKeyPairListParams{
		HTTPClient: client,
	}
}

/*SecretsGenerateRsaKeyPairListParams contains all the parameters to send to the API endpoint
for the secrets generate rsa key pair list operation typically these are written to a http.Request
*/
type SecretsGenerateRsaKeyPairListParams struct {
	timeout    time.Duration
	Context    context.Context
	HTTPClient *http.Client
}

// WithTimeout adds the timeout to the secrets generate rsa key pair list params
func (o *SecretsGenerateRsaKeyPairListParams) WithTimeout(timeout time.Duration) *SecretsGenerateRsaKeyPairListParams {
	o.SetTimeout(timeout)
	return o
}

// SetTimeout adds the timeout to the secrets generate rsa key pair list params
func (o *SecretsGenerateRsaKeyPairListParams) SetTimeout(timeout time.Duration) {
	o.timeout = timeout
}

// WithContext adds the context to the secrets generate rsa key pair list params
func (o *SecretsGenerateRsaKeyPairListParams) WithContext(ctx context.Context) *SecretsGenerateRsaKeyPairListParams {
	o.SetContext(ctx)
	return o
}

// SetContext adds the context to the secrets generate rsa key pair list params
func (o *SecretsGenerateRsaKeyPairListParams) SetContext(ctx context.Context) {
	o.Context = ctx
}

// WithHTTPClient adds the HTTPClient to the secrets generate rsa key pair list params
func (o *SecretsGenerateRsaKeyPairListParams) WithHTTPClient(client *http.Client) *SecretsGenerateRsaKeyPairListParams {
	o.SetHTTPClient(client)
	return o
}

// SetHTTPClient adds the HTTPClient to the secrets generate rsa key pair list params
func (o *SecretsGenerateRsaKeyPairListParams) SetHTTPClient(client *http.Client) {
	o.HTTPClient = client
}

// WriteToRequest writes these params to a swagger request
func (o *SecretsGenerateRsaKeyPairListParams) WriteToRequest(r runtime.ClientRequest, reg strfmt.Registry) error {

	if err := r.SetTimeout(o.timeout); err != nil {
		return err
	}
	var res []error

	if len(res) > 0 {
		return errors.CompositeValidationError(res...)
	}
	return nil
}
