func (s *Secret) TokenTTL() (time.Duration, error) {
	if s == nil {
		return 0, nil
	}
	if s.Auth != nil && s.Auth.LeaseDuration > 0 {
		return time.Duration(s.Auth.LeaseDuration) * time.Second, nil
	}
	if s.Data == nil || s.Data["ttl"] == nil {
		return 0, nil
	}
	ttl, err := parseutil.ParseDurationSecond(s.Data["ttl"])
	if err != nil {
		return 0, err
	}
	return ttl, nil
}
TokenTTL returns the standardized remaining token TTL for the given secret.
If the secret is nil or does not contain a TTL, this returns 0.
package api
import (
	"bytes"
	"fmt"
	"io"
	"time"
	"github.com/hashicorp/errwrap"
	"github.com/hashicorp/vault/sdk/helper/jsonutil"
	"github.com/hashicorp/vault/sdk/helper/parseutil"
)
type Secret struct {
	RequestID string `json:"request_id"`
	LeaseID       string `json:"lease_id"`
	LeaseDuration int    `json:"lease_duration"`
	Renewable     bool   `json:"renewable"`
	Data map[string]interface{} `json:"data"`
	Warnings []string `json:"warnings"`
	Auth *SecretAuth `json:"auth,omitempty"`
	WrapInfo *SecretWrapInfo `json:"wrap_info,omitempty"`
}
func (s *Secret) TokenID() (string, error) {
	if s == nil {
		return "", nil
	}
	if s.Auth != nil && len(s.Auth.ClientToken) > 0 {
		return s.Auth.ClientToken, nil
	}
	if s.Data == nil || s.Data["id"] == nil {
		return "", nil
	}
	id, ok := s.Data["id"].(string)
	if !ok {
		return "", fmt.Errorf("token found but in the wrong format")
	}
	return id, nil
}
func (s *Secret) TokenAccessor() (string, error) {
	if s == nil {
		return "", nil
	}
	if s.Auth != nil && len(s.Auth.Accessor) > 0 {
		return s.Auth.Accessor, nil
	}
	if s.Data == nil || s.Data["accessor"] == nil {
		return "", nil
	}
	accessor, ok := s.Data["accessor"].(string)
	if !ok {
		return "", fmt.Errorf("token found but in the wrong format")
	}
	return accessor, nil
}
func (s *Secret) TokenRemainingUses() (int, error) {
	if s == nil || s.Data == nil || s.Data["num_uses"] == nil {
		return -1, nil
	}
	uses, err := parseutil.ParseInt(s.Data["num_uses"])
	if err != nil {
		return 0, err
	}
	return int(uses), nil
}
func (s *Secret) TokenPolicies() ([]string, error) {
	if s == nil {
		return nil, nil
	}
	if s.Auth != nil && len(s.Auth.Policies) > 0 {
		return s.Auth.Policies, nil
	}
	if s.Data == nil || s.Data["policies"] == nil {
		return nil, nil
	}
	var tokenPolicies []string
	{
		_, ok := s.Data["policies"]
		if !ok {
			goto TOKEN_DONE
		}
		sList, ok := s.Data["policies"].([]string)
		if ok {
			tokenPolicies = sList
			goto TOKEN_DONE
		}
		list, ok := s.Data["policies"].([]interface{})
		if !ok {
			return nil, fmt.Errorf("unable to convert token policies to expected format")
		}
		for _, v := range list {
			p, ok := v.(string)
			if !ok {
				return nil, fmt.Errorf("unable to convert policy %v to string", v)
			}
			tokenPolicies = append(tokenPolicies, p)
		}
	}
TOKEN_DONE:
	var identityPolicies []string
	{
		_, ok := s.Data["identity_policies"]
		if !ok {
			goto DONE
		}
		sList, ok := s.Data["identity_policies"].([]string)
		if ok {
			identityPolicies = sList
			goto DONE
		}
		list, ok := s.Data["identity_policies"].([]interface{})
		if !ok {
			return nil, fmt.Errorf("unable to convert identity policies to expected format")
		}
		for _, v := range list {
			p, ok := v.(string)
			if !ok {
				return nil, fmt.Errorf("unable to convert policy %v to string", v)
			}
			identityPolicies = append(identityPolicies, p)
		}
	}
DONE:
	if s.Auth == nil {
		s.Auth = &SecretAuth{}
	}
	policies := append(tokenPolicies, identityPolicies...)
	s.Auth.TokenPolicies = tokenPolicies
	s.Auth.IdentityPolicies = identityPolicies
	s.Auth.Policies = policies
	return policies, nil
}
func (s *Secret) TokenMetadata() (map[string]string, error) {
	if s == nil {
		return nil, nil
	}
	if s.Auth != nil && len(s.Auth.Metadata) > 0 {
		return s.Auth.Metadata, nil
	}
	if s.Data == nil || (s.Data["metadata"] == nil && s.Data["meta"] == nil) {
		return nil, nil
	}
	data, ok := s.Data["metadata"].(map[string]interface{})
	if !ok {
		data, ok = s.Data["meta"].(map[string]interface{})
		if !ok {
			return nil, fmt.Errorf("unable to convert metadata field to expected format")
		}
	}
	metadata := make(map[string]string, len(data))
	for k, v := range data {
		typed, ok := v.(string)
		if !ok {
			return nil, fmt.Errorf("unable to convert metadata value %v to string", v)
		}
		metadata[k] = typed
	}
	return metadata, nil
}
func (s *Secret) TokenIsRenewable() (bool, error) {
	if s == nil {
		return false, nil
	}
	if s.Auth != nil && s.Auth.Renewable {
		return s.Auth.Renewable, nil
	}
	if s.Data == nil || s.Data["renewable"] == nil {
		return false, nil
	}
	renewable, err := parseutil.ParseBool(s.Data["renewable"])
	if err != nil {
		return false, errwrap.Wrapf("could not convert renewable value to a boolean: {{err}}", err)
	}
	return renewable, nil
}