Merge pull request #528 from jodh-intel/fix-log-fields

Ensure containerID and sandboxID fields logged as early as possible
This commit is contained in:
James O. D. Hunt 2018-07-31 09:09:29 +01:00 committed by GitHub
commit 17a2fb886f
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
22 changed files with 102 additions and 58 deletions

View File

@ -53,12 +53,17 @@ EXAMPLE:
} }
func delete(containerID string, force bool) error { func delete(containerID string, force bool) error {
kataLog = kataLog.WithField("container", containerID)
setExternalLoggers(kataLog)
// Checks the MUST and MUST NOT from OCI runtime specification // Checks the MUST and MUST NOT from OCI runtime specification
status, sandboxID, err := getExistingContainerInfo(containerID) status, sandboxID, err := getExistingContainerInfo(containerID)
if err != nil { if err != nil {
return err return err
} }
containerID = status.ID
kataLog = kataLog.WithFields(logrus.Fields{ kataLog = kataLog.WithFields(logrus.Fields{
"container": containerID, "container": containerID,
"sandbox": sandboxID, "sandbox": sandboxID,
@ -66,8 +71,6 @@ func delete(containerID string, force bool) error {
setExternalLoggers(kataLog) setExternalLoggers(kataLog)
containerID = status.ID
containerType, err := oci.GetContainerType(status.Annotations) containerType, err := oci.GetContainerType(status.Annotations)
if err != nil { if err != nil {
return err return err

View File

@ -141,6 +141,9 @@ information is displayed once every 5 seconds.`,
return fmt.Errorf("container id cannot be empty") return fmt.Errorf("container id cannot be empty")
} }
kataLog = kataLog.WithField("container", containerID)
setExternalLoggers(kataLog)
duration := context.Duration("interval") duration := context.Duration("interval")
if duration <= 0 { if duration <= 0 {
return fmt.Errorf("duration interval must be greater than 0") return fmt.Errorf("duration interval must be greater than 0")
@ -151,6 +154,8 @@ information is displayed once every 5 seconds.`,
return err return err
} }
containerID = status.ID
kataLog = kataLog.WithFields(logrus.Fields{ kataLog = kataLog.WithFields(logrus.Fields{
"container": containerID, "container": containerID,
"sandbox": sandboxID, "sandbox": sandboxID,

View File

@ -16,7 +16,6 @@ import (
vc "github.com/kata-containers/runtime/virtcontainers" vc "github.com/kata-containers/runtime/virtcontainers"
"github.com/kata-containers/runtime/virtcontainers/pkg/oci" "github.com/kata-containers/runtime/virtcontainers/pkg/oci"
specs "github.com/opencontainers/runtime-spec/specs-go" specs "github.com/opencontainers/runtime-spec/specs-go"
"github.com/sirupsen/logrus"
"github.com/urfave/cli" "github.com/urfave/cli"
) )
@ -184,16 +183,16 @@ func generateExecParams(context *cli.Context, specProcess *oci.CompatOCIProcess)
func execute(context *cli.Context) error { func execute(context *cli.Context) error {
containerID := context.Args().First() containerID := context.Args().First()
kataLog = kataLog.WithField("container", containerID)
setExternalLoggers(kataLog)
status, sandboxID, err := getExistingContainerInfo(containerID) status, sandboxID, err := getExistingContainerInfo(containerID)
if err != nil { if err != nil {
return err return err
} }
kataLog = kataLog.WithFields(logrus.Fields{ kataLog = kataLog.WithField("sandbox", sandboxID)
"container": containerID,
"sandbox": sandboxID,
})
setExternalLoggers(kataLog) setExternalLoggers(kataLog)
// Retrieve OCI spec configuration. // Retrieve OCI spec configuration.
@ -208,6 +207,10 @@ func execute(context *cli.Context) error {
} }
params.cID = status.ID params.cID = status.ID
containerID = params.cID
kataLog = kataLog.WithField("container", containerID)
setExternalLoggers(kataLog)
// container MUST be ready or running. // container MUST be ready or running.
if status.State.State != vc.StateReady && if status.State.State != vc.StateReady &&

View File

@ -91,8 +91,12 @@ var signals = map[string]syscall.Signal{
} }
func kill(containerID, signal string, all bool) error { func kill(containerID, signal string, all bool) error {
kataLog = kataLog.WithField("container", containerID)
setExternalLoggers(kataLog)
// Checks the MUST and MUST NOT from OCI runtime specification // Checks the MUST and MUST NOT from OCI runtime specification
status, sandboxID, err := getExistingContainerInfo(containerID) status, sandboxID, err := getExistingContainerInfo(containerID)
if err != nil { if err != nil {
return err return err
} }

View File

@ -42,6 +42,9 @@ Where "<container-id>" is the container name to be resumed.`,
} }
func toggleContainerPause(containerID string, pause bool) (err error) { func toggleContainerPause(containerID string, pause bool) (err error) {
kataLog = kataLog.WithField("container", containerID)
setExternalLoggers(kataLog)
// Checks the MUST and MUST NOT from OCI runtime specification // Checks the MUST and MUST NOT from OCI runtime specification
status, sandboxID, err := getExistingContainerInfo(containerID) status, sandboxID, err := getExistingContainerInfo(containerID)
if err != nil { if err != nil {

View File

@ -48,6 +48,9 @@ func ps(containerID, format string, args []string) error {
return fmt.Errorf("Missing container ID") return fmt.Errorf("Missing container ID")
} }
kataLog = kataLog.WithField("container", containerID)
setExternalLoggers(kataLog)
// Checks the MUST and MUST NOT from OCI runtime specification // Checks the MUST and MUST NOT from OCI runtime specification
status, sandboxID, err := getExistingContainerInfo(containerID) status, sandboxID, err := getExistingContainerInfo(containerID)
if err != nil { if err != nil {

View File

@ -41,12 +41,17 @@ var startCLICommand = cli.Command{
} }
func start(containerID string) (vc.VCSandbox, error) { func start(containerID string) (vc.VCSandbox, error) {
kataLog = kataLog.WithField("container", containerID)
setExternalLoggers(kataLog)
// Checks the MUST and MUST NOT from OCI runtime specification // Checks the MUST and MUST NOT from OCI runtime specification
status, sandboxID, err := getExistingContainerInfo(containerID) status, sandboxID, err := getExistingContainerInfo(containerID)
if err != nil { if err != nil {
return nil, err return nil, err
} }
containerID = status.ID
kataLog = kataLog.WithFields(logrus.Fields{ kataLog = kataLog.WithFields(logrus.Fields{
"container": containerID, "container": containerID,
"sandbox": sandboxID, "sandbox": sandboxID,
@ -54,8 +59,6 @@ func start(containerID string) (vc.VCSandbox, error) {
setExternalLoggers(kataLog) setExternalLoggers(kataLog)
containerID = status.ID
containerType, err := oci.GetContainerType(status.Annotations) containerType, err := oci.GetContainerType(status.Annotations)
if err != nil { if err != nil {
return nil, err return nil, err

View File

@ -132,6 +132,10 @@ other options are ignored.
} }
containerID := context.Args().First() containerID := context.Args().First()
kataLog = kataLog.WithField("container", containerID)
setExternalLoggers(kataLog)
status, sandboxID, err := getExistingContainerInfo(containerID) status, sandboxID, err := getExistingContainerInfo(containerID)
if err != nil { if err != nil {
return err return err
@ -144,6 +148,8 @@ other options are ignored.
"sandbox": sandboxID, "sandbox": sandboxID,
}) })
setExternalLoggers(kataLog)
// container MUST be running // container MUST be running
if status.State.State != vc.StateRunning { if status.State.State != vc.StateRunning {
return fmt.Errorf("Container %s is not running", containerID) return fmt.Errorf("Container %s is not running", containerID)

View File

@ -19,16 +19,13 @@ func init() {
runtime.LockOSThread() runtime.LockOSThread()
} }
var virtLog = logrus.FieldLogger(logrus.New()) var virtLog = logrus.WithField("source", "virtcontainers")
// SetLogger sets the logger for virtcontainers package. // SetLogger sets the logger for virtcontainers package.
func SetLogger(logger logrus.FieldLogger) { func SetLogger(logger *logrus.Entry) {
fields := logrus.Fields{ fields := virtLog.Data
"source": "virtcontainers",
"arch": runtime.GOARCH,
}
virtLog = logger.WithFields(fields) virtLog = logger.WithFields(fields)
deviceApi.SetLogger(virtLog) deviceApi.SetLogger(virtLog)
} }

View File

@ -265,8 +265,7 @@ func (c *Container) ID() string {
func (c *Container) Logger() *logrus.Entry { func (c *Container) Logger() *logrus.Entry {
return virtLog.WithFields(logrus.Fields{ return virtLog.WithFields(logrus.Fields{
"subsystem": "container", "subsystem": "container",
"container-id": c.id, "sandbox": c.sandboxID,
"sandbox-id": c.sandboxID,
}) })
} }

View File

@ -12,16 +12,17 @@ import (
"github.com/kata-containers/runtime/virtcontainers/device/config" "github.com/kata-containers/runtime/virtcontainers/device/config"
) )
var devLogger = logrus.FieldLogger(logrus.New()) var devLogger = logrus.WithField("subsystem", "device")
// SetLogger sets the logger for device api package. // SetLogger sets the logger for device api package.
func SetLogger(logger logrus.FieldLogger) { func SetLogger(logger *logrus.Entry) {
devLogger = logger fields := devLogger.Data
devLogger = logger.WithFields(fields)
} }
// DeviceLogger returns logger for device management // DeviceLogger returns logger for device management
func DeviceLogger() *logrus.Entry { func DeviceLogger() *logrus.Entry {
return devLogger.WithField("subsystem", "device") return devLogger
} }
// DeviceReceiver is an interface used for accepting devices // DeviceReceiver is an interface used for accepting devices

View File

@ -19,7 +19,7 @@ import (
vc "github.com/kata-containers/runtime/virtcontainers" vc "github.com/kata-containers/runtime/virtcontainers"
) )
var virtcLog = logrus.New() var virtcLog *logrus.Entry
var listFormat = "%s\t%s\t%s\t%s\n" var listFormat = "%s\t%s\t%s\t%s\n"
var statusFormat = "%s\t%s\n" var statusFormat = "%s\t%s\n"
@ -915,14 +915,14 @@ func main() {
if err != nil { if err != nil {
return err return err
} }
virtcLog.Out = f virtcLog.Logger.Out = f
} }
switch context.GlobalString("log-format") { switch context.GlobalString("log-format") {
case "text": case "text":
// retain logrus's default. // retain logrus's default.
case "json": case "json":
virtcLog.Formatter = new(logrus.JSONFormatter) virtcLog.Logger.Formatter = new(logrus.JSONFormatter)
default: default:
return fmt.Errorf("unknown log-format %q", context.GlobalString("log-format")) return fmt.Errorf("unknown log-format %q", context.GlobalString("log-format"))
} }

View File

@ -22,7 +22,7 @@ type VCImpl struct {
} }
// SetLogger implements the VC function of the same name. // SetLogger implements the VC function of the same name.
func (impl *VCImpl) SetLogger(logger logrus.FieldLogger) { func (impl *VCImpl) SetLogger(logger *logrus.Entry) {
SetLogger(logger) SetLogger(logger)
} }

View File

@ -15,7 +15,7 @@ import (
// VC is the Virtcontainers interface // VC is the Virtcontainers interface
type VC interface { type VC interface {
SetLogger(logger logrus.FieldLogger) SetLogger(logger *logrus.Entry)
SetFactory(Factory) SetFactory(Factory)
CreateSandbox(sandboxConfig SandboxConfig) (VCSandbox, error) CreateSandbox(sandboxConfig SandboxConfig) (VCSandbox, error)

View File

@ -469,7 +469,7 @@ func (k *kataAgent) startProxy(sandbox *Sandbox) error {
proxyParams := proxyParams{ proxyParams := proxyParams{
agentURL: agentURL, agentURL: agentURL,
logger: k.Logger().WithField("sandbox-id", sandbox.id), logger: k.Logger().WithField("sandbox", sandbox.id),
} }
// Start the proxy here // Start the proxy here
@ -494,7 +494,7 @@ func (k *kataAgent) startProxy(sandbox *Sandbox) error {
} }
k.Logger().WithFields(logrus.Fields{ k.Logger().WithFields(logrus.Fields{
"sandbox-id": sandbox.id, "sandbox": sandbox.id,
"proxy-pid": pid, "proxy-pid": pid,
"proxy-url": uri, "proxy-url": uri,
}).Info("proxy started") }).Info("proxy started")

View File

@ -219,9 +219,10 @@ func networkLogger() *logrus.Entry {
// Attach for virtual endpoint bridges the network pair and adds the // Attach for virtual endpoint bridges the network pair and adds the
// tap interface of the network pair to the hypervisor. // tap interface of the network pair to the hypervisor.
func (endpoint *VirtualEndpoint) Attach(h hypervisor) error { func (endpoint *VirtualEndpoint) Attach(h hypervisor) error {
networkLogger().Info("Attaching virtual endpoint") networkLogger().WithField("endpoint-type", "virtual").Info("Attaching endpoint")
if err := xconnectVMNetwork(&(endpoint.NetPair), true); err != nil { if err := xconnectVMNetwork(&(endpoint.NetPair), true); err != nil {
networkLogger().WithError(err).Error("Error bridging virtual ep") networkLogger().WithError(err).Error("Error bridging virtual endpoint")
return err return err
} }
@ -237,7 +238,7 @@ func (endpoint *VirtualEndpoint) Detach(netNsCreated bool, netNsPath string) err
return nil return nil
} }
networkLogger().Info("Detaching virtual endpoint") networkLogger().WithField("endpoint-type", "virtual").Info("Detaching endpoint")
return doNetNS(netNsPath, func(_ ns.NetNS) error { return doNetNS(netNsPath, func(_ ns.NetNS) error {
return xconnectVMNetwork(&(endpoint.NetPair), false) return xconnectVMNetwork(&(endpoint.NetPair), false)
@ -271,7 +272,7 @@ func (endpoint *VhostUserEndpoint) SetProperties(properties NetworkInfo) {
// Attach for vhostuser endpoint // Attach for vhostuser endpoint
func (endpoint *VhostUserEndpoint) Attach(h hypervisor) error { func (endpoint *VhostUserEndpoint) Attach(h hypervisor) error {
networkLogger().Info("Attaching vhostuser based endpoint") networkLogger().WithField("endpoint-type", "vhostuser").Info("Attaching endpoint")
// Generate a unique ID to be used for hypervisor commandline fields // Generate a unique ID to be used for hypervisor commandline fields
randBytes, err := utils.GenerateRandomBytes(8) randBytes, err := utils.GenerateRandomBytes(8)
@ -291,7 +292,7 @@ func (endpoint *VhostUserEndpoint) Attach(h hypervisor) error {
// Detach for vhostuser endpoint // Detach for vhostuser endpoint
func (endpoint *VhostUserEndpoint) Detach(netNsCreated bool, netNsPath string) error { func (endpoint *VhostUserEndpoint) Detach(netNsCreated bool, netNsPath string) error {
networkLogger().Info("Detaching vhostuser based endpoint") networkLogger().WithField("endpoint-type", "vhostuser").Info("Detaching endpoint")
return nil return nil
} }
@ -335,7 +336,7 @@ func (endpoint *PhysicalEndpoint) SetProperties(properties NetworkInfo) {
// Attach for physical endpoint binds the physical network interface to // Attach for physical endpoint binds the physical network interface to
// vfio-pci and adds device to the hypervisor with vfio-passthrough. // vfio-pci and adds device to the hypervisor with vfio-passthrough.
func (endpoint *PhysicalEndpoint) Attach(h hypervisor) error { func (endpoint *PhysicalEndpoint) Attach(h hypervisor) error {
networkLogger().Info("Attaching physical endpoint") networkLogger().WithField("endpoint-type", "physical").Info("Attaching endpoint")
// Unbind physical interface from host driver and bind to vfio // Unbind physical interface from host driver and bind to vfio
// so that it can be passed to qemu. // so that it can be passed to qemu.
@ -356,7 +357,7 @@ func (endpoint *PhysicalEndpoint) Detach(netNsCreated bool, netNsPath string) er
// Bind back the physical network interface to host. // Bind back the physical network interface to host.
// We need to do this even if a new network namespace has not // We need to do this even if a new network namespace has not
// been created by virtcontainers. // been created by virtcontainers.
networkLogger().Info("Detaching physical endpoint") networkLogger().WithField("endpoint-type", "physical").Info("Detaching endpoint")
// We do not need to enter the network namespace to bind back the // We do not need to enter the network namespace to bind back the
// physical interface to host driver. // physical interface to host driver.
@ -489,7 +490,10 @@ func (n *NetworkNamespace) UnmarshalJSON(b []byte) error {
} }
endpoints = append(endpoints, &endpoint) endpoints = append(endpoints, &endpoint)
virtLog.Infof("Physical endpoint unmarshalled [%v]", endpoint) networkLogger().WithFields(logrus.Fields{
"endpoint": endpoint,
"endpoint-type": "physical",
}).Info("endpoint unmarshalled")
case VirtualEndpointType: case VirtualEndpointType:
var endpoint VirtualEndpoint var endpoint VirtualEndpoint
@ -499,7 +503,10 @@ func (n *NetworkNamespace) UnmarshalJSON(b []byte) error {
} }
endpoints = append(endpoints, &endpoint) endpoints = append(endpoints, &endpoint)
virtLog.Infof("Virtual endpoint unmarshalled [%v]", endpoint) networkLogger().WithFields(logrus.Fields{
"endpoint": endpoint,
"endpoint-type": "virtual",
}).Info("endpoint unmarshalled")
case VhostUserEndpointType: case VhostUserEndpointType:
var endpoint VhostUserEndpoint var endpoint VhostUserEndpoint
@ -509,10 +516,13 @@ func (n *NetworkNamespace) UnmarshalJSON(b []byte) error {
} }
endpoints = append(endpoints, &endpoint) endpoints = append(endpoints, &endpoint)
virtLog.Infof("VhostUser endpoint unmarshalled [%v]", endpoint) networkLogger().WithFields(logrus.Fields{
"endpoint": endpoint,
"endpoint-type": "vhostuser",
}).Info("endpoint unmarshalled")
default: default:
virtLog.Errorf("Unknown endpoint type received %s\n", e.Type) networkLogger().WithField("endpoint-type", e.Type).Error("Ignoring unknown endpoint type")
} }
} }
@ -1010,7 +1020,7 @@ func untapNetworkPair(netPair NetworkInterfacePair) error {
vethLink, err := getLinkByName(netHandle, netPair.VirtIface.Name, &netlink.Veth{}) vethLink, err := getLinkByName(netHandle, netPair.VirtIface.Name, &netlink.Veth{})
if err != nil { if err != nil {
// The veth pair is not totally managed by virtcontainers // The veth pair is not totally managed by virtcontainers
virtLog.Warnf("Could not get veth interface %s: %s", netPair.VirtIface.Name, err) networkLogger().WithError(err).WithField("veth-name", netPair.VirtIface.Name).Warn("Could not get veth interface")
} else { } else {
if err := netHandle.LinkSetDown(vethLink); err != nil { if err := netHandle.LinkSetDown(vethLink); err != nil {
return fmt.Errorf("Could not disable veth %s: %s", netPair.VirtIface.Name, err) return fmt.Errorf("Could not disable veth %s: %s", netPair.VirtIface.Name, err)
@ -1062,7 +1072,7 @@ func unBridgeNetworkPair(netPair NetworkInterfacePair) error {
vethLink, err := getLinkByName(netHandle, netPair.VirtIface.Name, &netlink.Veth{}) vethLink, err := getLinkByName(netHandle, netPair.VirtIface.Name, &netlink.Veth{})
if err != nil { if err != nil {
// The veth pair is not totally managed by virtcontainers // The veth pair is not totally managed by virtcontainers
virtLog.WithError(err).Warn("Could not get veth interface") networkLogger().WithError(err).Warn("Could not get veth interface")
} else { } else {
if err := netHandle.LinkSetDown(vethLink); err != nil { if err := netHandle.LinkSetDown(vethLink); err != nil {
return fmt.Errorf("Could not disable veth %s: %s", netPair.VirtIface.Name, err) return fmt.Errorf("Could not disable veth %s: %s", netPair.VirtIface.Name, err)

View File

@ -124,7 +124,10 @@ var hyperLog = logrus.FieldLogger(logrus.New())
// SetLogger sets the logger for hyperstart package. // SetLogger sets the logger for hyperstart package.
func SetLogger(logger logrus.FieldLogger) { func SetLogger(logger logrus.FieldLogger) {
hyperLog = logger.WithField("source", "virtcontainers/hyperstart") hyperLog = logger.WithFields(logrus.Fields{
"source": "virtcontainers",
"subsystem": "hyperstart",
})
} }
// NewHyperstart returns a new hyperstart structure. // NewHyperstart returns a new hyperstart structure.

View File

@ -128,11 +128,15 @@ func (config *RuntimeConfig) AddKernelParam(p vc.Param) error {
return config.HypervisorConfig.AddKernelParam(p) return config.HypervisorConfig.AddKernelParam(p)
} }
var ociLog = logrus.FieldLogger(logrus.New()) var ociLog = logrus.WithFields(logrus.Fields{
"source": "virtcontainers",
"subsystem": "oci",
})
// SetLogger sets the logger for oci package. // SetLogger sets the logger for oci package.
func SetLogger(logger logrus.FieldLogger) { func SetLogger(logger *logrus.Entry) {
ociLog = logger.WithField("source", "virtcontainers/oci") fields := ociLog.Data
ociLog = logger.WithFields(fields)
} }
func cmdEnvs(spec CompatOCISpec, envs []vc.EnvVar) []vc.EnvVar { func cmdEnvs(spec CompatOCISpec, envs []vc.EnvVar) []vc.EnvVar {

View File

@ -29,7 +29,7 @@ import (
const mockErrorPrefix = "vcmock forced failure" const mockErrorPrefix = "vcmock forced failure"
// SetLogger implements the VC function of the same name. // SetLogger implements the VC function of the same name.
func (m *VCMock) SetLogger(logger logrus.FieldLogger) { func (m *VCMock) SetLogger(logger *logrus.Entry) {
if m.SetLoggerFunc != nil { if m.SetLoggerFunc != nil {
m.SetLoggerFunc(logger) m.SetLoggerFunc(logger)
} }

View File

@ -98,7 +98,7 @@ func TestVCMockSetLogger(t *testing.T) {
m := &VCMock{} m := &VCMock{}
assert.Nil(m.SetLoggerFunc) assert.Nil(m.SetLoggerFunc)
logger := logrus.New() logger := logrus.NewEntry(logrus.New())
assert.Equal(loggerTriggered, 0) assert.Equal(loggerTriggered, 0)
m.SetLogger(logger) m.SetLogger(logger)

View File

@ -484,7 +484,7 @@ func (s *Sandbox) ID() string {
func (s *Sandbox) Logger() *logrus.Entry { func (s *Sandbox) Logger() *logrus.Entry {
return virtLog.WithFields(logrus.Fields{ return virtLog.WithFields(logrus.Fields{
"subsystem": "sandbox", "subsystem": "sandbox",
"sandbox-id": s.id, "sandbox": s.id,
}) })
} }
@ -827,7 +827,7 @@ func (s *Sandbox) storeSandbox() error {
// fetchSandbox fetches a sandbox config from a sandbox ID and returns a sandbox. // fetchSandbox fetches a sandbox config from a sandbox ID and returns a sandbox.
func fetchSandbox(sandboxID string) (sandbox *Sandbox, err error) { func fetchSandbox(sandboxID string) (sandbox *Sandbox, err error) {
virtLog.WithField("sandbox-id", sandboxID).Info("fetch sandbox") virtLog.Info("fetch sandbox")
if sandboxID == "" { if sandboxID == "" {
return nil, errNeedSandboxID return nil, errNeedSandboxID
} }

View File

@ -66,11 +66,11 @@ func TestMain(m *testing.M) {
flag.Parse() flag.Parse()
logger := logrus.New() logger := logrus.NewEntry(logrus.New())
logger.Level = logrus.ErrorLevel logger.Logger.Level = logrus.ErrorLevel
for _, arg := range flag.Args() { for _, arg := range flag.Args() {
if arg == "debug-logs" { if arg == "debug-logs" {
logger.Level = logrus.DebugLevel logger.Logger.Level = logrus.DebugLevel
} }
} }
SetLogger(logger) SetLogger(logger)