// Copyright 2015 The Vanadium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.

// This file was auto-generated by the vanadium vdl tool.
// Package: role

// Package role defines an interface for requesting blessings from a role
// account server.
package role

import (
	"v.io/v23"
	"v.io/v23/context"
	"v.io/v23/rpc"
	"v.io/v23/security"
)

var _ = __VDLInit() // Must be first; see __VDLInit comments for details.

//////////////////////////////////////////////////
// Const definitions

// Role.SeekBlessings will return an error if the requestor does not present
// blessings that end in this suffix.
const RoleSuffix = "_role"

//////////////////////////////////////////////////
// Interface definitions

// RoleClientMethods is the client interface
// containing Role methods.
//
// Role is an interface to request blessings from a role account server. The
// returned blessings are bound to the client's public key thereby authorizing
// the client to acquire the role. The server may tie the returned blessings
// with the client's presented blessing name in order to maintain audit
// information in the blessing.
//
// In order to avoid granting role blessings to all delegates of a principal,
// the role server requires that each authorized blessing presented by the
// client have the string "_role" as suffix.
type RoleClientMethods interface {
	SeekBlessings(*context.T, ...rpc.CallOpt) (security.Blessings, error)
}

// RoleClientStub adds universal methods to RoleClientMethods.
type RoleClientStub interface {
	RoleClientMethods
	rpc.UniversalServiceMethods
}

// RoleClient returns a client stub for Role.
func RoleClient(name string) RoleClientStub {
	return implRoleClientStub{name}
}

type implRoleClientStub struct {
	name string
}

func (c implRoleClientStub) SeekBlessings(ctx *context.T, opts ...rpc.CallOpt) (o0 security.Blessings, err error) {
	err = v23.GetClient(ctx).Call(ctx, c.name, "SeekBlessings", nil, []interface{}{&o0}, opts...)
	return
}

// RoleServerMethods is the interface a server writer
// implements for Role.
//
// Role is an interface to request blessings from a role account server. The
// returned blessings are bound to the client's public key thereby authorizing
// the client to acquire the role. The server may tie the returned blessings
// with the client's presented blessing name in order to maintain audit
// information in the blessing.
//
// In order to avoid granting role blessings to all delegates of a principal,
// the role server requires that each authorized blessing presented by the
// client have the string "_role" as suffix.
type RoleServerMethods interface {
	SeekBlessings(*context.T, rpc.ServerCall) (security.Blessings, error)
}

// RoleServerStubMethods is the server interface containing
// Role methods, as expected by rpc.Server.
// There is no difference between this interface and RoleServerMethods
// since there are no streaming methods.
type RoleServerStubMethods RoleServerMethods

// RoleServerStub adds universal methods to RoleServerStubMethods.
type RoleServerStub interface {
	RoleServerStubMethods
	// Describe the Role interfaces.
	Describe__() []rpc.InterfaceDesc
}

// RoleServer returns a server stub for Role.
// It converts an implementation of RoleServerMethods into
// an object that may be used by rpc.Server.
func RoleServer(impl RoleServerMethods) RoleServerStub {
	stub := implRoleServerStub{
		impl: impl,
	}
	// Initialize GlobState; always check the stub itself first, to handle the
	// case where the user has the Glob method defined in their VDL source.
	if gs := rpc.NewGlobState(stub); gs != nil {
		stub.gs = gs
	} else if gs := rpc.NewGlobState(impl); gs != nil {
		stub.gs = gs
	}
	return stub
}

type implRoleServerStub struct {
	impl RoleServerMethods
	gs   *rpc.GlobState
}

func (s implRoleServerStub) SeekBlessings(ctx *context.T, call rpc.ServerCall) (security.Blessings, error) {
	return s.impl.SeekBlessings(ctx, call)
}

func (s implRoleServerStub) Globber() *rpc.GlobState {
	return s.gs
}

func (s implRoleServerStub) Describe__() []rpc.InterfaceDesc {
	return []rpc.InterfaceDesc{RoleDesc}
}

// RoleDesc describes the Role interface.
var RoleDesc rpc.InterfaceDesc = descRole

// descRole hides the desc to keep godoc clean.
var descRole = rpc.InterfaceDesc{
	Name:    "Role",
	PkgPath: "v.io/x/ref/services/role",
	Doc:     "// Role is an interface to request blessings from a role account server. The\n// returned blessings are bound to the client's public key thereby authorizing\n// the client to acquire the role. The server may tie the returned blessings\n// with the client's presented blessing name in order to maintain audit\n// information in the blessing.\n//\n// In order to avoid granting role blessings to all delegates of a principal,\n// the role server requires that each authorized blessing presented by the\n// client have the string \"_role\" as suffix.",
	Methods: []rpc.MethodDesc{
		{
			Name: "SeekBlessings",
			OutArgs: []rpc.ArgDesc{
				{"", ``}, // security.Blessings
			},
		},
	},
}

var __VDLInitCalled bool

// __VDLInit performs vdl initialization.  It is safe to call multiple times.
// If you have an init ordering issue, just insert the following line verbatim
// into your source files in this package, right after the "package foo" clause:
//
//    var _ = __VDLInit()
//
// The purpose of this function is to ensure that vdl initialization occurs in
// the right order, and very early in the init sequence.  In particular, vdl
// registration and package variable initialization needs to occur before
// functions like vdl.TypeOf will work properly.
//
// This function returns a dummy value, so that it can be used to initialize the
// first var in the file, to take advantage of Go's defined init order.
func __VDLInit() struct{} {
	if __VDLInitCalled {
		return struct{}{}
	}
	__VDLInitCalled = true

	return struct{}{}
}
