How I can retrieve Test Cases that related to some release.
I want to retrieve data about Test Cases that related to Release.
But Test Case doesn't have Release filed. Btw, Test Case has WorkProduct it's the for which this test case was created. But when I'm trying to get the WorkProdut from test case object,
I don't have any useful information except US name, actually I can use this Name for getting legal US object.
But it looks difficult...
TestCases get scheduled into Iterations and Releases via TestSets. I have an app in this github repo that builds a grid of stories scheduled for release, and testsets scheduled for release and associated testcases.
Here is the code fragment where TestSet objects are loaded, with their TestCases collection, and then TestCases collection is hydrated (since this cannot be done in a single request):
_makeAnotherStore: function(){
Ext.create('Rally.data.WsapiDataStore', {
model: 'TestSet',
fetch: ['FormattedID', 'TestCases', 'TestCaseStatus'],
pageSize: 100,
autoLoad: true,
filters: [this.getContext().getTimeboxScope().getQueryFilter()],
listeners: {
load: this._onTestSetsLoaded,
scope: this
}
});
},
_onTestSetsLoaded: function(store, data){
console.log('store...',store);
console.log('data...',data);
var testSets = [];
var pendingTestCases = data.length;
console.log(data.length);
if (data.length ===0) {
this._createTestSetGrid(testSets);
}
Ext.Array.each(data, function(testset){
var ts = {
FormattedID: testset.get('FormattedID'),
_ref: testset.get('_ref'),
TestCaseStatus: testset.get('TestCaseStatus'),
TestCaseCount: testset.get('TestCases').Count,
TestCases: []
};
var testCases = testset.getCollection('TestCases');
testCases.load({
fetch: ['FormattedID'],
callback: function(records, operation, success){
Ext.Array.each(records, function(testcase){
ts.TestCases.push({_ref: testcase.get('_ref'),
FormattedID: testcase.get('FormattedID')
});
}, this);
--pendingTestCases;
if (pendingTestCases === 0) {
this._createTestSetGrid(testSets);
}
},
scope: this
});
testSets.push(ts);
},this);
}
,
Related
I'm writing an application that should load Accepted stories that have tasks with integer in the Time Spent field.
As I can see in some tests I made the task fields that are accessible through UserStory is: 'Tasks', 'TaskActualTotal', 'TaskEstimateTotal', 'TaskRemainingTotal' and 'TaskStatus'.
Tasks has a _ref attribute with a link to a JSON with all tasks for this story. How may I explore this since I'm using Rally API? Or Is there a better way to do this?
UPDATE:
So this is pretty much i have now.
var storiesCall = Ext.create('Rally.data.WsapiDataStore', {
model: 'UserStory',
fetch: ['Tasks']
});
storiesCall.load().then({
success: this.loadTasks,
scope: this
});
loadTasks: function(stories) {
storiesCall = _.flatten(stories);
console.log(stories.length);
_.each(stories, function(story) {
var tasks = story.get('Tasks');
if(tasks.Count > 0) {
tasks.store = story.getCollection('Tasks', {fetch: ['Name','FormattedID','Workproduct','Estimate','TimeSpent']});
console.log(tasks.store.load().deferred);
}
else{
console.log('no tasks');
}
});
}
tasks.store.load().deferred is returning the following object:
Note that we can see the task data on value[0] but when i try to wrap it out with tasks.store.load().deferred.value[0] its crashing.
Any thoughts?
Per WS API doc, TimeSpent field on Task object (which is populated automatically from entries in Rally Timesheet/Time Tracker module) cannot be used in queries, so something like this (TimeSpent > 0) will not work.
Also, a UserStory object (referred to as HierarchicalRequirement in WS API) does not have a field where child tasks' TimeSpent rolls up to the story similar to how child tasks' Estimate rolls up to TaskEstimateTotal on a story.
It is possible to get TimeSpent for each task and then add them up by accessing a story's Tasks collection as done in this app:
Ext.define('CustomApp', {
extend: 'Rally.app.App',
componentCls: 'app',
launch: function() {
var initiatives = Ext.create('Rally.data.wsapi.Store', {
model: 'PortfolioItem/Initiative',
fetch: ['Children']
});
initiatives.load().then({
success: this.loadFeatures,
scope: this
}).then({
success: this.loadParentStories,
scope: this
}).then({
success: this.loadChildStories,
scope: this
}).then({
success: this.loadTasks,
failure: this.onFailure,
scope: this
}).then({
success: function(results) {
results = _.flatten(results);
_.each(results, function(result){
console.log(result.data.FormattedID, 'Estimate: ', result.data.Estimate, 'WorkProduct:', result.data.WorkProduct.FormattedID, 'TimeSpent', result.data.TimeSpent );
});
this.makeGrid(results);
},
failure: function(error) {
console.log('oh, noes!');
},
scope: this
});
},
loadFeatures: function(initiatives) {
var promises = [];
_.each(initiatives, function(initiative) {
var features = initiative.get('Children');
if(features.Count > 0) {
features.store = initiative.getCollection('Children',{fetch: ['Name','FormattedID','UserStories']});
promises.push(features.store.load());
}
});
return Deft.Promise.all(promises);
},
loadParentStories: function(features) {
features = _.flatten(features);
var promises = [];
_.each(features, function(feature) {
var stories = feature.get('UserStories');
if(stories.Count > 0) {
stories.store = feature.getCollection('UserStories', {fetch: ['Name','FormattedID','Children']});
promises.push(stories.store.load());
}
});
return Deft.Promise.all(promises);
},
loadChildStories: function(parentStories) {
parentStories = _.flatten(parentStories);
var promises = [];
_.each(parentStories, function(parentStory) {
var children = parentStory.get('Children');
if(children.Count > 0) {
children.store = parentStory.getCollection('Children', {fetch: ['Name','FormattedID','Tasks']});
promises.push(children.store.load());
}
});
return Deft.Promise.all(promises);
},
loadTasks: function(stories) {
stories = _.flatten(stories);
var promises = [];
_.each(stories, function(story) {
var tasks = story.get('Tasks');
if(tasks.Count > 0) {
tasks.store = story.getCollection('Tasks', {fetch: ['Name','FormattedID','Workproduct','Estimate','TimeSpent']});
promises.push(tasks.store.load());
}
else{
console.log('no tasks');
}
});
return Deft.Promise.all(promises);
},
makeGrid:function(tasks){
var data = [];
_.each(tasks, function(task){
data.push(task.data);
});
_.each(data, function(record){
record.Story = record.WorkProduct.FormattedID + " " + record.WorkProduct.Name;
});
this.add({
xtype: 'rallygrid',
showPagingToolbar: true,
showRowActionsColumn: true,
editable: false,
store: Ext.create('Rally.data.custom.Store', {
data: data,
groupField: 'Story'
}),
features: [{ftype:'groupingsummary'}],
columnCfgs: [
{
xtype: 'templatecolumn',text: 'ID',dataIndex: 'FormattedID',width: 100,
tpl: Ext.create('Rally.ui.renderer.template.FormattedIDTemplate'),
summaryRenderer: function() {
return "Totals";
}
},
{
text: 'Name',dataIndex: 'Name'
},
{
text: 'TimeSpent',dataIndex: 'TimeSpent',
summaryType: 'sum'
},
{
text: 'Estimate',dataIndex: 'Estimate',
summaryType: 'sum'
}
]
});
}
});
We want to take a number test cases from previous iterations / test sets and import them into a new test set. The problem is that we cannot export the test cases from a test set into CSV or any other data format as all we get is a printable report. We have also tried copy and paste the printable report into MS Excel but it does not give a data format.
Any suggestions / HTML forms that can be used.
It is possible to copy TestSets in Rally UI and that functionality allows re-using member Test Cases from Iteration to Iteration or from Release to Release. When you copy Test Sets they preserve the member Test Cases, including Test Steps. Rally recommends this method to handle testing. If the same tests are use repeatedly, copy the test sets that contain them into the new iteration directly in the Rally UI. This resets the results for that iteration and keeps you from duplicating the testcases.
Mark's Ruby tools provide an alternative which allows selective copying of member test cases - something that does not happen when a testset is copied in the UI.
Here is a javascript example using AppSDK2. You may certainly customize it further. The main point of this example is to illustrate how to update a collection using AppSDK2.
A user may select a "source" iteration from the iteration combobox, then a testset combobox is populated with testsets scheduled for this iteration. Next a user can select a destination iteration from the third combobox that limits iterations to current and future iterations, and create a new testset scheduled for the "destination" iteration. The testcases from the "source" testset are copied to the new testset.
Currently updating collections will not work if the app is run outside of Rally, but this limitation will be corrected soon. It will allow collection updates outside of rally using CORS as long as rab run command is used. The code below should work inside Rally now. The deployment html is available from this github repo.
Ext.define('CustomApp', {
extend: 'Rally.app.TimeboxScopedApp',
componentCls: 'app',
scopeType: 'iteration',
comboboxConfig: {
fieldLabel: 'Select a source Iteration',
labelWidth: 150,
width: 350
},
onScopeChange: function() {
if (!this.down('#parentPanel')) {
this._panel = Ext.create('Ext.panel.Panel', {
layout: 'hbox',
itemId: 'parentPanel',
componentCls: 'panel',
items: [
{
xtype: 'container',
itemId: 'pickerContainer',
},
{
xtype: 'container',
itemId: 'iterationContainer',
}
]
});
this.add(this._panel);
}
if (this.down('#testSetComboxBox')) {
this.down('#testSetComboxBox').destroy();
}
var testSetComboxBox = Ext.create('Rally.ui.combobox.ComboBox',{
itemId: 'testSetComboxBox',
storeConfig: {
model: 'TestSet',
limit: Infinity,
pageSize: 100,
autoLoad: true,
filters: [this.getContext().getTimeboxScope().getQueryFilter()]
},
fieldLabel: 'Select a TestSet',
listeners:{
ready: function(combobox){
if (combobox.getRecord()) {
this._onTestSetSelected(combobox.getRecord());
}
else{
console.log('selected iteration has no testsets');
}
},
select: function(combobox){
if (combobox.getRecord()) {
this._onTestSetSelected(combobox.getRecord());
}
},
scope: this
}
});
this.down('#pickerContainer').add(testSetComboxBox);
},
_onTestSetSelected:function(testset){
var id = testset.get('ObjectID');
this._name = testset.get('Name');
testset.self.load(id, {
fetch: ['Name','TestCases'],
callback: this._onSourceRecordRead,
scope: this
});
},
_onSourceRecordRead: function(record) {
var that = this;
that._testcases = [];
var testcaseStore = record.getCollection('TestCases',{fetch:['Name','FormattedID']});
testcaseStore.load({
callback: function() {
_.each(testcaseStore.getRange(), function(tc){
that._testcases.push(tc.data._ref);
});
console.log(that._testcases);
that._selectFutureIteration();
}
});
},
_selectFutureIteration: function(){
if (!this.down('#iterationComboxBox')) {
var iterationComboxBox = Ext.create('Rally.ui.combobox.ComboBox',{
itemId: 'iterationComboxBox',
storeConfig: {
model: 'Iteration',
limit: Infinity,
pageSize: 100,
autoLoad: true,
filters: [
{
property: 'StartDate',
operator: '>=',
value: (new Date()).toISOString()
}
]
},
fieldLabel: 'Select a destination Iteration',
labelWidth: 150,
listeners:{
ready: function(combobox){
if (combobox.getRecord()) {
this._onFutureIterationSelected(combobox.getRecord());
}
else{
console.log('no current or future iterations');
}
},
select: function(combobox){
if (combobox.getRecord()) {
this._onFutureIterationSelected(combobox.getRecord());
}
},
scope: this
}
});
this.down('#iterationContainer').add(iterationComboxBox);
}
},
_onFutureIterationSelected:function(iteration){
var that = this;
that._iteration = iteration.data._ref;
if (!this.down('#create')) {
var createButton = Ext.create('Ext.Container', {
items: [
{
xtype : 'rallybutton',
text : 'create a testset',
itemId: 'create',
handler: function() {
that._createTestSet();
}
}
]
});
this.add(createButton);
}
},
_createTestSet: function(){
var that = this;
console.log('create testset scheduled for ', that._iteration);
Rally.data.ModelFactory.getModel({
type: 'TestSet',
success: function(model) {
that._model = model;
var ts = Ext.create(model, {
Name: that._name + 'Copy',
Iteration: that._iteration
});
ts.save({
callback: function(result, operation) {
if(operation.wasSuccessful()) {
console.log(result.get('Name'), ' ', result.get('Iteration')._refObjectName);
that._readRecord(result);
}
else{
console.log("?");
}
}
});
}
});
},
_readRecord: function(result) {
var id = result.get('ObjectID');
this._model.load(id, {
fetch: ['Name','TestCases'],
callback: this._onRecordRead(result),
scope: this
});
},
_onRecordRead: function(record, operation) {
console.log('There are ', record.get('TestCases').Count, ' in ', record.get('Name') );
var that = this;
var testcaseStore = record.getCollection('TestCases');
testcaseStore.load({
callback: function() {
testcaseStore.add(that._testcases);
testcaseStore.sync({
callback: function() {
console.log('success');
}
});
}
});
}
});
There are a couple of Ruby scripts that might help you here:
https://github.com/markwilliams970/Rally-Test-Set-Export
https://github.com/markwilliams970/Rally-Add-TestCases-TestSet
These do require a working Ruby scripting environment and some familiarity with configuring/running scripts at the command line. However, working in combination, these should be enough to accomplish your goal.
I am trying to create a Custom HTML grid to show a list of all user stories with their different properties including name, id, schedule states and story types.
I am not getting the state and the type somehow, getting the id and name and some other fields.
Heres the code snippet for fetching them:
onScopeChange: function() {
Ext.create('Rally.data.WsapiDataStore', {
model: 'UserStory',
fetch: ['FormattedID','Name','State', 'Type','TestCases'],
pageSize: 100,
autoLoad: true,
filters: [this.getContext().getTimeboxScope().getQueryFilter()],
listeners: {
load: this._onDataLoaded,
scope: this
}
});
},
_onDataLoaded: function(store, data){
var stories = [];
var pendingTestCases = data.length;
Ext.Array.each(data, function(story) {
var s = {
FormattedID: story.get('FormattedID'),
Name: story.get('Name'),
_ref: story.get("_ref"),
State: story.get('ScheduleState'),
Type: story.get('StoryType'),
TestCaseCount: story.get('TestCases').Count,
TestCases: []
};
your fetch does not include 'ScheduleState' :
fetch: ['FormattedID','Name','State', 'Type','TestCases'],
ScheduleState shows as State in the UI to keep it short, but in the WS API it is referred to as ScheduleState. Please check with WS API for names of fields. Find HierarchicalRequirement in the object model.
Also you refer to Type as Type in the fetch and as StoryType later. Based on the name, it looks like this is a custom field. In WS API it would have c_ prepended.
I have an app that I am trying to use but it seems that while iterating through arrays and pushing into another array.i.e combining the arrays into one is not working for me. Example - I see all 213 pushes to this array but when I check its contents they are less.
Here is the code that shows me incomplete array push list.
For 213 test cases test set only 67 are pushed and present in the array
that = this;
that._testSetTestList = [];
console.log('testsetdata',testsetdata);
Ext.Array.each(testsetdata, function(record) {
console.log('record.get(TestCases)',record.get('TestCases'));
Ext.Array.each(record.get('TestCases'), function(name, index) {
that._testSetTestList.push({
resID: name.FormattedID,
resName: name.Name,
resObject: name.ObjectID,
resSetID: record.get('FormattedID'),
resSet: record.get('Name'),
resSetObject: record.get('ObjectID'),
resSetProject: name.Project.ObjectID
});
console.log('_testSetTestList.push',{
resID: name.FormattedID
});
});
});
Can anyone guide me to what I am doing wrong if anything.
Try using this code instead:
this._testSetTestList = Ext.Array.flatten(Ext.Array.map(testsetdata, function(record) {
return Ext.Array.map(record.get('TestCases'), function(name, index) {
return {
resID: name.FormattedID,
resName: name.Name,
resObject: name.ObjectID,
resSetID: record.get('FormattedID'),
resSet: record.get('Name'),
resSetObject: record.get('ObjectID'),
resSetProject: name.Project.ObjectID
};
});
}))
The issue in my case was not the code but the scope..I was trying to get the test case results for test cases that were not directly reachable in the project tree. We have the test cases residing in several projects but then we use them in test sets under different projects. If the test cases that are part of the queried test sets are directly reachable for the project for which we view this page, then test case results were accounted for BUT if the test cases were in projects that were siblings to the one that view the app from then the query could not find them and take their test case results. The solution was to consolidate all test cases under the correct project so that the app can access them from any required project.
Based on the example of using promises from this github repo, here is a code that builds a grid of test sets with their collection of test cases, where elements of array of test sets setsWithCases is pushed in to another array testsets, and the second array is used to populate the grid. The second array contains all elements of the first array. I am using LowDash _.each, included with AppSDK2.
Ext.define('CustomApp', {
extend: 'Rally.app.App',
componentsCls: 'app',
launch: function(){
var aStore = Ext.create('Rally.data.wsapi.Store', {
model: 'TestSet',
fetch: ['ObjectID', 'FormattedID', 'Name', 'TestCases'],
autoLoad: true,
context:{
projectScopeUp: false,
projectScopeDown: false
},
listeners:{
scope: this,
load: this._onStoreLoaded
}
});
},
_onStoreLoaded: function(store, records){
var setsWithCases = [];
var testsets = [];
var that = this;
var promises = [];
_.each(records, function(testset){
promises.push(that._getTestCases(testset, that));
});
Deft.Promise.all(promises).then({
success: function(results) {
_.each(results, function(result) {
if (result.TestCases.length > 0) {
setsWithCases.push(result);
}
});
_.each(setsWithCases, function(testset){
testsets.push(testset);
});
that._makeGrid(testsets);
}
});
},
_getTestCases:function(testset, scope){
var deferred = Ext.create('Deft.Deferred');
var that = scope;
var testcases = [];
var result = {};
var testsetRef = testset.get('_ref');
var testsetObjectID = testset.get('ObjectID');
var testsetFormattedID = testset.get('FormattedID');
var testsetName = testset.get('Name');
var testcaseCollection = testset.getCollection("TestCases", {fetch: ['Name', 'FormattedID']});
var testcaseCount = testcaseCollection.getCount();
testcaseCollection.load({
callback: function(records, operation, success){
_.each(records, function(testcase){
testcases.push(testcase);
});
result = {
"_ref": testsetRef,
"ObjectID": testsetObjectID,
"FormattedID": testsetFormattedID,
"Name": testsetName,
"TestCases": testcases
};
deferred.resolve(result);
}
});
return deferred;
},
_makeGrid:function(testsets){
var that = this;
var gridStore = Ext.create('Rally.data.custom.Store', {
data: testsets,
pageSize: 1000,
remoteSort: false
});
var aGrid = Ext.create('Rally.ui.grid.Grid', {
itemId: 'testsetGrid',
store: gridStore,
columnCfgs:[
{
text: 'Formatted ID', dataIndex: 'FormattedID', xtype: 'templatecolumn',
tpl: Ext.create('Rally.ui.renderer.template.FormattedIDTemplate')
},
{
text: 'Name', dataIndex: 'Name', flex: 1
},
{
text: 'TestCases', dataIndex: 'TestCases', flex:1,
renderer: function(value) {
var html = [];
_.each(value, function(testcase){
html.push('' + testcase.get('FormattedID') + '' + ' ' + testcase.get('Name'));
});
return html.join(', ');
}
}
]
});
that.add(aGrid);
}
});
I'm fairly new to Rally and so far have only used the web interface (I haven't used the Rally APIs from a programming languages yet). Occasionally we have a test set that we don't finish in an iteration, so we'd like to be able to copy the test set to the next iteration but retain the test case results entered so far in the new iteration so that we don't have to look in 2 different places for the complete test set results. Perhaps one solution is better iteration planning, but I'm still curious if there's a way to copy test case results along with a test set when copying a test set.
Test Case Result cannot be copied. It can be created in UI or Web Services API with the identical data, but it does not support a copy functionality.
For a general example of how to create a TCR object using a browser REST client see this SO post here.
Here is a poof of concept app that creates a copy of an existing TCR. The app filters TestSets by Iteration, and loads those TestSets into a combobox. Based on the TestSet selection in the combobox another combobox is created, populated with TestCases. When a Test Case is selected from that combobox a grid is built with TestCaseResults. Doubleclicking on a TCR in the grid will invoke a copy function. See AppSDK2 topic on how to copy records here. You may extend the code per your specifications. The source is in this github repo.
Minimally you need to change ObjectIDs of destination test case and destination test set in _copyRecordOnDoubleClick method below:
Ext.define('CustomApp', {
extend: 'Rally.app.TimeboxScopedApp',
componentCls: 'app',
scopeType: 'iteration',
comboboxConfig: {
fieldLabel: 'Select an Iteration:',
labelWidth: 100,
width: 300
},
onScopeChange: function() {
if (this.down('#testSetComboxBox')) {
this.down('#testSetComboxBox').destroy();
}
if (this.down('#testCaseComboxBox')) {
this.down('#testCaseComboxBox').destroy();
}
if (this.down('#resultsGrid')) {
this.down('#resultsGrid').destroy();
}
var testSetComboxBox = Ext.create('Rally.ui.combobox.ComboBox',{
id: 'testSetComboxBox',
storeConfig: {
model: 'TestSet',
pageSize: 100,
autoLoad: true,
filters: [this.getContext().getTimeboxScope().getQueryFilter()]
},
fieldLabel: 'select TestSet',
listeners:{
ready: function(combobox){
if (combobox.getRecord()) {
this._onTestSetSelected(combobox.getRecord());
}
else{
console.log('selected iteration has no testsets');
}
},
select: function(combobox){
if (combobox.getRecord()) {
this._onTestSetSelected(combobox.getRecord());
}
},
scope: this
}
});
this.add(testSetComboxBox);
},
_onTestSetSelected:function(selectedTestset){
var testCases = selectedTestset.getCollection('TestCases', {fetch: ['FormattedID','ObjectID', 'Results']});
var ts = {
FormattedID: selectedTestset.get('FormattedID'),
TestCaseCount: selectedTestset.get('TestCases').Count,
TestCases: [],
ResultCount: 0
};
testCases.load({
callback: function(records, operation, success){
Ext.Array.each(records, function(testcase){
console.log("testcase.get('FormattedID')", testcase.get('FormattedID'));
console.log("testcase.get('Results').Count", testcase.get('Results').Count);
ts.ResultCount = testcase.get('Results').Count;
ts.TestCases.push({_ref: testcase.get('_ref'),
FormattedID: testcase.get('FormattedID'),
ObjectID: testcase.get('ObjectID')
});
}, this);
this._makeTestCaseCombobox(ts.TestCases);
},
scope: this
});
},
_makeTestCaseCombobox:function(testcases){
if (this.down('#testCaseComboxBox')) {
this.down('#testCaseComboxBox').destroy();
}
if (this.down('#resultsGrid')) {
this.down('#resultsGrid').destroy();
}
if (testcases.length>0) {
var idArray = [];
_.each(testcases, function(testcase){
console.log(testcase);
console.log('OID', testcase['ObjectID']);
idArray.push(testcase['ObjectID']);
});
console.log('idArray',idArray);
var filterArray = [];
_.each(idArray, function(id){
filterArray.push(
{
property: 'ObjectID',
value:id
}
)
});
var filters = Ext.create('Rally.data.QueryFilter', filterArray[0]);
filterArray = _.rest(filterArray,1);
_.each(filterArray, function(filter){
filters = filters.or(filter)
},1);
var testCaseComboxBox = Ext.create('Rally.ui.combobox.ComboBox',{
id: 'testCaseComboxBox',
storeConfig: {
model: 'TestCase',
pageSize: 100,
autoLoad: true,
filters:filters,
fetch: true
},
fieldLabel: 'select TestCase',
listeners:{
ready: function(combobox){
if (combobox.getRecord()) {
this._onTestCaseSelected(combobox.getRecord());
}
else{
console.log('selected testset has no testcases');
}
},
select: function(combobox){
if (combobox.getRecord()) {
this._onTestCaseSelected(combobox.getRecord());
}
},
scope: this
}
});
this.add(testCaseComboxBox);
}
else{
console.log('selected testset has no testcases');
}
},
_onTestCaseSelected:function(selectedTestcase){
var results = selectedTestcase.getCollection('Results', {fetch: ['ObjectID','Date', 'TestSet', 'TestCase', 'Build', 'Verdict']});
var tc = {
ObjectID: selectedTestcase.get('ObjectID'),
FormattedID: selectedTestcase.get('FormattedID'),
Results: []
};
results.load({
callback: function(records, operation, success){
Ext.Array.each(records, function(result){
console.log("result.get('ObjectID')", result.get('ObjectID'));
console.log("result.get('Verdict')", result.get('Verdict'));
tc.Results.push({_ref: result.get('_ref'),
ObjectID: result.get('ObjectID'),
Date: result.get('Date'),
Build: result.get('Build'),
Verdict: result.get('Verdict')
});
}, this);
this._updateGrid(tc.Results);
},
scope: this
});
},
_updateGrid: function(results){
var store = Ext.create('Rally.data.custom.Store', {
data: results,
pageSize: 100
});
if (!this.down('#resultsGrid')) {
this._createGrid(store);
}
else{
this.down('#resultsGrid').reconfigure(store);
}
},
_createGrid: function(store){
var that = this;
var that = this;
var resultsGrid = Ext.create('Rally.ui.grid.Grid', {
id: 'resultsGrid',
store: store,
columnCfgs: [
{
text: 'ObjectID ID', dataIndex: 'ObjectID',
},
{
text: 'Date', dataIndex: 'Date',
},
{
text: 'Build', dataIndex: 'Build',
},
{
text: 'Verdict', dataIndex: 'Verdict',
},
],
listeners: {
celldblclick: function( grid, td, cellIndex, record, tr, rowIndex){
that._copyRecordOnDoubleClick(record);
}
}
});
this.add(resultsGrid);
},
_copyRecordOnDoubleClick: function(record){
var that = this;
console.log('record', record);
Rally.data.ModelFactory.getModel({
type: 'TestCaseResult',
success: function(model) {
that._model = model;
var copy = Ext.create(model, {
Date: record.get('Date'),
Build: record.get('Build'),
Verdict: record.get('Verdict'),
TestCase: '/testcase/17237838118',
TestSet: '/testset/17234968911'
});
copy.save({
callback: function(result, operation) {
if(operation.wasSuccessful()) {
console.log('result',result);
}
else{
console.log("problem");
}
}
});
}
});
}
});