// +build integration,!no-etcd package integration import ( "bytes" "io/ioutil" "net/http" "net/http/httptest" "reflect" "testing" kubeapi "github.com/GoogleCloudPlatform/kubernetes/pkg/api" klatest "github.com/GoogleCloudPlatform/kubernetes/pkg/api/latest" "github.com/GoogleCloudPlatform/kubernetes/pkg/apiserver" "github.com/GoogleCloudPlatform/kubernetes/pkg/client" "github.com/GoogleCloudPlatform/kubernetes/pkg/labels" "github.com/GoogleCloudPlatform/kubernetes/pkg/master" "github.com/GoogleCloudPlatform/kubernetes/pkg/tools" "github.com/GoogleCloudPlatform/kubernetes/pkg/version" "github.com/openshift/origin/pkg/api/latest" "github.com/openshift/origin/pkg/api/v1beta1" buildapi "github.com/openshift/origin/pkg/build/api" buildregistry "github.com/openshift/origin/pkg/build/registry/build" buildconfigregistry "github.com/openshift/origin/pkg/build/registry/buildconfig" buildetcd "github.com/openshift/origin/pkg/build/registry/etcd" "github.com/openshift/origin/pkg/build/webhook" "github.com/openshift/origin/pkg/build/webhook/github" osclient "github.com/openshift/origin/pkg/client" ) func init() { requireEtcd() } func TestWebhookGithubPush(t *testing.T) { osClient, url := setup(t) // create buildconfig buildConfig := &buildapi.BuildConfig{ JSONBase: kubeapi.JSONBase{ ID: "pushbuild", }, DesiredInput: buildapi.BuildInput{ Type: buildapi.DockerBuildType, SourceURI: "http://my.docker/build", ImageTag: "namespace/builtimage", }, Secret: "secret101", } if _, err := osClient.CreateBuildConfig(buildConfig); err != nil { t.Fatalf("Unexpected error: %v", err) } // trigger build event sending push notification postFile("push", "pushevent.json", url+"pushbuild/secret101/github", http.StatusOK, t) // get a list of builds builds, err := osClient.ListBuilds(labels.Everything()) if err != nil { t.Fatalf("Unexpected error: %v", err) } if len(builds.Items) != 1 { t.Fatalf("Expected one build, got %#v", builds) } actual := builds.Items[0] if actual.Status != buildapi.BuildNew { t.Errorf("Expected %s, got %s", buildapi.BuildNew, actual.Status) } if !reflect.DeepEqual(actual.Input, buildConfig.DesiredInput) { t.Errorf("Expected %#v, got %#v", buildConfig.DesiredInput, actual.Input) } cleanup(osClient, t) } func TestWebhookGithubPing(t *testing.T) { osClient, url := setup(t) // create buildconfig buildConfig := &buildapi.BuildConfig{ JSONBase: kubeapi.JSONBase{ ID: "pingbuild", }, DesiredInput: buildapi.BuildInput{ Type: buildapi.DockerBuildType, SourceURI: "http://my.docker/build", ImageTag: "namespace/builtimage", }, Secret: "secret101", } if _, err := osClient.CreateBuildConfig(buildConfig); err != nil { t.Fatalf("Unexpected error: %v", err) } // trigger build event sending push notification postFile("ping", "pingevent.json", url+"pingbuild/secret101/github", http.StatusOK, t) // get a list of builds builds, err := osClient.ListBuilds(labels.Everything()) if err != nil { t.Fatalf("Unexpected error: %v", err) } if len(builds.Items) != 0 { t.Fatalf("Unexpected build appeared, got %#v", builds) } cleanup(osClient, t) } func setup(t *testing.T) (*osclient.Client, string) { etcdClient := newEtcdClient() helper, _ := master.NewEtcdHelper(etcdClient.GetCluster(), klatest.Version) m := master.New(&master.Config{ EtcdHelper: helper, }) interfaces, _ := latest.InterfacesFor(latest.Version) buildRegistry := buildetcd.New(tools.EtcdHelper{etcdClient, interfaces.Codec, interfaces.ResourceVersioner}) storage := map[string]apiserver.RESTStorage{ "builds": buildregistry.NewREST(buildRegistry), "buildConfigs": buildconfigregistry.NewREST(buildRegistry), } osMux := http.NewServeMux() apiserver.NewAPIGroup(m.API_v1beta1()).InstallREST(osMux, "/api/v1beta1") osPrefix := "/osapi/v1beta1" apiserver.NewAPIGroup(storage, v1beta1.Codec, osPrefix, interfaces.SelfLinker).InstallREST(osMux, osPrefix) apiserver.InstallSupport(osMux) s := httptest.NewServer(osMux) kubeclient := client.NewOrDie(&client.Config{Host: s.URL, Version: klatest.Version}) osClient := osclient.NewOrDie(&client.Config{Host: s.URL, Version: latest.Version}) whPrefix := osPrefix + "/buildConfigHooks/" osMux.Handle(whPrefix, http.StripPrefix(whPrefix, webhook.NewController(osClient, map[string]webhook.Plugin{ "github": github.New(), }))) info, err := kubeclient.ServerVersion() if err != nil { t.Fatalf("Unexpected error: %v", err) } if e, a := version.Get(), *info; !reflect.DeepEqual(e, a) { t.Errorf("Expected %#v, got %#v", e, a) } return osClient, s.URL + whPrefix } func cleanup(osClient *osclient.Client, t *testing.T) { builds, err := osClient.ListBuilds(labels.Everything()) if err != nil { t.Fatalf("Unexpected error: %v", err) } for _, build := range builds.Items { if err := osClient.DeleteBuild(build.ID); err != nil { t.Errorf("Unexpected error: %v", err) } } buildConfigs, err := osClient.ListBuildConfigs(labels.Everything()) if err != nil { t.Fatalf("Unexpected error: %v", err) } for _, bc := range buildConfigs.Items { if err := osClient.DeleteBuildConfig(bc.ID); err != nil { t.Errorf("Unexpected error: %v", err) } } } func postFile(event, filename, url string, expStatusCode int, t *testing.T) { client := &http.Client{} data, err := ioutil.ReadFile("../../pkg/build/webhook/github/fixtures/" + filename) if err != nil { t.Fatalf("Failed to open %s: %v", filename, err) } req, err := http.NewRequest("POST", url, bytes.NewReader(data)) if err != nil { t.Fatalf("Error creating POST request: %v", err) } req.Header.Add("Content-Type", "application/json") req.Header.Add("User-Agent", "GitHub-Hookshot/github") req.Header.Add("X-Github-Event", event) resp, err := client.Do(req) if err != nil { t.Fatalf("Failed posting webhook: %v", err) } body, _ := ioutil.ReadAll(resp.Body) if resp.StatusCode != expStatusCode { t.Errorf("Wrong response code, expecting %d, got %s: %s!", expStatusCode, resp.Status, string(body)) } }