Update osbuild/images to v0.40.0
In addition, simplify the SPEC file to not have to update the minimum required osbuild version gazillion times, but just once. Update the minimum required osbuild version to v109, due to changes in grub2 stages required by the new osbuild/images version. Update osbild SHA in Schutzfile to v109. Signed-off-by: Tomáš Hozza <thozza@redhat.com>
This commit is contained in:
parent
c138ea6939
commit
2f087f1a6c
190 changed files with 57031 additions and 52810 deletions
15
vendor/github.com/gophercloud/gophercloud/CHANGELOG.md
generated
vendored
15
vendor/github.com/gophercloud/gophercloud/CHANGELOG.md
generated
vendored
|
|
@ -1,3 +1,18 @@
|
|||
## v1.9.0 (2024-02-02)
|
||||
|
||||
New features and improvements:
|
||||
|
||||
* [GH-2884](https://github.com/gophercloud/gophercloud/pull/2884) [v1] Context-aware methods to ProviderClient and ServiceClient
|
||||
* [GH-2887](https://github.com/gophercloud/gophercloud/pull/2887) [v1] Add support of Flavors and FlavorProfiles for Octavia
|
||||
* [GH-2875](https://github.com/gophercloud/gophercloud/pull/2875) [v1] [db/v1/instance]: adding support for availability_zone for a db instance
|
||||
|
||||
CI changes:
|
||||
|
||||
* [GH-2856](https://github.com/gophercloud/gophercloud/pull/2856) [v1] Fix devstack install on EOL magnum branches
|
||||
* [GH-2857](https://github.com/gophercloud/gophercloud/pull/2857) [v1] Fix networking acceptance tests
|
||||
* [GH-2858](https://github.com/gophercloud/gophercloud/pull/2858) [v1] build(deps): bump actions/upload-artifact from 3 to 4
|
||||
* [GH-2859](https://github.com/gophercloud/gophercloud/pull/2859) [v1] build(deps): bump github/codeql-action from 2 to 3
|
||||
|
||||
## v1.8.0 (2023-11-30)
|
||||
|
||||
New features and improvements:
|
||||
|
|
|
|||
739
vendor/github.com/gophercloud/gophercloud/internal/ctxt/context.go
generated
vendored
Normal file
739
vendor/github.com/gophercloud/gophercloud/internal/ctxt/context.go
generated
vendored
Normal file
|
|
@ -0,0 +1,739 @@
|
|||
package ctxt
|
||||
|
||||
// This file is package context of the standard library that ships with Go
|
||||
// v1.21.6. It has been vendored to import AfterFunc.
|
||||
//
|
||||
// Changes made to the original file:
|
||||
// * replace "internal/reflectlite" with "reflect" in the imports
|
||||
// * replace "any" with "interface{}"
|
||||
// * remove the atomic.Int32 type that only exists for testing and is not
|
||||
// compatible with Go v1.14.
|
||||
//
|
||||
// https://cs.opensource.google/go/go/+/refs/tags/go1.21.6:src/context/context.go
|
||||
|
||||
import (
|
||||
"errors"
|
||||
reflectlite "reflect"
|
||||
"sync"
|
||||
"sync/atomic"
|
||||
"time"
|
||||
)
|
||||
|
||||
// A Context carries a deadline, a cancellation signal, and other values across
|
||||
// API boundaries.
|
||||
//
|
||||
// Context's methods may be called by multiple goroutines simultaneously.
|
||||
type Context interface {
|
||||
// Deadline returns the time when work done on behalf of this context
|
||||
// should be canceled. Deadline returns ok==false when no deadline is
|
||||
// set. Successive calls to Deadline return the same results.
|
||||
Deadline() (deadline time.Time, ok bool)
|
||||
|
||||
// Done returns a channel that's closed when work done on behalf of this
|
||||
// context should be canceled. Done may return nil if this context can
|
||||
// never be canceled. Successive calls to Done return the same value.
|
||||
// The close of the Done channel may happen asynchronously,
|
||||
// after the cancel function returns.
|
||||
//
|
||||
// WithCancel arranges for Done to be closed when cancel is called;
|
||||
// WithDeadline arranges for Done to be closed when the deadline
|
||||
// expires; WithTimeout arranges for Done to be closed when the timeout
|
||||
// elapses.
|
||||
//
|
||||
// Done is provided for use in select statements:
|
||||
//
|
||||
// // Stream generates values with DoSomething and sends them to out
|
||||
// // until DoSomething returns an error or ctx.Done is closed.
|
||||
// func Stream(ctx context.Context, out chan<- Value) error {
|
||||
// for {
|
||||
// v, err := DoSomething(ctx)
|
||||
// if err != nil {
|
||||
// return err
|
||||
// }
|
||||
// select {
|
||||
// case <-ctx.Done():
|
||||
// return ctx.Err()
|
||||
// case out <- v:
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// See https://blog.golang.org/pipelines for more examples of how to use
|
||||
// a Done channel for cancellation.
|
||||
Done() <-chan struct{}
|
||||
|
||||
// If Done is not yet closed, Err returns nil.
|
||||
// If Done is closed, Err returns a non-nil error explaining why:
|
||||
// Canceled if the context was canceled
|
||||
// or DeadlineExceeded if the context's deadline passed.
|
||||
// After Err returns a non-nil error, successive calls to Err return the same error.
|
||||
Err() error
|
||||
|
||||
// Value returns the value associated with this context for key, or nil
|
||||
// if no value is associated with key. Successive calls to Value with
|
||||
// the same key returns the same result.
|
||||
//
|
||||
// Use context values only for request-scoped data that transits
|
||||
// processes and API boundaries, not for passing optional parameters to
|
||||
// functions.
|
||||
//
|
||||
// A key identifies a specific value in a Context. Functions that wish
|
||||
// to store values in Context typically allocate a key in a global
|
||||
// variable then use that key as the argument to context.WithValue and
|
||||
// Context.Value. A key can be any type that supports equality;
|
||||
// packages should define keys as an unexported type to avoid
|
||||
// collisions.
|
||||
//
|
||||
// Packages that define a Context key should provide type-safe accessors
|
||||
// for the values stored using that key:
|
||||
//
|
||||
// // Package user defines a User type that's stored in Contexts.
|
||||
// package user
|
||||
//
|
||||
// import "context"
|
||||
//
|
||||
// // User is the type of value stored in the Contexts.
|
||||
// type User struct {...}
|
||||
//
|
||||
// // key is an unexported type for keys defined in this package.
|
||||
// // This prevents collisions with keys defined in other packages.
|
||||
// type key int
|
||||
//
|
||||
// // userKey is the key for user.User values in Contexts. It is
|
||||
// // unexported; clients use user.NewContext and user.FromContext
|
||||
// // instead of using this key directly.
|
||||
// var userKey key
|
||||
//
|
||||
// // NewContext returns a new Context that carries value u.
|
||||
// func NewContext(ctx context.Context, u *User) context.Context {
|
||||
// return context.WithValue(ctx, userKey, u)
|
||||
// }
|
||||
//
|
||||
// // FromContext returns the User value stored in ctx, if any.
|
||||
// func FromContext(ctx context.Context) (*User, bool) {
|
||||
// u, ok := ctx.Value(userKey).(*User)
|
||||
// return u, ok
|
||||
// }
|
||||
Value(key interface{}) interface{}
|
||||
}
|
||||
|
||||
// Canceled is the error returned by [Context.Err] when the context is canceled.
|
||||
var Canceled = errors.New("context canceled")
|
||||
|
||||
// DeadlineExceeded is the error returned by [Context.Err] when the context's
|
||||
// deadline passes.
|
||||
var DeadlineExceeded error = deadlineExceededError{}
|
||||
|
||||
type deadlineExceededError struct{}
|
||||
|
||||
func (deadlineExceededError) Error() string { return "context deadline exceeded" }
|
||||
func (deadlineExceededError) Timeout() bool { return true }
|
||||
func (deadlineExceededError) Temporary() bool { return true }
|
||||
|
||||
// An emptyCtx is never canceled, has no values, and has no deadline.
|
||||
// It is the common base of backgroundCtx and todoCtx.
|
||||
type emptyCtx struct{}
|
||||
|
||||
func (emptyCtx) Deadline() (deadline time.Time, ok bool) {
|
||||
return
|
||||
}
|
||||
|
||||
func (emptyCtx) Done() <-chan struct{} {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (emptyCtx) Err() error {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (emptyCtx) Value(key interface{}) interface{} {
|
||||
return nil
|
||||
}
|
||||
|
||||
type backgroundCtx struct{ emptyCtx }
|
||||
|
||||
func (backgroundCtx) String() string {
|
||||
return "context.Background"
|
||||
}
|
||||
|
||||
type todoCtx struct{ emptyCtx }
|
||||
|
||||
func (todoCtx) String() string {
|
||||
return "context.TODO"
|
||||
}
|
||||
|
||||
// Background returns a non-nil, empty [Context]. It is never canceled, has no
|
||||
// values, and has no deadline. It is typically used by the main function,
|
||||
// initialization, and tests, and as the top-level Context for incoming
|
||||
// requests.
|
||||
func Background() Context {
|
||||
return backgroundCtx{}
|
||||
}
|
||||
|
||||
// TODO returns a non-nil, empty [Context]. Code should use context.TODO when
|
||||
// it's unclear which Context to use or it is not yet available (because the
|
||||
// surrounding function has not yet been extended to accept a Context
|
||||
// parameter).
|
||||
func TODO() Context {
|
||||
return todoCtx{}
|
||||
}
|
||||
|
||||
// A CancelFunc tells an operation to abandon its work.
|
||||
// A CancelFunc does not wait for the work to stop.
|
||||
// A CancelFunc may be called by multiple goroutines simultaneously.
|
||||
// After the first call, subsequent calls to a CancelFunc do nothing.
|
||||
type CancelFunc func()
|
||||
|
||||
// WithCancel returns a copy of parent with a new Done channel. The returned
|
||||
// context's Done channel is closed when the returned cancel function is called
|
||||
// or when the parent context's Done channel is closed, whichever happens first.
|
||||
//
|
||||
// Canceling this context releases resources associated with it, so code should
|
||||
// call cancel as soon as the operations running in this Context complete.
|
||||
func WithCancel(parent Context) (ctx Context, cancel CancelFunc) {
|
||||
c := withCancel(parent)
|
||||
return c, func() { c.cancel(true, Canceled, nil) }
|
||||
}
|
||||
|
||||
// A CancelCauseFunc behaves like a [CancelFunc] but additionally sets the cancellation cause.
|
||||
// This cause can be retrieved by calling [Cause] on the canceled Context or on
|
||||
// any of its derived Contexts.
|
||||
//
|
||||
// If the context has already been canceled, CancelCauseFunc does not set the cause.
|
||||
// For example, if childContext is derived from parentContext:
|
||||
// - if parentContext is canceled with cause1 before childContext is canceled with cause2,
|
||||
// then Cause(parentContext) == Cause(childContext) == cause1
|
||||
// - if childContext is canceled with cause2 before parentContext is canceled with cause1,
|
||||
// then Cause(parentContext) == cause1 and Cause(childContext) == cause2
|
||||
type CancelCauseFunc func(cause error)
|
||||
|
||||
// WithCancelCause behaves like [WithCancel] but returns a [CancelCauseFunc] instead of a [CancelFunc].
|
||||
// Calling cancel with a non-nil error (the "cause") records that error in ctx;
|
||||
// it can then be retrieved using Cause(ctx).
|
||||
// Calling cancel with nil sets the cause to Canceled.
|
||||
//
|
||||
// Example use:
|
||||
//
|
||||
// ctx, cancel := context.WithCancelCause(parent)
|
||||
// cancel(myError)
|
||||
// ctx.Err() // returns context.Canceled
|
||||
// context.Cause(ctx) // returns myError
|
||||
func WithCancelCause(parent Context) (ctx Context, cancel CancelCauseFunc) {
|
||||
c := withCancel(parent)
|
||||
return c, func(cause error) { c.cancel(true, Canceled, cause) }
|
||||
}
|
||||
|
||||
func withCancel(parent Context) *cancelCtx {
|
||||
if parent == nil {
|
||||
panic("cannot create context from nil parent")
|
||||
}
|
||||
c := &cancelCtx{}
|
||||
c.propagateCancel(parent, c)
|
||||
return c
|
||||
}
|
||||
|
||||
// Cause returns a non-nil error explaining why c was canceled.
|
||||
// The first cancellation of c or one of its parents sets the cause.
|
||||
// If that cancellation happened via a call to CancelCauseFunc(err),
|
||||
// then [Cause] returns err.
|
||||
// Otherwise Cause(c) returns the same value as c.Err().
|
||||
// Cause returns nil if c has not been canceled yet.
|
||||
func Cause(c Context) error {
|
||||
if cc, ok := c.Value(&cancelCtxKey).(*cancelCtx); ok {
|
||||
cc.mu.Lock()
|
||||
defer cc.mu.Unlock()
|
||||
return cc.cause
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// AfterFunc arranges to call f in its own goroutine after ctx is done
|
||||
// (cancelled or timed out).
|
||||
// If ctx is already done, AfterFunc calls f immediately in its own goroutine.
|
||||
//
|
||||
// Multiple calls to AfterFunc on a context operate independently;
|
||||
// one does not replace another.
|
||||
//
|
||||
// Calling the returned stop function stops the association of ctx with f.
|
||||
// It returns true if the call stopped f from being run.
|
||||
// If stop returns false,
|
||||
// either the context is done and f has been started in its own goroutine;
|
||||
// or f was already stopped.
|
||||
// The stop function does not wait for f to complete before returning.
|
||||
// If the caller needs to know whether f is completed,
|
||||
// it must coordinate with f explicitly.
|
||||
//
|
||||
// If ctx has a "AfterFunc(func()) func() bool" method,
|
||||
// AfterFunc will use it to schedule the call.
|
||||
func AfterFunc(ctx Context, f func()) (stop func() bool) {
|
||||
a := &afterFuncCtx{
|
||||
f: f,
|
||||
}
|
||||
a.cancelCtx.propagateCancel(ctx, a)
|
||||
return func() bool {
|
||||
stopped := false
|
||||
a.once.Do(func() {
|
||||
stopped = true
|
||||
})
|
||||
if stopped {
|
||||
a.cancel(true, Canceled, nil)
|
||||
}
|
||||
return stopped
|
||||
}
|
||||
}
|
||||
|
||||
type afterFuncer interface {
|
||||
AfterFunc(func()) func() bool
|
||||
}
|
||||
|
||||
type afterFuncCtx struct {
|
||||
cancelCtx
|
||||
once sync.Once // either starts running f or stops f from running
|
||||
f func()
|
||||
}
|
||||
|
||||
func (a *afterFuncCtx) cancel(removeFromParent bool, err, cause error) {
|
||||
a.cancelCtx.cancel(false, err, cause)
|
||||
if removeFromParent {
|
||||
removeChild(a.Context, a)
|
||||
}
|
||||
a.once.Do(func() {
|
||||
go a.f()
|
||||
})
|
||||
}
|
||||
|
||||
// A stopCtx is used as the parent context of a cancelCtx when
|
||||
// an AfterFunc has been registered with the parent.
|
||||
// It holds the stop function used to unregister the AfterFunc.
|
||||
type stopCtx struct {
|
||||
Context
|
||||
stop func() bool
|
||||
}
|
||||
|
||||
// &cancelCtxKey is the key that a cancelCtx returns itself for.
|
||||
var cancelCtxKey int
|
||||
|
||||
// parentCancelCtx returns the underlying *cancelCtx for parent.
|
||||
// It does this by looking up parent.Value(&cancelCtxKey) to find
|
||||
// the innermost enclosing *cancelCtx and then checking whether
|
||||
// parent.Done() matches that *cancelCtx. (If not, the *cancelCtx
|
||||
// has been wrapped in a custom implementation providing a
|
||||
// different done channel, in which case we should not bypass it.)
|
||||
func parentCancelCtx(parent Context) (*cancelCtx, bool) {
|
||||
done := parent.Done()
|
||||
if done == closedchan || done == nil {
|
||||
return nil, false
|
||||
}
|
||||
p, ok := parent.Value(&cancelCtxKey).(*cancelCtx)
|
||||
if !ok {
|
||||
return nil, false
|
||||
}
|
||||
pdone, _ := p.done.Load().(chan struct{})
|
||||
if pdone != done {
|
||||
return nil, false
|
||||
}
|
||||
return p, true
|
||||
}
|
||||
|
||||
// removeChild removes a context from its parent.
|
||||
func removeChild(parent Context, child canceler) {
|
||||
if s, ok := parent.(stopCtx); ok {
|
||||
s.stop()
|
||||
return
|
||||
}
|
||||
p, ok := parentCancelCtx(parent)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
p.mu.Lock()
|
||||
if p.children != nil {
|
||||
delete(p.children, child)
|
||||
}
|
||||
p.mu.Unlock()
|
||||
}
|
||||
|
||||
// A canceler is a context type that can be canceled directly. The
|
||||
// implementations are *cancelCtx and *timerCtx.
|
||||
type canceler interface {
|
||||
cancel(removeFromParent bool, err, cause error)
|
||||
Done() <-chan struct{}
|
||||
}
|
||||
|
||||
// closedchan is a reusable closed channel.
|
||||
var closedchan = make(chan struct{})
|
||||
|
||||
func init() {
|
||||
close(closedchan)
|
||||
}
|
||||
|
||||
// A cancelCtx can be canceled. When canceled, it also cancels any children
|
||||
// that implement canceler.
|
||||
type cancelCtx struct {
|
||||
Context
|
||||
|
||||
mu sync.Mutex // protects following fields
|
||||
done atomic.Value // of chan struct{}, created lazily, closed by first cancel call
|
||||
children map[canceler]struct{} // set to nil by the first cancel call
|
||||
err error // set to non-nil by the first cancel call
|
||||
cause error // set to non-nil by the first cancel call
|
||||
}
|
||||
|
||||
func (c *cancelCtx) Value(key interface{}) interface{} {
|
||||
if key == &cancelCtxKey {
|
||||
return c
|
||||
}
|
||||
return value(c.Context, key)
|
||||
}
|
||||
|
||||
func (c *cancelCtx) Done() <-chan struct{} {
|
||||
d := c.done.Load()
|
||||
if d != nil {
|
||||
return d.(chan struct{})
|
||||
}
|
||||
c.mu.Lock()
|
||||
defer c.mu.Unlock()
|
||||
d = c.done.Load()
|
||||
if d == nil {
|
||||
d = make(chan struct{})
|
||||
c.done.Store(d)
|
||||
}
|
||||
return d.(chan struct{})
|
||||
}
|
||||
|
||||
func (c *cancelCtx) Err() error {
|
||||
c.mu.Lock()
|
||||
err := c.err
|
||||
c.mu.Unlock()
|
||||
return err
|
||||
}
|
||||
|
||||
// propagateCancel arranges for child to be canceled when parent is.
|
||||
// It sets the parent context of cancelCtx.
|
||||
func (c *cancelCtx) propagateCancel(parent Context, child canceler) {
|
||||
c.Context = parent
|
||||
|
||||
done := parent.Done()
|
||||
if done == nil {
|
||||
return // parent is never canceled
|
||||
}
|
||||
|
||||
select {
|
||||
case <-done:
|
||||
// parent is already canceled
|
||||
child.cancel(false, parent.Err(), Cause(parent))
|
||||
return
|
||||
default:
|
||||
}
|
||||
|
||||
if p, ok := parentCancelCtx(parent); ok {
|
||||
// parent is a *cancelCtx, or derives from one.
|
||||
p.mu.Lock()
|
||||
if p.err != nil {
|
||||
// parent has already been canceled
|
||||
child.cancel(false, p.err, p.cause)
|
||||
} else {
|
||||
if p.children == nil {
|
||||
p.children = make(map[canceler]struct{})
|
||||
}
|
||||
p.children[child] = struct{}{}
|
||||
}
|
||||
p.mu.Unlock()
|
||||
return
|
||||
}
|
||||
|
||||
if a, ok := parent.(afterFuncer); ok {
|
||||
// parent implements an AfterFunc method.
|
||||
c.mu.Lock()
|
||||
stop := a.AfterFunc(func() {
|
||||
child.cancel(false, parent.Err(), Cause(parent))
|
||||
})
|
||||
c.Context = stopCtx{
|
||||
Context: parent,
|
||||
stop: stop,
|
||||
}
|
||||
c.mu.Unlock()
|
||||
return
|
||||
}
|
||||
|
||||
go func() {
|
||||
select {
|
||||
case <-parent.Done():
|
||||
child.cancel(false, parent.Err(), Cause(parent))
|
||||
case <-child.Done():
|
||||
}
|
||||
}()
|
||||
}
|
||||
|
||||
type stringer interface {
|
||||
String() string
|
||||
}
|
||||
|
||||
func contextName(c Context) string {
|
||||
if s, ok := c.(stringer); ok {
|
||||
return s.String()
|
||||
}
|
||||
return reflectlite.TypeOf(c).String()
|
||||
}
|
||||
|
||||
func (c *cancelCtx) String() string {
|
||||
return contextName(c.Context) + ".WithCancel"
|
||||
}
|
||||
|
||||
// cancel closes c.done, cancels each of c's children, and, if
|
||||
// removeFromParent is true, removes c from its parent's children.
|
||||
// cancel sets c.cause to cause if this is the first time c is canceled.
|
||||
func (c *cancelCtx) cancel(removeFromParent bool, err, cause error) {
|
||||
if err == nil {
|
||||
panic("context: internal error: missing cancel error")
|
||||
}
|
||||
if cause == nil {
|
||||
cause = err
|
||||
}
|
||||
c.mu.Lock()
|
||||
if c.err != nil {
|
||||
c.mu.Unlock()
|
||||
return // already canceled
|
||||
}
|
||||
c.err = err
|
||||
c.cause = cause
|
||||
d, _ := c.done.Load().(chan struct{})
|
||||
if d == nil {
|
||||
c.done.Store(closedchan)
|
||||
} else {
|
||||
close(d)
|
||||
}
|
||||
for child := range c.children {
|
||||
// NOTE: acquiring the child's lock while holding parent's lock.
|
||||
child.cancel(false, err, cause)
|
||||
}
|
||||
c.children = nil
|
||||
c.mu.Unlock()
|
||||
|
||||
if removeFromParent {
|
||||
removeChild(c.Context, c)
|
||||
}
|
||||
}
|
||||
|
||||
// WithoutCancel returns a copy of parent that is not canceled when parent is canceled.
|
||||
// The returned context returns no Deadline or Err, and its Done channel is nil.
|
||||
// Calling [Cause] on the returned context returns nil.
|
||||
func WithoutCancel(parent Context) Context {
|
||||
if parent == nil {
|
||||
panic("cannot create context from nil parent")
|
||||
}
|
||||
return withoutCancelCtx{parent}
|
||||
}
|
||||
|
||||
type withoutCancelCtx struct {
|
||||
c Context
|
||||
}
|
||||
|
||||
func (withoutCancelCtx) Deadline() (deadline time.Time, ok bool) {
|
||||
return
|
||||
}
|
||||
|
||||
func (withoutCancelCtx) Done() <-chan struct{} {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (withoutCancelCtx) Err() error {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (c withoutCancelCtx) Value(key interface{}) interface{} {
|
||||
return value(c, key)
|
||||
}
|
||||
|
||||
func (c withoutCancelCtx) String() string {
|
||||
return contextName(c.c) + ".WithoutCancel"
|
||||
}
|
||||
|
||||
// WithDeadline returns a copy of the parent context with the deadline adjusted
|
||||
// to be no later than d. If the parent's deadline is already earlier than d,
|
||||
// WithDeadline(parent, d) is semantically equivalent to parent. The returned
|
||||
// [Context.Done] channel is closed when the deadline expires, when the returned
|
||||
// cancel function is called, or when the parent context's Done channel is
|
||||
// closed, whichever happens first.
|
||||
//
|
||||
// Canceling this context releases resources associated with it, so code should
|
||||
// call cancel as soon as the operations running in this [Context] complete.
|
||||
func WithDeadline(parent Context, d time.Time) (Context, CancelFunc) {
|
||||
return WithDeadlineCause(parent, d, nil)
|
||||
}
|
||||
|
||||
// WithDeadlineCause behaves like [WithDeadline] but also sets the cause of the
|
||||
// returned Context when the deadline is exceeded. The returned [CancelFunc] does
|
||||
// not set the cause.
|
||||
func WithDeadlineCause(parent Context, d time.Time, cause error) (Context, CancelFunc) {
|
||||
if parent == nil {
|
||||
panic("cannot create context from nil parent")
|
||||
}
|
||||
if cur, ok := parent.Deadline(); ok && cur.Before(d) {
|
||||
// The current deadline is already sooner than the new one.
|
||||
return WithCancel(parent)
|
||||
}
|
||||
c := &timerCtx{
|
||||
deadline: d,
|
||||
}
|
||||
c.cancelCtx.propagateCancel(parent, c)
|
||||
dur := time.Until(d)
|
||||
if dur <= 0 {
|
||||
c.cancel(true, DeadlineExceeded, cause) // deadline has already passed
|
||||
return c, func() { c.cancel(false, Canceled, nil) }
|
||||
}
|
||||
c.mu.Lock()
|
||||
defer c.mu.Unlock()
|
||||
if c.err == nil {
|
||||
c.timer = time.AfterFunc(dur, func() {
|
||||
c.cancel(true, DeadlineExceeded, cause)
|
||||
})
|
||||
}
|
||||
return c, func() { c.cancel(true, Canceled, nil) }
|
||||
}
|
||||
|
||||
// A timerCtx carries a timer and a deadline. It embeds a cancelCtx to
|
||||
// implement Done and Err. It implements cancel by stopping its timer then
|
||||
// delegating to cancelCtx.cancel.
|
||||
type timerCtx struct {
|
||||
cancelCtx
|
||||
timer *time.Timer // Under cancelCtx.mu.
|
||||
|
||||
deadline time.Time
|
||||
}
|
||||
|
||||
func (c *timerCtx) Deadline() (deadline time.Time, ok bool) {
|
||||
return c.deadline, true
|
||||
}
|
||||
|
||||
func (c *timerCtx) String() string {
|
||||
return contextName(c.cancelCtx.Context) + ".WithDeadline(" +
|
||||
c.deadline.String() + " [" +
|
||||
time.Until(c.deadline).String() + "])"
|
||||
}
|
||||
|
||||
func (c *timerCtx) cancel(removeFromParent bool, err, cause error) {
|
||||
c.cancelCtx.cancel(false, err, cause)
|
||||
if removeFromParent {
|
||||
// Remove this timerCtx from its parent cancelCtx's children.
|
||||
removeChild(c.cancelCtx.Context, c)
|
||||
}
|
||||
c.mu.Lock()
|
||||
if c.timer != nil {
|
||||
c.timer.Stop()
|
||||
c.timer = nil
|
||||
}
|
||||
c.mu.Unlock()
|
||||
}
|
||||
|
||||
// WithTimeout returns WithDeadline(parent, time.Now().Add(timeout)).
|
||||
//
|
||||
// Canceling this context releases resources associated with it, so code should
|
||||
// call cancel as soon as the operations running in this [Context] complete:
|
||||
//
|
||||
// func slowOperationWithTimeout(ctx context.Context) (Result, error) {
|
||||
// ctx, cancel := context.WithTimeout(ctx, 100*time.Millisecond)
|
||||
// defer cancel() // releases resources if slowOperation completes before timeout elapses
|
||||
// return slowOperation(ctx)
|
||||
// }
|
||||
func WithTimeout(parent Context, timeout time.Duration) (Context, CancelFunc) {
|
||||
return WithDeadline(parent, time.Now().Add(timeout))
|
||||
}
|
||||
|
||||
// WithTimeoutCause behaves like [WithTimeout] but also sets the cause of the
|
||||
// returned Context when the timeout expires. The returned [CancelFunc] does
|
||||
// not set the cause.
|
||||
func WithTimeoutCause(parent Context, timeout time.Duration, cause error) (Context, CancelFunc) {
|
||||
return WithDeadlineCause(parent, time.Now().Add(timeout), cause)
|
||||
}
|
||||
|
||||
// WithValue returns a copy of parent in which the value associated with key is
|
||||
// val.
|
||||
//
|
||||
// Use context Values only for request-scoped data that transits processes and
|
||||
// APIs, not for passing optional parameters to functions.
|
||||
//
|
||||
// The provided key must be comparable and should not be of type
|
||||
// string or any other built-in type to avoid collisions between
|
||||
// packages using context. Users of WithValue should define their own
|
||||
// types for keys. To avoid allocating when assigning to an
|
||||
// interface{}, context keys often have concrete type
|
||||
// struct{}. Alternatively, exported context key variables' static
|
||||
// type should be a pointer or interface.
|
||||
func WithValue(parent Context, key, val interface{}) Context {
|
||||
if parent == nil {
|
||||
panic("cannot create context from nil parent")
|
||||
}
|
||||
if key == nil {
|
||||
panic("nil key")
|
||||
}
|
||||
if !reflectlite.TypeOf(key).Comparable() {
|
||||
panic("key is not comparable")
|
||||
}
|
||||
return &valueCtx{parent, key, val}
|
||||
}
|
||||
|
||||
// A valueCtx carries a key-value pair. It implements Value for that key and
|
||||
// delegates all other calls to the embedded Context.
|
||||
type valueCtx struct {
|
||||
Context
|
||||
key, val interface{}
|
||||
}
|
||||
|
||||
// stringify tries a bit to stringify v, without using fmt, since we don't
|
||||
// want context depending on the unicode tables. This is only used by
|
||||
// *valueCtx.String().
|
||||
func stringify(v interface{}) string {
|
||||
switch s := v.(type) {
|
||||
case stringer:
|
||||
return s.String()
|
||||
case string:
|
||||
return s
|
||||
}
|
||||
return "<not Stringer>"
|
||||
}
|
||||
|
||||
func (c *valueCtx) String() string {
|
||||
return contextName(c.Context) + ".WithValue(type " +
|
||||
reflectlite.TypeOf(c.key).String() +
|
||||
", val " + stringify(c.val) + ")"
|
||||
}
|
||||
|
||||
func (c *valueCtx) Value(key interface{}) interface{} {
|
||||
if c.key == key {
|
||||
return c.val
|
||||
}
|
||||
return value(c.Context, key)
|
||||
}
|
||||
|
||||
func value(c Context, key interface{}) interface{} {
|
||||
for {
|
||||
switch ctx := c.(type) {
|
||||
case *valueCtx:
|
||||
if key == ctx.key {
|
||||
return ctx.val
|
||||
}
|
||||
c = ctx.Context
|
||||
case *cancelCtx:
|
||||
if key == &cancelCtxKey {
|
||||
return c
|
||||
}
|
||||
c = ctx.Context
|
||||
case withoutCancelCtx:
|
||||
if key == &cancelCtxKey {
|
||||
// This implements Cause(ctx) == nil
|
||||
// when ctx is created using WithoutCancel.
|
||||
return nil
|
||||
}
|
||||
c = ctx.c
|
||||
case *timerCtx:
|
||||
if key == &cancelCtxKey {
|
||||
return &ctx.cancelCtx
|
||||
}
|
||||
c = ctx.Context
|
||||
case backgroundCtx, todoCtx:
|
||||
return nil
|
||||
default:
|
||||
return c.Value(key)
|
||||
}
|
||||
}
|
||||
}
|
||||
52
vendor/github.com/gophercloud/gophercloud/internal/ctxt/merge.go
generated
vendored
Normal file
52
vendor/github.com/gophercloud/gophercloud/internal/ctxt/merge.go
generated
vendored
Normal file
|
|
@ -0,0 +1,52 @@
|
|||
// package ctxt implements context merging.
|
||||
package ctxt
|
||||
|
||||
import (
|
||||
"context"
|
||||
"time"
|
||||
)
|
||||
|
||||
type mergeContext struct {
|
||||
context.Context
|
||||
ctx2 context.Context
|
||||
}
|
||||
|
||||
// Merge returns a context that is cancelled when at least one of the parents
|
||||
// is cancelled. The returned context also returns the values of ctx1, or ctx2
|
||||
// if nil.
|
||||
func Merge(ctx1, ctx2 context.Context) (context.Context, context.CancelFunc) {
|
||||
ctx, cancel := WithCancelCause(ctx1)
|
||||
stop := AfterFunc(ctx2, func() {
|
||||
cancel(Cause(ctx2))
|
||||
})
|
||||
|
||||
return &mergeContext{
|
||||
Context: ctx,
|
||||
ctx2: ctx2,
|
||||
}, func() {
|
||||
stop()
|
||||
cancel(context.Canceled)
|
||||
}
|
||||
}
|
||||
|
||||
// Value returns ctx2's value if ctx's is nil.
|
||||
func (ctx *mergeContext) Value(key interface{}) interface{} {
|
||||
if v := ctx.Context.Value(key); v != nil {
|
||||
return v
|
||||
}
|
||||
return ctx.ctx2.Value(key)
|
||||
}
|
||||
|
||||
// Deadline returns the earlier deadline of the two parents of ctx.
|
||||
func (ctx *mergeContext) Deadline() (time.Time, bool) {
|
||||
if d1, ok := ctx.Context.Deadline(); ok {
|
||||
if d2, ok := ctx.ctx2.Deadline(); ok {
|
||||
if d1.Before(d2) {
|
||||
return d1, true
|
||||
}
|
||||
return d2, true
|
||||
}
|
||||
return d1, ok
|
||||
}
|
||||
return ctx.ctx2.Deadline()
|
||||
}
|
||||
47
vendor/github.com/gophercloud/gophercloud/provider_client.go
generated
vendored
47
vendor/github.com/gophercloud/gophercloud/provider_client.go
generated
vendored
|
|
@ -10,11 +10,13 @@ import (
|
|||
"net/http"
|
||||
"strings"
|
||||
"sync"
|
||||
|
||||
"github.com/gophercloud/gophercloud/internal/ctxt"
|
||||
)
|
||||
|
||||
// DefaultUserAgent is the default User-Agent string set in the request header.
|
||||
const (
|
||||
DefaultUserAgent = "gophercloud/v1.8.0"
|
||||
DefaultUserAgent = "gophercloud/v1.9.0"
|
||||
DefaultMaxBackoffRetries = 60
|
||||
)
|
||||
|
||||
|
|
@ -88,7 +90,9 @@ type ProviderClient struct {
|
|||
// with the token and reauth func zeroed. Such client can be used to perform reauthorization.
|
||||
Throwaway bool
|
||||
|
||||
// Context is the context passed to the HTTP request.
|
||||
// Context is the context passed to the HTTP request. Values set on the
|
||||
// per-call context, when available, override values set on this
|
||||
// context.
|
||||
Context context.Context
|
||||
|
||||
// Retry backoff func is called when rate limited.
|
||||
|
|
@ -352,15 +356,20 @@ type requestState struct {
|
|||
|
||||
var applicationJSON = "application/json"
|
||||
|
||||
// Request performs an HTTP request using the ProviderClient's current HTTPClient. An authentication
|
||||
// header will automatically be provided.
|
||||
func (client *ProviderClient) Request(method, url string, options *RequestOpts) (*http.Response, error) {
|
||||
return client.doRequest(method, url, options, &requestState{
|
||||
// RequestWithContext performs an HTTP request using the ProviderClient's
|
||||
// current HTTPClient. An authentication header will automatically be provided.
|
||||
func (client *ProviderClient) RequestWithContext(ctx context.Context, method, url string, options *RequestOpts) (*http.Response, error) {
|
||||
return client.doRequest(ctx, method, url, options, &requestState{
|
||||
hasReauthenticated: false,
|
||||
})
|
||||
}
|
||||
|
||||
func (client *ProviderClient) doRequest(method, url string, options *RequestOpts, state *requestState) (*http.Response, error) {
|
||||
// Request is a compatibility wrapper for Request.
|
||||
func (client *ProviderClient) Request(method, url string, options *RequestOpts) (*http.Response, error) {
|
||||
return client.RequestWithContext(context.Background(), method, url, options)
|
||||
}
|
||||
|
||||
func (client *ProviderClient) doRequest(ctx context.Context, method, url string, options *RequestOpts, state *requestState) (*http.Response, error) {
|
||||
var body io.Reader
|
||||
var contentType *string
|
||||
|
||||
|
|
@ -389,14 +398,16 @@ func (client *ProviderClient) doRequest(method, url string, options *RequestOpts
|
|||
body = options.RawBody
|
||||
}
|
||||
|
||||
// Construct the http.Request.
|
||||
req, err := http.NewRequest(method, url, body)
|
||||
if client.Context != nil {
|
||||
var cancel context.CancelFunc
|
||||
ctx, cancel = ctxt.Merge(ctx, client.Context)
|
||||
defer cancel()
|
||||
}
|
||||
|
||||
req, err := http.NewRequestWithContext(ctx, method, url, body)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if client.Context != nil {
|
||||
req = req.WithContext(client.Context)
|
||||
}
|
||||
|
||||
// Populate the request headers.
|
||||
// Apply options.MoreHeaders and options.OmitHeaders, to give the caller the chance to
|
||||
|
|
@ -432,12 +443,12 @@ func (client *ProviderClient) doRequest(method, url string, options *RequestOpts
|
|||
if client.RetryFunc != nil {
|
||||
var e error
|
||||
state.retries = state.retries + 1
|
||||
e = client.RetryFunc(client.Context, method, url, options, err, state.retries)
|
||||
e = client.RetryFunc(ctx, method, url, options, err, state.retries)
|
||||
if e != nil {
|
||||
return nil, e
|
||||
}
|
||||
|
||||
return client.doRequest(method, url, options, state)
|
||||
return client.doRequest(ctx, method, url, options, state)
|
||||
}
|
||||
return nil, err
|
||||
}
|
||||
|
|
@ -491,7 +502,7 @@ func (client *ProviderClient) doRequest(method, url string, options *RequestOpts
|
|||
}
|
||||
}
|
||||
state.hasReauthenticated = true
|
||||
resp, err = client.doRequest(method, url, options, state)
|
||||
resp, err = client.doRequest(ctx, method, url, options, state)
|
||||
if err != nil {
|
||||
switch err.(type) {
|
||||
case *ErrUnexpectedResponseCode:
|
||||
|
|
@ -556,7 +567,7 @@ func (client *ProviderClient) doRequest(method, url string, options *RequestOpts
|
|||
return resp, e
|
||||
}
|
||||
|
||||
return client.doRequest(method, url, options, state)
|
||||
return client.doRequest(ctx, method, url, options, state)
|
||||
}
|
||||
case http.StatusInternalServerError:
|
||||
err = ErrDefault500{respErr}
|
||||
|
|
@ -592,7 +603,7 @@ func (client *ProviderClient) doRequest(method, url string, options *RequestOpts
|
|||
return resp, e
|
||||
}
|
||||
|
||||
return client.doRequest(method, url, options, state)
|
||||
return client.doRequest(ctx, method, url, options, state)
|
||||
}
|
||||
|
||||
return resp, err
|
||||
|
|
@ -616,7 +627,7 @@ func (client *ProviderClient) doRequest(method, url string, options *RequestOpts
|
|||
return resp, e
|
||||
}
|
||||
|
||||
return client.doRequest(method, url, options, state)
|
||||
return client.doRequest(ctx, method, url, options, state)
|
||||
}
|
||||
return nil, err
|
||||
}
|
||||
|
|
|
|||
78
vendor/github.com/gophercloud/gophercloud/service_client.go
generated
vendored
78
vendor/github.com/gophercloud/gophercloud/service_client.go
generated
vendored
|
|
@ -1,6 +1,7 @@
|
|||
package gophercloud
|
||||
|
||||
import (
|
||||
"context"
|
||||
"io"
|
||||
"net/http"
|
||||
"strings"
|
||||
|
|
@ -59,58 +60,88 @@ func (client *ServiceClient) initReqOpts(JSONBody interface{}, JSONResponse inte
|
|||
}
|
||||
}
|
||||
|
||||
// Get calls `Request` with the "GET" HTTP verb.
|
||||
func (client *ServiceClient) Get(url string, JSONResponse interface{}, opts *RequestOpts) (*http.Response, error) {
|
||||
// GetWithContext calls `Request` with the "GET" HTTP verb.
|
||||
func (client *ServiceClient) GetWithContext(ctx context.Context, url string, JSONResponse interface{}, opts *RequestOpts) (*http.Response, error) {
|
||||
if opts == nil {
|
||||
opts = new(RequestOpts)
|
||||
}
|
||||
client.initReqOpts(nil, JSONResponse, opts)
|
||||
return client.Request("GET", url, opts)
|
||||
return client.RequestWithContext(ctx, "GET", url, opts)
|
||||
}
|
||||
|
||||
// Post calls `Request` with the "POST" HTTP verb.
|
||||
// Get is a compatibility wrapper for GetWithContext.
|
||||
func (client *ServiceClient) Get(url string, JSONResponse interface{}, opts *RequestOpts) (*http.Response, error) {
|
||||
return client.GetWithContext(context.Background(), url, JSONResponse, opts)
|
||||
}
|
||||
|
||||
// PostWithContext calls `Request` with the "POST" HTTP verb.
|
||||
func (client *ServiceClient) PostWithContext(ctx context.Context, url string, JSONBody interface{}, JSONResponse interface{}, opts *RequestOpts) (*http.Response, error) {
|
||||
if opts == nil {
|
||||
opts = new(RequestOpts)
|
||||
}
|
||||
client.initReqOpts(JSONBody, JSONResponse, opts)
|
||||
return client.RequestWithContext(ctx, "POST", url, opts)
|
||||
}
|
||||
|
||||
// Post is a compatibility wrapper for PostWithContext.
|
||||
func (client *ServiceClient) Post(url string, JSONBody interface{}, JSONResponse interface{}, opts *RequestOpts) (*http.Response, error) {
|
||||
return client.PostWithContext(context.Background(), url, JSONBody, JSONResponse, opts)
|
||||
}
|
||||
|
||||
// PutWithContext calls `Request` with the "PUT" HTTP verb.
|
||||
func (client *ServiceClient) PutWithContext(ctx context.Context, url string, JSONBody interface{}, JSONResponse interface{}, opts *RequestOpts) (*http.Response, error) {
|
||||
if opts == nil {
|
||||
opts = new(RequestOpts)
|
||||
}
|
||||
client.initReqOpts(JSONBody, JSONResponse, opts)
|
||||
return client.Request("POST", url, opts)
|
||||
return client.RequestWithContext(ctx, "PUT", url, opts)
|
||||
}
|
||||
|
||||
// Put calls `Request` with the "PUT" HTTP verb.
|
||||
// Put is a compatibility wrapper for PurWithContext.
|
||||
func (client *ServiceClient) Put(url string, JSONBody interface{}, JSONResponse interface{}, opts *RequestOpts) (*http.Response, error) {
|
||||
return client.PutWithContext(context.Background(), url, JSONBody, JSONResponse, opts)
|
||||
}
|
||||
|
||||
// PatchWithContext calls `Request` with the "PATCH" HTTP verb.
|
||||
func (client *ServiceClient) PatchWithContext(ctx context.Context, url string, JSONBody interface{}, JSONResponse interface{}, opts *RequestOpts) (*http.Response, error) {
|
||||
if opts == nil {
|
||||
opts = new(RequestOpts)
|
||||
}
|
||||
client.initReqOpts(JSONBody, JSONResponse, opts)
|
||||
return client.Request("PUT", url, opts)
|
||||
return client.RequestWithContext(ctx, "PATCH", url, opts)
|
||||
}
|
||||
|
||||
// Patch calls `Request` with the "PATCH" HTTP verb.
|
||||
// Patch is a compatibility wrapper for PatchWithContext.
|
||||
func (client *ServiceClient) Patch(url string, JSONBody interface{}, JSONResponse interface{}, opts *RequestOpts) (*http.Response, error) {
|
||||
return client.PatchWithContext(context.Background(), url, JSONBody, JSONResponse, opts)
|
||||
}
|
||||
|
||||
// DeleteWithContext calls `Request` with the "DELETE" HTTP verb.
|
||||
func (client *ServiceClient) DeleteWithContext(ctx context.Context, url string, opts *RequestOpts) (*http.Response, error) {
|
||||
if opts == nil {
|
||||
opts = new(RequestOpts)
|
||||
}
|
||||
client.initReqOpts(JSONBody, JSONResponse, opts)
|
||||
return client.Request("PATCH", url, opts)
|
||||
client.initReqOpts(nil, nil, opts)
|
||||
return client.RequestWithContext(ctx, "DELETE", url, opts)
|
||||
}
|
||||
|
||||
// Delete calls `Request` with the "DELETE" HTTP verb.
|
||||
// Delete is a compatibility wrapper for DeleteWithContext.
|
||||
func (client *ServiceClient) Delete(url string, opts *RequestOpts) (*http.Response, error) {
|
||||
if opts == nil {
|
||||
opts = new(RequestOpts)
|
||||
}
|
||||
client.initReqOpts(nil, nil, opts)
|
||||
return client.Request("DELETE", url, opts)
|
||||
return client.DeleteWithContext(context.Background(), url, opts)
|
||||
}
|
||||
|
||||
// Head calls `Request` with the "HEAD" HTTP verb.
|
||||
func (client *ServiceClient) Head(url string, opts *RequestOpts) (*http.Response, error) {
|
||||
// HeadWithContext calls `Request` with the "HEAD" HTTP verb.
|
||||
func (client *ServiceClient) HeadWithContext(ctx context.Context, url string, opts *RequestOpts) (*http.Response, error) {
|
||||
if opts == nil {
|
||||
opts = new(RequestOpts)
|
||||
}
|
||||
client.initReqOpts(nil, nil, opts)
|
||||
return client.Request("HEAD", url, opts)
|
||||
return client.RequestWithContext(ctx, "HEAD", url, opts)
|
||||
}
|
||||
|
||||
// Head is a compatibility wrapper for HeadWithContext.
|
||||
func (client *ServiceClient) Head(url string, opts *RequestOpts) (*http.Response, error) {
|
||||
return client.HeadWithContext(context.Background(), url, opts)
|
||||
}
|
||||
|
||||
func (client *ServiceClient) setMicroversionHeader(opts *RequestOpts) {
|
||||
|
|
@ -133,7 +164,7 @@ func (client *ServiceClient) setMicroversionHeader(opts *RequestOpts) {
|
|||
}
|
||||
|
||||
// Request carries out the HTTP operation for the service client
|
||||
func (client *ServiceClient) Request(method, url string, options *RequestOpts) (*http.Response, error) {
|
||||
func (client *ServiceClient) RequestWithContext(ctx context.Context, method, url string, options *RequestOpts) (*http.Response, error) {
|
||||
if options.MoreHeaders == nil {
|
||||
options.MoreHeaders = make(map[string]string)
|
||||
}
|
||||
|
|
@ -151,7 +182,12 @@ func (client *ServiceClient) Request(method, url string, options *RequestOpts) (
|
|||
options.MoreHeaders[k] = v
|
||||
}
|
||||
}
|
||||
return client.ProviderClient.Request(method, url, options)
|
||||
return client.ProviderClient.RequestWithContext(ctx, method, url, options)
|
||||
}
|
||||
|
||||
// Request is a compatibility wrapper for RequestWithContext.
|
||||
func (client *ServiceClient) Request(method, url string, options *RequestOpts) (*http.Response, error) {
|
||||
return client.RequestWithContext(context.Background(), method, url, options)
|
||||
}
|
||||
|
||||
// ParseResponse is a helper function to parse http.Response to constituents.
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue