Back to godoc.org
v.io / v23 / context

Package context

v0.1.9
Latest Go to latest

The latest major version is .

Published: Jun 29, 2020 | License: BSD-3-Clause | Module: v.io

Overview

Package context implements a mechanism to carry data across API boundaries. The context.T struct carries deadlines and cancellation as well as other arbitrary values.

Application code receives contexts in two main ways:

1) A context.T is returned from v23.Init(). This will generally be used to set up servers in main, or for stand-alone client programs.

func main() {
  ctx, shutdown := v23.Init()
  defer shutdown()

  doSomething(ctx)
}

2) A context.T is passed to every server method implementation as the first parameter.

func (m *myServer) Method(ctx *context.T, call rpc.ServerCall) error {
  doSomething(ctx)
}

Once you have a context you can derive further contexts to change settings. for example to adjust a deadline you might do:

func main() {
  ctx, shutdown := v23.Init()
  defer shutdown()
  // We'll use cacheCtx to lookup data in memcache
  // if it takes more than a second to get data from
  // memcache we should just skip the cache and perform
  // the slow operation.
  cacheCtx, cancel := WithTimeout(ctx, time.Second)
  if err := FetchDataFromMemcache(cacheCtx, key); err != nil {
    // Here we use the original ctx, not the derived cacheCtx
    // so we aren't constrained by the 1 second timeout.
    RecomputeData(ctx, key)
  }
}

Contexts form a tree where derived contexts are children of the contexts from which they were derived. Children inherit all the properties of their parent except for the property being replaced (the deadline in the example above).

Contexts are extensible. The Value/WithValue functions allow you to attach new information to the context and extend its capabilities. In the same way we derive new contexts via the 'With' family of functions you can create methods to attach new data:

package auth

import "v.io/v23/context"

type Auth struct{...}

type key int
const authKey = key(0)

function WithAuth(parent *context.T, data *Auth) *context.T {
    return context.WithValue(parent, authKey, data)
}

function GetAuth(ctx *context.T) *Auth {
    data, _ := ctx.Value(authKey).(*Auth)
    return data
}

Note that a value of any type can be used as a key, but you should use an unexported value of an unexported type to ensure that no collisions can occur.

Index

Variables

var Canceled = errors.New("context canceled")

Cancelled is returned by contexts which have been cancelled. nolint:golint // API change required.

var DeadlineExceeded = errors.New("context deadline exceeded")

DeadlineExceeded is returned by contexts that have exceeded their deadlines and therefore been canceled automatically. nolint:golint // API change required.

func RootContext

func RootContext() (*T, CancelFunc)

RootContext creates a new root context with no data attached. A RootContext is cancelable (see WithCancel). Typically you should not call this function, instead you should derive contexts from other contexts, such as the context returned from v23.Init or the result of the Context() method on a ServerCall. This function is sometimes useful in tests, where it is undesirable to initialize a runtime to test a function that reads from a T.

func WithCancel

func WithCancel(parent *T) (*T, CancelFunc)

WithCancel returns a child of the current context along with a function that can be used to cancel it. After cancel() is called the channels returned by the Done() methods of the new context (and all context further derived from it) will be closed.

func WithDeadline

func WithDeadline(parent *T, deadline time.Time) (*T, CancelFunc)

WithDeadline returns a child of the current context along with a function that can be used to cancel it at any time (as from WithCancel). When the deadline is reached the context will be automatically cancelled. Contexts should be cancelled when they are no longer needed so that resources associated with their timers may be released.

func WithRootCancel

func WithRootCancel(parent *T) (*T, CancelFunc)

WithRootContext returns a context derived from parent, but that is detached from the deadlines and cancellation hierarchy so that this context will only ever be canceled when the returned CancelFunc is called, or the RootContext from which this context is ultimately derived is canceled.

func WithTimeout

func WithTimeout(parent *T, timeout time.Duration) (*T, CancelFunc)

WithTimeout is similar to WithDeadline except a Duration is given that represents a relative point in time from now.

type CancelFunc

type CancelFunc func()

CancelFunc is used to cancel a context. The first call will cause the paired context and all descendants to close their Done() channels. Further calls do nothing.

type ContextLogger

type ContextLogger interface {
	// InfoDepth logs to the INFO log. depth is used to determine which call frame to log.
	InfoDepth(ctx *T, depth int, args ...interface{})

	// InfoStack logs the current goroutine's stack if the all parameter
	// is false, or the stacks of all goroutines if it's true.
	InfoStack(ctx *T, all bool)

	// VDepth returns true if the configured logging level is greater than or equal to its parameter. depth
	// is used to determine which call frame to test against.
	VDepth(ctx *T, depth int, level int) bool

	// VIDepth is like VDepth, except that it returns nil if there level is greater than the
	// configured log level.
	VIDepth(ctx *T, depth int, level int) ContextLogger
}

ContextLogger is a logger that uses a passed in T to configure the logging behavior. nolint:golint // API change required.

type T

type T struct {
	// contains filtered or unexported fields
}

T carries deadlines, cancellation and data across API boundaries. It is safe to use a T from multiple goroutines simultaneously. The zero-type of context is uninitialized and will panic if used directly by application code. It also implements v23/logging.Logger and hence can be used directly for logging (e.g. ctx.Infof(...)).

func FromGoContext

func FromGoContext(ctx gocontext.Context) *T

FromGoContext creates a Vanadium Context object from a generic Context.

Note: a goroutine will leak if the original context is not cancelled.

func WithContextLogger

func WithContextLogger(parent *T, logger ContextLogger) *T

WithContextLogger returns a child of the current context that embeds the supplied context logger

func WithLogger

func WithLogger(parent *T, logger logging.Logger) *T

WithLogger returns a child of the current context that embeds the supplied logger.

func WithValue

func WithValue(parent *T, key interface{}, val interface{}) *T

WithValue returns a child of the current context that will return the given val when Value(key) is called.

func (*T) Deadline

func (t *T) Deadline() (deadline time.Time, ok bool)

Deadline returns the time at which this context will be automatically canceled.

func (*T) Done

func (t *T) Done() <-chan struct{}

Done returns a channel which will be closed when this context.T is canceled or exceeds its deadline. Successive calls will return the same value. Implementations may return nil if they can never be canceled.

func (*T) Err

func (t *T) Err() error

After the channel returned by Done() is closed, Err() will return either Canceled or DeadlineExceeded.

func (*T) Error

func (t *T) Error(args ...interface{})

func (*T) ErrorDepth

func (t *T) ErrorDepth(depth int, args ...interface{})

func (*T) Errorf

func (t *T) Errorf(format string, args ...interface{})

func (*T) Fatal

func (t *T) Fatal(args ...interface{})

func (*T) FatalDepth

func (t *T) FatalDepth(depth int, args ...interface{})

func (*T) Fatalf

func (t *T) Fatalf(format string, args ...interface{})

func (*T) FlushLog

func (t *T) FlushLog()

func (*T) Info

func (t *T) Info(args ...interface{})

func (*T) InfoDepth

func (t *T) InfoDepth(depth int, args ...interface{})

func (*T) InfoStack

func (t *T) InfoStack(all bool)

func (*T) Infof

func (t *T) Infof(format string, args ...interface{})

func (*T) Initialized

func (t *T) Initialized() bool

Initialized returns true if this context has been properly initialized by a runtime.

func (*T) LoggerImplementation

func (t *T) LoggerImplementation() interface{}

LoggerImplementation returns the implementation of the logger associated with this context. It should almost never need to be used by application code.

func (*T) Panic

func (t *T) Panic(args ...interface{})

func (*T) PanicDepth

func (t *T) PanicDepth(depth int, args ...interface{})

func (*T) Panicf

func (t *T) Panicf(format string, args ...interface{})

func (*T) V

func (t *T) V(level int) bool

func (*T) VDepth

func (t *T) VDepth(depth int, level int) bool

func (*T) VI

func (t *T) VI(level int) interface {
	Info(args ...interface{})
	Infof(format string, args ...interface{})
	InfoDepth(depth int, args ...interface{})
	InfoStack(all bool)
}

func (*T) VIDepth

func (t *T) VIDepth(depth int, level int) interface {
	Info(args ...interface{})
	Infof(format string, args ...interface{})
	InfoDepth(depth int, args ...interface{})
	InfoStack(all bool)
}

func (*T) Value

func (t *T) Value(key interface{}) interface{}

Value is used to carry data across API boundaries. This should be used only for data that is relevant across multiple API boundaries and not just to pass extra parameters to functions and methods. Any type that supports equality can be used as a key, but an unexported type should be used to prevent collisions.

Package Files

Documentation was rendered with GOOS=linux and GOARCH=amd64.

Jump to identifier

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to identifier