Updating cadvisor deps.

This commit is contained in:
Vishnu Kannan 2015-04-09 15:42:18 -07:00
parent 72fed9a2f3
commit f39908ebf4
7 changed files with 156 additions and 134 deletions

64
Godeps/Godeps.json generated
View File

@ -212,83 +212,83 @@
}, },
{ {
"ImportPath": "github.com/google/cadvisor/api", "ImportPath": "github.com/google/cadvisor/api",
"Comment": "0.11.0", "Comment": "0.11.0-14-ga1c6887",
"Rev": "318252a107983f9d9fc109cc97f8140c37ec8233" "Rev": "a1c688751c991f5002d4d36e8e0682186bc78566"
}, },
{ {
"ImportPath": "github.com/google/cadvisor/container", "ImportPath": "github.com/google/cadvisor/container",
"Comment": "0.11.0", "Comment": "0.11.0-14-ga1c6887",
"Rev": "318252a107983f9d9fc109cc97f8140c37ec8233" "Rev": "a1c688751c991f5002d4d36e8e0682186bc78566"
}, },
{ {
"ImportPath": "github.com/google/cadvisor/events", "ImportPath": "github.com/google/cadvisor/events",
"Comment": "0.11.0", "Comment": "0.11.0-14-ga1c6887",
"Rev": "318252a107983f9d9fc109cc97f8140c37ec8233" "Rev": "a1c688751c991f5002d4d36e8e0682186bc78566"
}, },
{ {
"ImportPath": "github.com/google/cadvisor/fs", "ImportPath": "github.com/google/cadvisor/fs",
"Comment": "0.11.0", "Comment": "0.11.0-14-ga1c6887",
"Rev": "318252a107983f9d9fc109cc97f8140c37ec8233" "Rev": "a1c688751c991f5002d4d36e8e0682186bc78566"
}, },
{ {
"ImportPath": "github.com/google/cadvisor/healthz", "ImportPath": "github.com/google/cadvisor/healthz",
"Comment": "0.11.0", "Comment": "0.11.0-14-ga1c6887",
"Rev": "318252a107983f9d9fc109cc97f8140c37ec8233" "Rev": "a1c688751c991f5002d4d36e8e0682186bc78566"
}, },
{ {
"ImportPath": "github.com/google/cadvisor/http", "ImportPath": "github.com/google/cadvisor/http",
"Comment": "0.11.0", "Comment": "0.11.0-14-ga1c6887",
"Rev": "318252a107983f9d9fc109cc97f8140c37ec8233" "Rev": "a1c688751c991f5002d4d36e8e0682186bc78566"
}, },
{ {
"ImportPath": "github.com/google/cadvisor/info/v1", "ImportPath": "github.com/google/cadvisor/info/v1",
"Comment": "0.11.0", "Comment": "0.11.0-14-ga1c6887",
"Rev": "318252a107983f9d9fc109cc97f8140c37ec8233" "Rev": "a1c688751c991f5002d4d36e8e0682186bc78566"
}, },
{ {
"ImportPath": "github.com/google/cadvisor/info/v2", "ImportPath": "github.com/google/cadvisor/info/v2",
"Comment": "0.11.0", "Comment": "0.11.0-14-ga1c6887",
"Rev": "318252a107983f9d9fc109cc97f8140c37ec8233" "Rev": "a1c688751c991f5002d4d36e8e0682186bc78566"
}, },
{ {
"ImportPath": "github.com/google/cadvisor/manager", "ImportPath": "github.com/google/cadvisor/manager",
"Comment": "0.11.0", "Comment": "0.11.0-14-ga1c6887",
"Rev": "318252a107983f9d9fc109cc97f8140c37ec8233" "Rev": "a1c688751c991f5002d4d36e8e0682186bc78566"
}, },
{ {
"ImportPath": "github.com/google/cadvisor/metrics", "ImportPath": "github.com/google/cadvisor/metrics",
"Comment": "0.11.0", "Comment": "0.11.0-14-ga1c6887",
"Rev": "318252a107983f9d9fc109cc97f8140c37ec8233" "Rev": "a1c688751c991f5002d4d36e8e0682186bc78566"
}, },
{ {
"ImportPath": "github.com/google/cadvisor/pages", "ImportPath": "github.com/google/cadvisor/pages",
"Comment": "0.11.0", "Comment": "0.11.0-14-ga1c6887",
"Rev": "318252a107983f9d9fc109cc97f8140c37ec8233" "Rev": "a1c688751c991f5002d4d36e8e0682186bc78566"
}, },
{ {
"ImportPath": "github.com/google/cadvisor/storage", "ImportPath": "github.com/google/cadvisor/storage",
"Comment": "0.11.0", "Comment": "0.11.0-14-ga1c6887",
"Rev": "318252a107983f9d9fc109cc97f8140c37ec8233" "Rev": "a1c688751c991f5002d4d36e8e0682186bc78566"
}, },
{ {
"ImportPath": "github.com/google/cadvisor/summary", "ImportPath": "github.com/google/cadvisor/summary",
"Comment": "0.11.0", "Comment": "0.11.0-14-ga1c6887",
"Rev": "318252a107983f9d9fc109cc97f8140c37ec8233" "Rev": "a1c688751c991f5002d4d36e8e0682186bc78566"
}, },
{ {
"ImportPath": "github.com/google/cadvisor/utils", "ImportPath": "github.com/google/cadvisor/utils",
"Comment": "0.11.0", "Comment": "0.11.0-14-ga1c6887",
"Rev": "318252a107983f9d9fc109cc97f8140c37ec8233" "Rev": "a1c688751c991f5002d4d36e8e0682186bc78566"
}, },
{ {
"ImportPath": "github.com/google/cadvisor/validate", "ImportPath": "github.com/google/cadvisor/validate",
"Comment": "0.11.0", "Comment": "0.11.0-14-ga1c6887",
"Rev": "318252a107983f9d9fc109cc97f8140c37ec8233" "Rev": "a1c688751c991f5002d4d36e8e0682186bc78566"
}, },
{ {
"ImportPath": "github.com/google/cadvisor/version", "ImportPath": "github.com/google/cadvisor/version",
"Comment": "0.11.0", "Comment": "0.11.0-14-ga1c6887",
"Rev": "318252a107983f9d9fc109cc97f8140c37ec8233" "Rev": "a1c688751c991f5002d4d36e8e0682186bc78566"
}, },
{ {
"ImportPath": "github.com/google/gofuzz", "ImportPath": "github.com/google/gofuzz",

View File

@ -25,64 +25,28 @@ import (
info "github.com/google/cadvisor/info/v1" info "github.com/google/cadvisor/info/v1"
) )
// EventManager is implemented by Events. It provides two ways to monitor
// events and one way to add events
type EventManager interface {
// Watch checks if events fed to it by the caller of AddEvent satisfy the
// request and if so sends the event back to the caller on outChannel
WatchEvents(request *Request) (*EventChannel, error)
// GetEvents() returns a slice of all events detected that have passed
// the *Request object parameters to the caller
GetEvents(request *Request) (EventSlice, error)
// AddEvent allows the caller to add an event to an EventManager
// object
AddEvent(e *info.Event) error
// Removes a watch instance from the EventManager's watchers map
StopWatch(watch_id int)
}
// Events holds a slice of *Event objects with a potential field
// that caps the number of events held. It is an implementation of the
// EventManager interface
type events struct {
// eventlist holds the complete set of events found over an
// EventManager events instantiation.
eventlist EventSlice
// the slice of watch pointers allows the EventManager access to channels
// linked to different calls of WatchEvents. When new events are found that
// satisfy the request of a given watch object in watchers, the event
// is sent over the channel to that caller of WatchEvents
watchers map[int]*watch
// lock that blocks eventlist from being accessed until a writer releases it
eventsLock sync.RWMutex
// lock that blocks watchers from being accessed until a writer releases it
watcherLock sync.RWMutex
// receives notices when a watch event ends and needs to be removed from
// the watchers list
lastId int
}
// initialized by a call to WatchEvents(), a watch struct will then be added
// to the events slice of *watch objects. When AddEvent() finds an event that
// satisfies the request parameter of a watch object in events.watchers,
// it will send that event out over the watch object's channel. The caller that
// called WatchEvents will receive the event over the channel provided to
// WatchEvents
type watch struct {
// request specifies all the parameters that events sent through the
// channel must satisfy. Specified by the creator of the watch object
request *Request
// a channel created by the caller through which events satisfying the
// request are sent to the caller
eventChannel *EventChannel
// unique identifier of a watch that is used as a key in events' watchers
// map
id int
}
// typedef of a slice of Event pointers
type EventSlice []*info.Event type EventSlice []*info.Event
// functions necessary to implement the sort interface on the Events struct
func (e EventSlice) Len() int {
return len(e)
}
func (e EventSlice) Swap(i, j int) {
e[i], e[j] = e[j], e[i]
}
func (e EventSlice) Less(i, j int) bool {
return e[i].Timestamp.Before(e[j].Timestamp)
}
type EventChannel struct {
// Watch ID. Can be used by the caller to request cancellation of watch events.
watchId int
// Channel on which the caller can receive watch events.
channel chan *info.Event
}
// Request holds a set of parameters by which Event objects may be screened. // Request holds a set of parameters by which Event objects may be screened.
// The caller may want events that occurred within a specific timeframe // The caller may want events that occurred within a specific timeframe
// or of a certain type, which may be specified in the *Request object // or of a certain type, which may be specified in the *Request object
@ -97,7 +61,7 @@ type Request struct {
// EventType is a map that specifies the type(s) of events wanted // EventType is a map that specifies the type(s) of events wanted
EventType map[info.EventType]bool EventType map[info.EventType]bool
// allows the caller to put a limit on how many // allows the caller to put a limit on how many
// events they receive. If there are more events than MaxEventsReturned // events to receive. If there are more events than MaxEventsReturned
// then the most chronologically recent events in the time period // then the most chronologically recent events in the time period
// specified are returned. Must be >= 1 // specified are returned. Must be >= 1
MaxEventsReturned int MaxEventsReturned int
@ -108,9 +72,50 @@ type Request struct {
IncludeSubcontainers bool IncludeSubcontainers bool
} }
type EventChannel struct { // EventManager is implemented by Events. It provides two ways to monitor
watchId int // events and one way to add events
channel chan *info.Event type EventManager interface {
// WatchEvents() allows a caller to register for receiving events based on the specified request.
// On successful registration, an EventChannel object is returned.
WatchEvents(request *Request) (*EventChannel, error)
// GetEvents() returns all detected events based on the filters specified in request.
GetEvents(request *Request) (EventSlice, error)
// AddEvent allows the caller to add an event to an EventManager
// object
AddEvent(e *info.Event) error
// Cancels a previously requested watch event.
StopWatch(watch_id int)
}
// events provides an implementation for the EventManager interface.
type events struct {
// eventList holds the complete set of events found over an
// EventManager events instantiation.
eventList EventSlice
// map of registered watchers keyed by watch id.
watchers map[int]*watch
// lock guarding the eventList.
eventsLock sync.RWMutex
// lock guarding watchers.
watcherLock sync.RWMutex
// last allocated watch id.
lastId int
}
// initialized by a call to WatchEvents(), a watch struct will then be added
// to the events slice of *watch objects. When AddEvent() finds an event that
// satisfies the request parameter of a watch object in events.watchers,
// it will send that event out over the watch object's channel. The caller that
// called WatchEvents will receive the event over the channel provided to
// WatchEvents
type watch struct {
// request parameters passed in by the caller of WatchEvents()
request *Request
// a channel used to send event back to the caller.
eventChannel *EventChannel
// unique identifier of a watch that is used as a key in events' watchers
// map
id int
} }
func NewEventChannel(watchId int) *EventChannel { func NewEventChannel(watchId int) *EventChannel {
@ -123,7 +128,7 @@ func NewEventChannel(watchId int) *EventChannel {
// returns a pointer to an initialized Events object // returns a pointer to an initialized Events object
func NewEventManager() *events { func NewEventManager() *events {
return &events{ return &events{
eventlist: make(EventSlice, 0), eventList: make(EventSlice, 0),
watchers: make(map[int]*watch), watchers: make(map[int]*watch),
} }
} }
@ -153,21 +158,6 @@ func (self *EventChannel) GetWatchId() int {
return self.watchId return self.watchId
} }
// function necessary to implement the sort interface on the Events struct
func (e EventSlice) Len() int {
return len(e)
}
// function necessary to implement the sort interface on the Events struct
func (e EventSlice) Swap(i, j int) {
e[i], e[j] = e[j], e[i]
}
// function necessary to implement the sort interface on the Events struct
func (e EventSlice) Less(i, j int) bool {
return e[i].Timestamp.Before(e[j].Timestamp)
}
// sorts and returns up to the last MaxEventsReturned chronological elements // sorts and returns up to the last MaxEventsReturned chronological elements
func getMaxEventsReturned(request *Request, eSlice EventSlice) EventSlice { func getMaxEventsReturned(request *Request, eSlice EventSlice) EventSlice {
sort.Sort(eSlice) sort.Sort(eSlice)
@ -213,7 +203,7 @@ func checkIfEventSatisfiesRequest(request *Request, event *info.Event) bool {
return true return true
} }
// method of Events object that screens Event objects found in the eventlist // method of Events object that screens Event objects found in the eventList
// attribute and if they fit the parameters passed by the Request object, // attribute and if they fit the parameters passed by the Request object,
// adds it to a slice of *Event objects that is returned. If both MaxEventsReturned // adds it to a slice of *Event objects that is returned. If both MaxEventsReturned
// and StartTime/EndTime are specified in the request object, then only // and StartTime/EndTime are specified in the request object, then only
@ -222,7 +212,7 @@ func (self *events) GetEvents(request *Request) (EventSlice, error) {
returnEventList := EventSlice{} returnEventList := EventSlice{}
self.eventsLock.RLock() self.eventsLock.RLock()
defer self.eventsLock.RUnlock() defer self.eventsLock.RUnlock()
for _, e := range self.eventlist { for _, e := range self.eventList {
if checkIfEventSatisfiesRequest(request, e) { if checkIfEventSatisfiesRequest(request, e) {
returnEventList = append(returnEventList, e) returnEventList = append(returnEventList, e)
} }
@ -251,11 +241,11 @@ func (self *events) WatchEvents(request *Request) (*EventChannel, error) {
return returnEventChannel, nil return returnEventChannel, nil
} }
// helper function to update the event manager's eventlist // helper function to update the event manager's eventList
func (self *events) updateEventList(e *info.Event) { func (self *events) updateEventList(e *info.Event) {
self.eventsLock.Lock() self.eventsLock.Lock()
defer self.eventsLock.Unlock() defer self.eventsLock.Unlock()
self.eventlist = append(self.eventlist, e) self.eventList = append(self.eventList, e)
} }
func (self *events) findValidWatchers(e *info.Event) []*watch { func (self *events) findValidWatchers(e *info.Event) []*watch {
@ -270,7 +260,7 @@ func (self *events) findValidWatchers(e *info.Event) []*watch {
} }
// method of Events object that adds the argument Event object to the // method of Events object that adds the argument Event object to the
// eventlist. It also feeds the event to a set of watch channels // eventList. It also feeds the event to a set of watch channels
// held by the manager if it satisfies the request keys of the channels // held by the manager if it satisfies the request keys of the channels
func (self *events) AddEvent(e *info.Event) error { func (self *events) AddEvent(e *info.Event) error {
self.updateEventList(e) self.updateEventList(e)

View File

@ -139,8 +139,8 @@ func TestAddEventAddsEventsToEventManager(t *testing.T) {
myEventHolder.AddEvent(fakeEvent) myEventHolder.AddEvent(fakeEvent)
checkNumberOfEvents(t, 1, myEventHolder.eventlist.Len()) checkNumberOfEvents(t, 1, myEventHolder.eventList.Len())
ensureProperEventReturned(t, fakeEvent, myEventHolder.eventlist[0]) ensureProperEventReturned(t, fakeEvent, myEventHolder.eventList[0])
} }
func TestGetEventsForOneEvent(t *testing.T) { func TestGetEventsForOneEvent(t *testing.T) {

View File

@ -72,7 +72,7 @@ func RegisterHandlers(mux httpMux.Mux, containerManager manager.Manager, httpAut
authenticator := auth.NewDigestAuthenticator(httpDigestRealm, secrets) authenticator := auth.NewDigestAuthenticator(httpDigestRealm, secrets)
mux.HandleFunc(static.StaticResource, authenticator.Wrap(staticHandler)) mux.HandleFunc(static.StaticResource, authenticator.Wrap(staticHandler))
if err := pages.RegisterHandlersDigest(mux, containerManager, authenticator); err != nil { if err := pages.RegisterHandlersDigest(mux, containerManager, authenticator); err != nil {
fmt.Errorf("failed to register pages digest handlers: %s", err) return fmt.Errorf("failed to register pages digest handlers: %s", err)
} }
authenticated = true authenticated = true
} }

View File

@ -479,14 +479,17 @@ func calculateCpuUsage(prev, cur uint64) uint64 {
// differentiated by the EventType field of Event. // differentiated by the EventType field of Event.
type Event struct { type Event struct {
// the absolute container name for which the event occurred // the absolute container name for which the event occurred
ContainerName string ContainerName string `json:"container_name"`
// the time at which the event occurred // the time at which the event occurred
Timestamp time.Time Timestamp time.Time `json:"timestamp"`
// the type of event. EventType is an enumerated type // the type of event. EventType is an enumerated type
EventType EventType EventType EventType `json:"event_type"`
// the original event object and all of its extraneous data, ex. an // the original event object and all of its extraneous data, ex. an
// OomInstance // OomInstance
EventData EventDataInterface EventData EventData `json:"event_data,omitempty"`
} }
// EventType is an enumerated type which lists the categories under which // EventType is an enumerated type which lists the categories under which
@ -499,7 +502,26 @@ const (
EventContainerDeletion EventContainerDeletion
) )
// a general interface which populates the Event field EventData. The actual // Extra information about an event. Only one type will be set.
// object, such as an OomInstance, is set as an Event's EventData type EventData struct {
type EventDataInterface interface { // Information about a container creation event.
Created *CreatedEventData `json:"created,omitempty"`
// Information about an OOM event.
Oom *OomEventData `json:"oom,omitempty"`
}
// Information related to a container creation event.
type CreatedEventData struct {
// Spec of the container at creation.
Spec ContainerSpec `json:"spec"`
}
// Information related to an OOM kill instance
type OomEventData struct {
// process id of the killed process
Pid int `json:"pid"`
// The name of the killed process
ProcessName string `json:"process_name"`
} }

View File

@ -660,12 +660,12 @@ func (m *manager) createContainer(containerName string) error {
} }
glog.V(2).Infof("Added container: %q (aliases: %v, namespace: %q)", containerName, cont.info.Aliases, cont.info.Namespace) glog.V(2).Infof("Added container: %q (aliases: %v, namespace: %q)", containerName, cont.info.Aliases, cont.info.Namespace)
contSpecs, err := cont.handler.GetSpec() contSpec, err := cont.handler.GetSpec()
if err != nil { if err != nil {
return err return err
} }
if contSpecs.CreationTime.After(m.startupTime) { if contSpec.CreationTime.After(m.startupTime) {
contRef, err := cont.handler.ContainerReference() contRef, err := cont.handler.ContainerReference()
if err != nil { if err != nil {
return err return err
@ -673,9 +673,13 @@ func (m *manager) createContainer(containerName string) error {
newEvent := &info.Event{ newEvent := &info.Event{
ContainerName: contRef.Name, ContainerName: contRef.Name,
EventData: contSpecs, Timestamp: contSpec.CreationTime,
Timestamp: contSpecs.CreationTime,
EventType: info.EventContainerCreation, EventType: info.EventContainerCreation,
EventData: info.EventData{
Created: &info.CreatedEventData{
Spec: contSpec,
},
},
} }
err = m.eventHandler.AddEvent(newEvent) err = m.eventHandler.AddEvent(newEvent)
if err != nil { if err != nil {
@ -847,7 +851,7 @@ func (self *manager) watchForNewContainers(quit chan error) error {
err = self.destroyContainer(event.Name) err = self.destroyContainer(event.Name)
} }
if err != nil { if err != nil {
glog.Warning("Failed to process watch event: %v", err) glog.Warningf("Failed to process watch event: %v", err)
} }
case <-quit: case <-quit:
// Stop processing events if asked to quit. // Stop processing events if asked to quit.
@ -878,7 +882,12 @@ func (self *manager) watchForNewOoms() error {
ContainerName: oomInstance.ContainerName, ContainerName: oomInstance.ContainerName,
Timestamp: oomInstance.TimeOfDeath, Timestamp: oomInstance.TimeOfDeath,
EventType: info.EventOom, EventType: info.EventOom,
EventData: oomInstance, EventData: info.EventData{
Oom: &info.OomEventData{
Pid: oomInstance.Pid,
ProcessName: oomInstance.ProcessName,
},
},
} }
glog.V(1).Infof("Created an oom event: %v", newEvent) glog.V(1).Infof("Created an oom event: %v", newEvent)
err := self.eventHandler.AddEvent(newEvent) err := self.eventHandler.AddEvent(newEvent)

View File

@ -23,7 +23,7 @@ import (
// A circular buffer for ContainerStats. // A circular buffer for ContainerStats.
type StatsBuffer struct { type StatsBuffer struct {
buffer []info.ContainerStats buffer []*info.ContainerStats
size int size int
index int index int
} }
@ -31,7 +31,7 @@ type StatsBuffer struct {
// Returns a new thread-compatible StatsBuffer. // Returns a new thread-compatible StatsBuffer.
func NewStatsBuffer(size int) *StatsBuffer { func NewStatsBuffer(size int) *StatsBuffer {
return &StatsBuffer{ return &StatsBuffer{
buffer: make([]info.ContainerStats, size), buffer: make([]*info.ContainerStats, size),
size: 0, size: 0,
index: size - 1, index: size - 1,
} }
@ -43,7 +43,8 @@ func (self *StatsBuffer) Add(item *info.ContainerStats) {
self.size++ self.size++
} }
self.index = (self.index + 1) % len(self.buffer) self.index = (self.index + 1) % len(self.buffer)
self.buffer[self.index] = *item copied := *item
self.buffer[self.index] = &copied
} }
// Returns up to maxResult elements in the specified time period (inclusive). // Returns up to maxResult elements in the specified time period (inclusive).
@ -131,7 +132,7 @@ func (self *StatsBuffer) FirstN(n int) []*info.ContainerStats {
res := make([]*info.ContainerStats, n) res := make([]*info.ContainerStats, n)
for i := 0; i < n; i++ { for i := 0; i < n; i++ {
index := (start + i) % len(self.buffer) index := (start + i) % len(self.buffer)
res[i] = &self.buffer[index] res[i] = self.buffer[index]
} }
return res return res
} }
@ -142,7 +143,7 @@ func (self *StatsBuffer) Get(index int) *info.ContainerStats {
if calculatedIndex < 0 { if calculatedIndex < 0 {
calculatedIndex += len(self.buffer) calculatedIndex += len(self.buffer)
} }
return &self.buffer[calculatedIndex] return self.buffer[calculatedIndex]
} }
func (self *StatsBuffer) Size() int { func (self *StatsBuffer) Size() int {