github.com/billybanfield/evergreen@v0.0.0-20170525200750-eeee692790f7/model/testutil/api.go (about)

     1  package testutil
     2  
     3  import (
     4  	"io/ioutil"
     5  
     6  	"github.com/evergreen-ci/evergreen"
     7  	"github.com/evergreen-ci/evergreen/db"
     8  	"github.com/evergreen-ci/evergreen/model"
     9  	"github.com/evergreen-ci/evergreen/model/build"
    10  	"github.com/evergreen-ci/evergreen/model/distro"
    11  	"github.com/evergreen-ci/evergreen/model/host"
    12  	"github.com/evergreen-ci/evergreen/model/manifest"
    13  	"github.com/evergreen-ci/evergreen/model/patch"
    14  	"github.com/evergreen-ci/evergreen/model/task"
    15  	"github.com/evergreen-ci/evergreen/model/version"
    16  	"github.com/pkg/errors"
    17  	"gopkg.in/mgo.v2/bson"
    18  	yaml "gopkg.in/yaml.v2"
    19  )
    20  
    21  type TestModelData struct {
    22  	Task       *task.Task
    23  	Build      *build.Build
    24  	Host       *host.Host
    25  	TaskConfig *model.TaskConfig
    26  }
    27  
    28  func SetupAPITestData(testConfig *evergreen.Settings, taskDisplayName string, variant string, projectFile string, patchMode PatchTestMode) (*TestModelData, error) {
    29  	// Ignore errs here because the ns might just not exist.
    30  	clearDataMsg := "Failed to clear test data collection"
    31  	testCollections := []string{
    32  		task.Collection, build.Collection, host.Collection,
    33  		distro.Collection, version.Collection, patch.Collection,
    34  		model.PushlogCollection, model.ProjectVarsCollection, model.TaskQueuesCollection,
    35  		manifest.Collection, model.ProjectRefCollection}
    36  
    37  	if err := db.ClearCollections(testCollections...); err != nil {
    38  		return nil, errors.Wrap(err, clearDataMsg)
    39  	}
    40  
    41  	// Read in the project configuration
    42  	projectConfig, err := ioutil.ReadFile(projectFile)
    43  	if err != nil {
    44  		return nil, errors.Wrap(err, "failed to read project config")
    45  	}
    46  
    47  	modelData := &TestModelData{}
    48  
    49  	// Unmarshall the project configuration into a struct
    50  	project := &model.Project{}
    51  	if err := model.LoadProjectInto(projectConfig, "test", project); err != nil {
    52  		return nil, errors.Wrap(err, "failed to unmarshal project config")
    53  	}
    54  
    55  	// create a build variant for this project
    56  	bv := model.BuildVariant{
    57  		Name: variant,
    58  		Tasks: []model.BuildVariantTask{{
    59  			Name: taskDisplayName,
    60  		}},
    61  	}
    62  
    63  	project.BuildVariants = append(project.BuildVariants, bv)
    64  	// Marshall the project YAML for storage
    65  	projectYamlBytes, err := yaml.Marshal(project)
    66  	if err != nil {
    67  		return nil, errors.Wrap(err, "failed to unmarshal project config")
    68  	}
    69  
    70  	// Create the ref for the project
    71  	projectRef := &model.ProjectRef{
    72  		Identifier:  project.DisplayName,
    73  		Owner:       project.Owner,
    74  		Repo:        project.Repo,
    75  		RepoKind:    project.RepoKind,
    76  		Branch:      project.Branch,
    77  		Enabled:     project.Enabled,
    78  		BatchTime:   project.BatchTime,
    79  		LocalConfig: string(projectConfig),
    80  	}
    81  	if err := projectRef.Insert(); err != nil {
    82  		return nil, errors.Wrap(err, "failed to insert projectRef")
    83  	}
    84  
    85  	// Save the project variables
    86  	projectVars := &model.ProjectVars{
    87  		Id: project.DisplayName,
    88  		Vars: map[string]string{
    89  			"aws_key":    testConfig.Providers.AWS.Id,
    90  			"aws_secret": testConfig.Providers.AWS.Secret,
    91  			"fetch_key":  "fetch_expansion_value",
    92  		},
    93  	}
    94  	if _, err := projectVars.Upsert(); err != nil {
    95  		return nil, errors.Wrap(err, "problem inserting project variables")
    96  	}
    97  
    98  	// Create and insert two tasks
    99  	taskOne := &task.Task{
   100  		Id:           "testTaskId",
   101  		BuildId:      "testBuildId",
   102  		DistroId:     "test-distro-one",
   103  		BuildVariant: variant,
   104  		Project:      projectRef.Identifier,
   105  		DisplayName:  taskDisplayName,
   106  		HostId:       "testHost",
   107  		Secret:       "testTaskSecret",
   108  		Version:      "testVersionId",
   109  		Status:       evergreen.TaskDispatched,
   110  		Requester:    evergreen.RepotrackerVersionRequester,
   111  	}
   112  	if patchMode != NoPatch {
   113  		taskOne.Requester = evergreen.PatchVersionRequester
   114  	}
   115  	if err := taskOne.Insert(); err != nil {
   116  		return nil, errors.Wrap(err, "failed to insert taskOne")
   117  	}
   118  	modelData.Task = taskOne
   119  
   120  	taskTwo := &task.Task{
   121  		Id:           "testTaskIdTwo",
   122  		BuildId:      "testBuildId",
   123  		DistroId:     "test-distro-one",
   124  		BuildVariant: variant,
   125  		Project:      project.DisplayName,
   126  		DisplayName:  taskDisplayName,
   127  		HostId:       "",
   128  		Secret:       "testTaskSecret",
   129  		Version:      "testVersionId",
   130  		Status:       evergreen.TaskUndispatched,
   131  		Requester:    evergreen.RepotrackerVersionRequester,
   132  		Activated:    true,
   133  	}
   134  	if err := taskTwo.Insert(); err != nil {
   135  		return nil, errors.Wrap(err, "failed to insert taskTwo")
   136  	}
   137  
   138  	// Set up a task queue for task end tests
   139  	taskQueue := &model.TaskQueue{
   140  		Distro: "test-distro-one",
   141  		Queue: []model.TaskQueueItem{
   142  			{
   143  				Id:          "testTaskIdTwo",
   144  				DisplayName: taskDisplayName,
   145  			},
   146  		},
   147  	}
   148  	if err := taskQueue.Save(); err != nil {
   149  		return nil, errors.Wrap(err, "failed to insert task queue")
   150  	}
   151  
   152  	// Insert the version document
   153  	v := &version.Version{
   154  		Id:       taskOne.Version,
   155  		BuildIds: []string{taskOne.BuildId},
   156  		Config:   string(projectYamlBytes),
   157  	}
   158  	if err := v.Insert(); err != nil {
   159  		return nil, errors.Wrap(err, "failed to insert version: ")
   160  	}
   161  
   162  	// Insert the build that contains the tasks
   163  	build := &build.Build{
   164  		Id: "testBuildId",
   165  		Tasks: []build.TaskCache{
   166  			build.NewTaskCache(taskOne.Id, taskOne.DisplayName, true),
   167  			build.NewTaskCache(taskTwo.Id, taskTwo.DisplayName, true),
   168  		},
   169  		Version: v.Id,
   170  	}
   171  	if err := build.Insert(); err != nil {
   172  		return nil, errors.Wrap(err, "failed to insert build")
   173  	}
   174  	modelData.Build = build
   175  
   176  	workDir, err := ioutil.TempDir("", "agent_test_")
   177  	if err != nil {
   178  		return nil, errors.Wrap(err, "failed to create working directory")
   179  	}
   180  
   181  	// Insert the host info for running the tests
   182  	testHost := &host.Host{
   183  		Id:   "testHost",
   184  		Host: "testHost",
   185  		Distro: distro.Distro{
   186  			Id:         "test-distro-one",
   187  			WorkDir:    workDir,
   188  			Expansions: []distro.Expansion{{"distro_exp", "DISTRO_EXP"}},
   189  		},
   190  		Provider:      evergreen.HostTypeStatic,
   191  		RunningTask:   taskOne.Id,
   192  		Secret:        "testHostSecret",
   193  		StartedBy:     evergreen.User,
   194  		AgentRevision: agentRevision,
   195  		Status:        evergreen.HostRunning,
   196  	}
   197  	if err := testHost.Insert(); err != nil {
   198  		return nil, errors.Wrap(err, "failed to insert host")
   199  	}
   200  	modelData.Host = testHost
   201  
   202  	session, _, err := db.GetGlobalSessionFactory().GetSession()
   203  	if err != nil {
   204  		return nil, errors.Wrap(err, "couldn't get db session!")
   205  
   206  	}
   207  
   208  	config, err := model.NewTaskConfig(&testHost.Distro, v, project,
   209  		taskOne, projectRef)
   210  	if err != nil {
   211  		return nil, errors.Wrap(err, "failed to create task config")
   212  	}
   213  	modelData.TaskConfig = config
   214  
   215  	// Remove any logs for our test task from previous runs.
   216  	_, err = session.DB(model.TaskLogDB).C(model.TaskLogCollection).
   217  		RemoveAll(bson.M{"t_id": bson.M{"$in": []string{taskOne.Id, taskTwo.Id}}})
   218  	if err != nil {
   219  		return nil, errors.Wrap(err, "failed to remove logs")
   220  	}
   221  
   222  	return modelData, nil
   223  }