Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fixes #541 #578

Merged
merged 9 commits into from
Oct 28, 2016
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion netmaster/master/api.go
100755 → 100644
Original file line number Diff line number Diff line change
Expand Up @@ -346,7 +346,7 @@ func UpdateEndpointHandler(w http.ResponseWriter, r *http.Request, vars map[stri
return nil, err
}

if epUpdReq.Event == "start" {
if epUpdReq.Event == "start" || epUpdReq.Event == "connect" {
//Received container start event from netplugin. Check if the Provider
//matches any service and perform service provider update if there is a matching
//service.
Expand Down
159 changes: 56 additions & 103 deletions netplugin/agent/docker_event.go
Original file line number Diff line number Diff line change
Expand Up @@ -28,65 +28,80 @@ import (
"golang.org/x/net/context"
)

// Handles docker events monitored by dockerclient. Currently we only handle
// container start and die event*/
// Handles docker events monitored by dockerclient. Currently we only handle // container start and die event*/
func handleDockerEvents(event *dockerclient.Event, ec chan error, args ...interface{}) {

log.Infof("Received Docker event: {%#v}\n", *event)
log.Debugf("Received Docker event: {%#v}\n", *event)
endpointUpdReq := &master.UpdateEndpointRequest{}
switch event.Status {
case "start":

var containerID string
var networkID string

if (event.Type == "container" && event.Action == "start") ||
(event.Type == "network" && event.Action == "connect") {

if event.Type == "container" {
containerID = event.ID
networkID = ""
} else {
containerID = event.Actor.Attributes["container"]
networkID = event.Actor.ID
}

if containerID == "" {
log.Errorf("Container ID missing in docker event {%#v}\n", *event)
return
}

defaultHeaders := map[string]string{"User-Agent": "engine-api-cli-1.0"}
cli, err := client.NewClient("unix:///var/run/docker.sock", "v1.21", nil, defaultHeaders)
if err != nil {
panic(err)
log.Errorf("Client lookup failed :%s", err)
return
}

containerInfo, err := cli.ContainerInspect(context.Background(), event.ID)
containerInfo, err := cli.ContainerInspect(context.Background(), containerID)

if err != nil {
log.Errorf("Container Inspect failed :%s", err)
return
}

if event.ID != "" {
labelMap := getLabelsFromContainerInspect(&containerInfo)
containerTenant := getTenantFromContainerInspect(&containerInfo)
networkName, ipAddress, err := getEpNetworkInfoFromContainerInspect(&containerInfo, "")
if err != nil {
log.Errorf("Error getting container network info for %v.Err:%s", event.ID, err)
}
endpoint := getEndpointFromContainerInspect(&containerInfo,
networkName, containerTenant)

if ipAddress != "" {
//Create provider info
endpointUpdReq.IPAddress = ipAddress
endpointUpdReq.ContainerID = event.ID
endpointUpdReq.Tenant = containerTenant
endpointUpdReq.Network = networkName
endpointUpdReq.Event = "start"
endpointUpdReq.EndpointID = endpoint
endpointUpdReq.ContainerName = containerInfo.Name
endpointUpdReq.Labels = make(map[string]string)

for k, v := range labelMap {
endpointUpdReq.Labels[k] = v
}
labelMap := getLabelsFromContainerInspect(&containerInfo)
containerTenant := getTenantFromContainerInspect(&containerInfo)
networkName, ipAddress, err := getEpNetworkInfoFromContainerInspect(&containerInfo, networkID)
if err != nil {
log.Errorf("Error getting container network info for %v.Err:%s", containerID, err)
}
endpoint := getEndpointFromContainerInspect(&containerInfo,
networkName, containerTenant)

if ipAddress != "" {
//Create provider info
endpointUpdReq.IPAddress = ipAddress
endpointUpdReq.ContainerID = containerID
endpointUpdReq.Tenant = containerTenant
endpointUpdReq.Network = networkName
endpointUpdReq.Event = event.Action
endpointUpdReq.EndpointID = endpoint
endpointUpdReq.ContainerName = containerInfo.Name
endpointUpdReq.Labels = make(map[string]string)

for k, v := range labelMap {
endpointUpdReq.Labels[k] = v
}
}

var epUpdResp master.UpdateEndpointResponse
var epUpdResp master.UpdateEndpointResponse

log.Infof("Sending Endpoint update request to master: {%+v}", endpointUpdReq)
log.Infof("Sending Endpoint update request to master: {%+v}", endpointUpdReq)

err = cluster.MasterPostReq("/plugin/updateEndpoint", endpointUpdReq, &epUpdResp)
if err != nil {
log.Errorf("Event: 'start' , Http error posting endpoint update, Error:%s", err)
}
} else {
log.Errorf("Unable to fetch container labels for container %s ", event.ID)
err = cluster.MasterPostReq("/plugin/updateEndpoint", endpointUpdReq, &epUpdResp)
if err != nil {
log.Errorf("Event: 'start' , Http error posting endpoint update, Error:%s", err)
}
case "die":

} else if event.Type == "container" && event.Action == "die" {
endpointUpdReq.ContainerID = event.ID
endpointUpdReq.Event = "die"
var epUpdResp master.UpdateEndpointResponse
Expand All @@ -95,69 +110,7 @@ func handleDockerEvents(event *dockerclient.Event, ec chan error, args ...interf
if err != nil {
log.Errorf("Event:'die' Http error posting endpoint update, Error:%s", err)
}

case "":

/* Handles the case when we get a docker event with null event status
such as when we proactively create containers ourselves rather than the end user
Look for the "connect" action in such cases.
*/

containerID := event.Actor.Attributes["container"]
networkID := event.Actor.ID

if event.Action == "connect" && containerID != "" {

endpointUpdReq.Event = "connect"
defaultHeaders := map[string]string{"User-Agent": "engine-api-cli-1.0"}
cli, err := client.NewClient("unix:///var/run/docker.sock", "v1.21", nil, defaultHeaders)
if err != nil {
panic(err)
}

containerInfo, err := cli.ContainerInspect(context.Background(), containerID)

if err != nil {
log.Errorf("Container Inspect failed :%s", err)
return
}

labelMap := getLabelsFromContainerInspect(&containerInfo)
containerTenant := getTenantFromContainerInspect(&containerInfo)
networkName, ipAddress, err := getEpNetworkInfoFromContainerInspect(&containerInfo, networkID)
if err != nil {
log.Errorf("Error getting container network info for %v.Err:%s", containerID, err)
}

endpoint := getEndpointFromContainerInspect(&containerInfo,
networkName, containerTenant)

if ipAddress != "" {
//Create provider info
endpointUpdReq.IPAddress = ipAddress
endpointUpdReq.ContainerID = containerID
endpointUpdReq.Tenant = containerTenant
endpointUpdReq.Network = networkName
endpointUpdReq.Event = "start"
endpointUpdReq.EndpointID = endpoint
endpointUpdReq.ContainerName = containerInfo.Name
endpointUpdReq.Labels = make(map[string]string)

for k, v := range labelMap {
endpointUpdReq.Labels[k] = v
}
}

var epUpdResp master.UpdateEndpointResponse

log.Infof("Sending Endpoint update request to master: {%+v}", endpointUpdReq)

err = cluster.MasterPostReq("/plugin/updateEndpoint", endpointUpdReq, &epUpdResp)
if err != nil {
log.Errorf("Event: 'start' , Http error posting endpoint update, Error:%s", err)
}
}
} /*switch() */
}
}

//getLabelsFromContainerInspect returns the labels associated with the container
Expand Down
38 changes: 5 additions & 33 deletions test/systemtests/network_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,6 @@ package systemtests
import (
"fmt"

"errors"
"strings"
"sync"
"time"

Expand Down Expand Up @@ -83,36 +81,6 @@ func (s *systemtestSuite) testInfraNetworkAddDelete(c *C, encap string) {
}
}

/* Confirm network inspect includes a dns endpoint (assumes this is the only endpoint on the network currently) */
func (s *systemtestSuite) testNetworkInspectDNS(tenant, network string) (bool, error) {

netInspect, err := s.cli.NetworkInspect(tenant, network)
// Network inspect must succeed
if err != nil {
return false, err
}

// logrus.Infof(" %+v \n", netInspect)

// Network inspect should show exactly 1 endpoint
if len(netInspect.Oper.Endpoints) != 1 {
logrus.Infof("testNetworkInspectDNS has %d endpoints (should have 1)!", len(netInspect.Oper.Endpoints))
return false, errors.New("testNetworkInspectDNS has incorrect # of endpoints (should have 1)!")
}

// First endpoint in network inspect should not have a null container ID
if netInspect.Oper.Endpoints[0].ContainerID == "" {
return false, errors.New("testNetworkInspectDNS endpoint has null containerID!")
}

// First endpoint in network inspect should incude dns in the container name
if !strings.Contains(netInspect.Oper.Endpoints[0].ContainerName, "dns") {
return false, errors.New("testNetworkInspectDNS has no endpoint with dns in containerName!")
}

return true, nil
}

func (s *systemtestSuite) TestNetworkAddDeleteVXLAN(c *C) {
s.testNetworkAddDelete(c, "vxlan")
}
Expand All @@ -121,10 +89,14 @@ func (s *systemtestSuite) TestNetworkAddDeleteVLAN(c *C) {
s.testNetworkAddDelete(c, "vlan")
}

func (s *systemtestSuite) TestNetworkAddDeleteWithDns(c *C) {
func (s *systemtestSuite) TestNetworkAddDeleteVLANWithDns(c *C) {
s.testNetworkAddDeleteWithDns(c, "vlan")
}

func (s *systemtestSuite) TestNetworkAddDeleteVXLANWithDns(c *C) {
s.testNetworkAddDeleteWithDns(c, "vxlan")
}

func (s *systemtestSuite) testNetworkAddDelete(c *C, encap string) {

if s.fwdMode == "routing" && encap == "vlan" {
Expand Down
33 changes: 31 additions & 2 deletions test/systemtests/util_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -1003,6 +1003,36 @@ func (s *systemtestSuite) verifyIPs(ipaddrs []string) error {
return err
}

/* Confirm network inspect includes a dns endpoint (assumes this is the only endpoint on the network currently) */
func (s *systemtestSuite) testNetworkInspectDNS(tenant, network string) (bool, error) {
Copy link
Member

@abhi abhi Oct 27, 2016

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

very very very minor nit - can we change this to check instead of test.


netInspect, err := s.cli.NetworkInspect(tenant, network)
// Network inspect must succeed
if err != nil {
return false, err
}

// logrus.Infof(" %+v \n", netInspect)

// Network inspect should show exactly 1 endpoint
if len(netInspect.Oper.Endpoints) != 1 {
logrus.Infof("testNetworkInspectDNS has %d endpoints (should have 1)!", len(netInspect.Oper.Endpoints))
return false, errors.New("testNetworkInspectDNS has incorrect # of endpoints (should have 1)!")
}

// First endpoint in network inspect should not have a null container ID
if netInspect.Oper.Endpoints[0].ContainerID == "" {
return false, errors.New("testNetworkInspectDNS endpoint has null containerID!")
}

// First endpoint in network inspect should incude dns in the container name
if !strings.Contains(netInspect.Oper.Endpoints[0].ContainerName, "dns") {
return false, errors.New("testNetworkInspectDNS has no endpoint with dns in containerName!")
}

return true, nil
}

//Function to extract cfg Info from JSON file
func getInfo(file string) (BasicInfo, HostInfo, GlobInfo) {
raw, err := ioutil.ReadFile(file)
Expand Down Expand Up @@ -1263,8 +1293,7 @@ func (s *systemtestSuite) SetUpTestVagrant(c *C) {
// temporarily enable DNS for service discovery tests or for network test requiring dns
prevDNSEnabled := s.basicInfo.EnableDNS
if strings.Contains(c.TestName(), "SvcDiscovery") ||
strings.Contains(c.TestName(), "NetworkAddDeleteWithDns") ||
strings.Contains(c.TestName(), "NetworkAddDeleteTenantWithDns") {
strings.Contains(c.TestName(), "WithDns") {
s.basicInfo.EnableDNS = true
}

Expand Down