def test_bad_server_spec(): """ Use a known to be invalid server name using prohibited characters in the server name. Do the same test using default access credentials and known correct valid credentials to an existing Rally server. The status_code in the response must indicate a non-success condition. """ bad_server = "ww!w.\fo,o\r\n.c%om" expectedErrMsg = "Unknown host" with py.test.raises(RallyRESTAPIError) as excinfo: rally = Rally(server=bad_server, timeout=3) response = rally.get('Project', fetch=False, limit=10) actualErrVerbiage = excinfo.value.args[0] # becuz Python2.6 deprecates message :-( assert excinfo.value.__class__.__name__ == 'RallyRESTAPIError' assert 'cannot resolve' in actualErrVerbiage and 'Unknown host' in actualErrVerbiage time.sleep(1) with py.test.raises(RallyRESTAPIError) as excinfo: rally = Rally(server=bad_server, user=TRIAL_USER, password=TRIAL_PSWD, timeout=3) response = rally.get('Project', fetch=False, limit=5) actualErrVerbiage = excinfo.value.args[0] # becuz Python2.6 deprecates message :-( assert excinfo.value.__class__.__name__ == 'RallyRESTAPIError' assert 'cannot resolve' in actualErrVerbiage and 'Unknown host' in actualErrVerbiage time.sleep(1)
def test_bad_server_spec(): """ Use a known to be invalid server name using prohibited characters in the server name. Do the same test using default access credentials and known correct valid credentials to an existing Rally server. The status_code in the response must indicate a non-success condition. """ bad_server = "ww!w.\fo,o\r\n.c%om" expectedErrMsg = "404 Target host: '%s' doesn't support the Rally WSAPI" % bad_server altErrText = "non-existent or unreachable" with py.test.raises(RallyRESTAPIError) as excinfo: rally = Rally(server=bad_server, timeout=3) response = rally.get('Project', fetch=False, limit=10) actualErrVerbiage = excinfo.value.args[0] # becuz Python2.6 deprecates message :-( assert excinfo.value.__class__.__name__ == 'RallyRESTAPIError' assert actualErrVerbiage == expectedErrMsg or altErrText in actualErrVerbiage with py.test.raises(RallyRESTAPIError) as excinfo: rally = Rally(server=bad_server, user=TRIAL_USER, password=TRIAL_PSWD, timeout=3) response = rally.get('Project', fetch=False, limit=5) actualErrVerbiage = excinfo.value.args[0] # becuz Python2.6 deprecates message :-( assert excinfo.value.__class__.__name__ == 'RallyRESTAPIError' assert actualErrVerbiage == expectedErrMsg or altErrText in actualErrVerbiage
def main(args): options = [opt for opt in args if opt.startswith('--')] args = [arg for arg in args if arg not in options] server, user, password, apikey, workspace, project = rallyWorkset(options) #rally = Rally(server, user, password, apikey=apikey, workspace=workspace) rally = Rally(server, user, password, workspace=workspace, project=project) rally.enableLogging("rally.history.addtags") if len(args) < 2: print(USAGE) sys.exit(1) story_id = args.pop(0) tag_names = args[:] tags = [] story = rally.get('Story', fetch="FormattedID,Name,Description,Tags", query="FormattedID = %s" % story_id, server_ping=False, isolated_workspace=True, instance=True) response = rally.get('Tag', fetch="true", order="Name", server_ping=False, isolated_workspace=True) for tag in response: print("Workspace %s has tag: %-14.14s created on %s Name: %s" % \ (tag.Workspace.Name, tag.oid, tag.CreationDate[:-5].replace('T', ' '), tag.Name)) if tag.Name in tag_names: tags.append(tag) print("=====================================================") print(", ".join([tag.Name for tag in tags])) adds = rally.addCollectionItems(story, tags) print(adds) droppable_tags = [tag for tag in tags if tag.Name == VICTIM_TAG_NAME] print("dropping Tags %s ..." % ", ".join([tag.Name for tag in droppable_tags])) drops = rally.dropCollectionItems(story, droppable_tags) if drops.errors: print("Problem attempting to drop tags: %s" % drops.errors) sys.exit(2) story = rally.get('Story', fetch="FormattedID,Name,Description,Tags", query="FormattedID = %s" % story_id, server_ping=False, isolated_workspace=True, instance=True) #print(story.details()) print "story tags after deleting the '%s' Tag" % (droppable_tags[0].Name) story_tags = [str(tag.Name) for tag in story.Tags] print(story_tags)
def test_getAllowedValues_for_UserStory_Milestone(): """ Using a known valid Rally server and known valid access credentials, request allowed value information for the Milestones field of the UserStory entity. The Milestones field is a standard field of schema type COLLECTION whose value is entirely context dependent on the specific artifact so getting allowed values doesn't really make sense in the same way as an attribute like State or Severity that has a finite set of possible values that are the same for every Story or Defect in the workspace. Because of that characteristic, we return a list with a single True value ( [True] ) to designate that yes, technically the Milestones field has allowed values but that asking for them on a specific AC artifact short-circuits. The proper way to get all of the AllowedValues for Milestones is to query the Milestone entity itself. There are numerous other standard attributes with the same sort of semantic that are excluded from chasing the COLLECTION url and returning some list of values. (like, Changesets, Discussions, Tags, etc.) """ rally = Rally(server=AGICEN, apikey=API_KEY) avs = rally.getAllowedValues('Story', 'Milestones') assert avs == [True] response = rally.get('Milestone', fetch=True, workspace=LARGE_WORKSPACE, project=LARGE_PROJECT_TREE_BASE, projectScopeDown=True) milestones = [item for item in response] assert len(milestones) > 150 # Given the singular name of the target field (which is invalid...) return a None value avs = rally.getAllowedValues('Story', 'Milestone') assert avs is None
class Avant_Rally(object): iterations = [] rally = None def __init__(self, project): self.project = project def connect(self, username, password): self.rally = Rally(server, user, password, project=self.project) self.rally.enableLogging('rally.simple-use.log') def fetch_Iterations(self): self.iterations = [] response = self.rally.get('Iteration', fetch=True) for rls in response: iter = Iteration() rlsStart = rls.StartDate.split('T')[0] # just need the date part rlsDate = rls.EndDate.split('T')[0] # ditto self.iterations.append(iter.set_Iteration(rlsStart, rlsDate, rls.Name, rls.PlannedVelocity, self.rally)) def display_Iterations(self): for i in self.iterations: print "\n\n%s %s --> %s\t" % \ (i.name, i.start_date, i.end_date) i.display_User_Stories(i.name)
def main(args): options = [opt for opt in args if opt.startswith('--')] args = [arg for arg in args if arg not in options] server, user, password, apikey, workspace, project = rallyWorkset(options) rally = Rally(server, user, password, apikey=apikey, workspace=workspace, project=project) entity_name = 'Milestone' fields = 'FormattedID,Name,TargetProject,TargetDate,TotalArtifactCount' response = rally.get(entity_name, fetch=fields, order="TargetDate,FormattedID", project=project, projectScopeDown=True) if response.errors: errout("Request could not be successfully serviced, error code: %d\n" % response.status_code) errout("\n".join(response.errors)) sys.exit(1) if response.resultCount == 0: errout('No items found for %s\n' % entity_name) sys.exit(2) milestones = [item for item in response] sans_project = [mi for mi in milestones if not mi.TargetProject] with_project = [mi for mi in milestones if mi.TargetProject] with_project.sort(key=lambda mi: mi.TargetProject.Name) for item in (with_project + sans_project): proj_name = item.TargetProject.Name if item.TargetProject else "" print(" %15.15s %-6.6s %-36.36s %3d %-10.10s %s " % \ (item.oid, item.FormattedID, item.Name, item.TotalArtifactCount, item.TargetDate, proj_name))
def test_get_distant_duplicated_project(): """ Using a known valid Rally server and known valid access credentials, obtain a Rally instance and use it to obtain a Project instance for a Project whose name contains multiple path elements with the elements separated by the ' // ' token string. Expect the result to return one and only one Project that is the correct Project. The result should have the correct Parent Project. When the Rally instance is called to setProject with the value of that multi element path for the Project it should do so and should return the correct value when asked for the current Project. """ rally = Rally(server=TRIAL, user=YETI_USER, password=YETI_PSWD, workspace=BOONDOCKS_WORKSPACE, project=BOONDOCKS_PROJECT) dupey_project = rally.getProject(DEEP_DUPE) assert dupey_project is not None assert dupey_project.__class__.__name__ == 'Project' assert dupey_project.Name == DEEP_DUPE criteria = 'Name = "%s"' % 'Corral' expected_parent = rally.get('Project', fetch="Name,ObjectID,Parent,Children", query=criteria, projectScopeDown=False, instance=True) assert expected_parent is not None assert expected_parent.__class__.__name__ == 'Project' assert expected_parent.Name == 'Corral' assert dupey_project.Parent.ref == expected_parent.ref result = rally.setProject(DEEP_DUPE) assert result is None cur_project = rally.getProject() assert cur_project.Name == DEEP_DUPE
def test_set_mep_project_used_as_default_in_request_operation(): """ Using a known valid Rally server and known valid access credentials, obtain a Rally instance associated with a unique Project name within a valid Workspace. Subsequently, set the instance's Project to a Project whose name is a duplicate. The duplicate Project is specified as a path chain of: baseProject // nextLevelProject // leafProject At least one of the other non-target duplicates should exist in a shorter path. Issue a request using the target duplicate Project m-e-p. The result should be an Artifact whose projet matches the target duplicate Project leaf name and ref exactly. """ rally = Rally(server=TRIAL, user=YETI_USER, password=YETI_PSWD, workspace=BOONDOCKS_WORKSPACE, project=BOONDOCKS_PROJECT) rally.setProject(DEEP_DUPE) target_story = 'US3' result = rally.get('Story', fetch="FormattedID,Name,Description,State,Project", query='FormattedID = %s' % target_story, projectScopeUp=False) assert result is not None assert result.resultCount > 0 stories = [story for story in result] assert len(stories) > 0 hits = [story for story in stories if story.FormattedID == target_story] assert len(hits) == 1 hit = hits[0] assert hit.FormattedID == target_story
def test_two_conditions_query_as_dict(): rally = Rally(server=TRIAL, user=TRIAL_USER, password=TRIAL_PSWD) qualifiers = {'State' : 'Submitted', 'Ready' : 'False' } response = rally.get('Defect', fetch=True, query=qualifiers, limit=10) assert response.resultCount > 0
def test_defects_revision_history(): """ Using a known valid Rally server and known valid access credentials, issue a simple query (no qualifying criteria) against a Rally entity (Defect) known to have an attribute (RevisionHistory) that has an attribute (Revisions) that is a Rally collections reference. This test demonstrates the lazy-evaluation of non first-level attributes. Ultimately, the attributes deeper than the first level must be obtained and have their attributes filled out completely (_hydrated == True). """ rally = Rally(server=TRIAL, user=TRIAL_USER, password=TRIAL_PSWD) response = rally.get('Defect', fetch=True, limit=10) defect1 = response.next() defect2 = response.next() assert defect1.oid != defect2.oid d1_revs = defect1.RevisionHistory.Revisions d2_revs = defect2.RevisionHistory.Revisions assert type(d1_revs) == types.ListType assert type(d2_revs) == types.ListType d1_rev1 = d1_revs.pop() # now the revs are in stack order, newest first, original the last d2_rev1 = d2_revs.pop() # ditto assert d1_rev1.RevisionNumber == 0 assert d2_rev1.RevisionNumber == 0 assert d1_rev1.Description != "" and len(d1_rev1.Description) > 0 assert d2_rev1.Description != "" and len(d2_rev1.Description) > 0 assert d1_rev1._hydrated == True assert d2_rev1._hydrated == True
def main(args): options = [opt for opt in args if opt.startswith('--')] server, user, password, workspace, project = rallySettings(options) rally = Rally(server, user, password, workspace=workspace) rally.enableLogging("rally.history.blddefs") for workspace, project in wps: print "workspace: %s project: %s" % (workspace, project) rally.setWorkspace(workspace) response = rally.get('BuildDefinition', fetch=True, order='Name', workspace=workspace, project=project) if response.errors: print response.errors sys.exit(9) for builddef in response: if builddef.Project.Name != project: continue if builddef.LastStatus == "NO BUILDS": print "NO BUILDS" continue #print builddef.oid, builddef.Name, builddef.LastStatus lbt = builddef.LastBuild.CreationDate.split('T') last_build_time = "%s %s" % (lbt[0], lbt[1][:5] ) bd_name = "%-24.24s" % builddef.Name status = "%-10.10s" % builddef.LastStatus print builddef.oid, builddef.CreationDate[:10], \ bd_name, status, last_build_time, len(builddef.Builds) print "\n"
def main(args): options = [opt for opt in args if opt.startswith('--')] server, user, password, workspace, project = rallySettings(options) rally = Rally(server, user, password, workspace=workspace) rally.enableLogging("rally.history.blddefs") for workspace, project in wps: rally.setWorkspace(workspace) print "workspace: %s project: %s\n" % (workspace, project) response = rally.get('BuildDefinition', fetch=True, query='Project.Name = "%s"' % project, order='Name', workspace=workspace, project=project) if response.errors: print response.errors sys.exit(9) print "%-12.12s %-10.10s %-36.36s %12s %-20.20s %s" % \ ('BuildDef OID', 'CreateDate', 'BuildDefinition.Name', 'LastStatus', 'LastBuildDateTime', 'NumBuilds') print "%-12.12s %-10.10s %-36.36s %10s %-19.19s %s" % \ ('-' * 12, '-' * 10, '-' * 36, '-' * 10, '-' * 19, '-' * 9) for builddef in response: if builddef.LastStatus == "NO BUILDS": print "%s %s %-24.24s NO BUILDS" % \ (builddef.oid, builddef.CreationDate[:10], builddef.Name) continue lbt = builddef.LastBuild.CreationDate.split('T') last_build_time = "%s %s" % (lbt[0], lbt[1][:8] ) bdf = "%12.12s %-10.10s %-36.36s %12s %-20.20s %4s" print bdf % (builddef.oid, builddef.CreationDate[:10], builddef.Name, builddef.LastStatus, last_build_time, len(builddef.Builds))
def basic_connection(): """ Using a known valid Rally server and access credentials, issue a simple query request against a known valid Rally entity. """ rally = Rally(server=PROD, user=PROD_USER, password=PROD_PSWD) response = rally.get('Project', fetch=False, limit=10) print response
def get_story(formatted_id): r = Rally(server, apikey=apikey, project=project) r.enableLogging('rally.log') aa = r.get('UserStory', fetch=True, query='FormattedID = "' + formatted_id + '"', instance=True) return dict_from_story(aa)
def test_delete_pull_request(): #rally = Rally(server=TESTN, user=TESTN_USER, password=TESTN_PSWD) rally = Rally(server=AGICEN, apikey=AGICEN_SUB_100_API_KEY) attrs = "ExternalId,ExternalFormattedId,Artifact,Name,Url,Description" response = rally.get('PullRequest', fetch=attrs, project=None) assert response.status_code == 200 assert len(response.errors) == 0 assert len(response.warnings) == 0 prs = [pr for pr in response] assert len(prs) > 0 victim = prs[0] result = rally.delete('PullRequest', victim.oid, project=None) assert result == True response = rally.get('PullRequest', fetch=attrs, query='ObjectID = %s' % victim.oid) ghosts = [pr for pr in response] assert not ghosts
def test_limit_query(): """ Use a pagesize of 200 and a limit of 80 in the params in the URL """ rally = Rally(server=TRIAL, user=TRIAL_USER, password=TRIAL_PSWD) qualifier = "State = Submitted" response = rally.get('Defect', fetch=True, query=qualifier, pagesize=200, limit=80) items = [item for item in response] assert len(items) == 80
def test_start_and_limit_query(): """ Use a pagesize of 50 and a start index value of 20 and a limit of 60 in the params in the URL """ rally = Rally(server=TRIAL, user=TRIAL_USER, password=TRIAL_PSWD) qualifier = "State = Submitted" response = rally.get('Defect', fetch=True, query=qualifier, pagesize=50, start=20,limit=60) items = [item for item in response] assert len(items) == 60
def main(args): options = [opt for opt in args if opt.startswith('--')] args = [arg for arg in args if arg not in options] server, username, password, apikey, workspace, project = rallyWorkset(options) if apikey: rally = Rally(server, apikey=apikey, workspace=workspace, project=project) else: rally = Rally(server, user=username, password=password, workspace=workspace, project=project) rally.enableLogging("rally.hist.add_tcrs") if len(args) < 2: errout(USAGE) sys.exit(1) test_case_id, tcr_info_filename = args if not os.path.exists(tcr_info_filename): errout("ERROR: file argument '%s' does not exist. Respecify using corrent name or path\n" % tcr_info_filename) errout(USAGE) sys.exit(2) try: with open(tcr_info_filename, 'r') as tcif: content = tcif.readlines() tcr_info = [] # each line must have Build, Date, Verdict for ix, line in enumerate(content): fields = line.split(',') if len(fields) != 3: raise Exception('Line #%d has invalid number of fields: %s' % (ix+1, repr(fields))) tcr_info.append([field.strip() for field in fields]) except Exception: errout("ERROR: reading file '%s'. Check the permissions or the content format for correctness." % tcr_info_filename) errout(USAGE) sys.exit(2) test_case = rally.get('TestCase', query="FormattedID = %s" % test_case_id, workspace=workspace, project=None, instance=True) if not test_case or hasattr(test_case, 'resultCount'): print "Sorry, unable to find a TestCase with a FormattedID of %s in the %s workspace" % \ (test_case_id, workspace) sys.exit(3) wksp = rally.getWorkspace() for build, run_date, verdict in tcr_info: tcr_data = { "Workspace" : wksp.ref, "TestCase" : test_case.ref, "Build" : build, "Date" : run_date, "Verdict" : verdict } try: tcr = rally.create('TestCaseResult', tcr_data) except RallyRESTAPIError, details: sys.stderr.write('ERROR: %s \n' % details) sys.exit(4) print "Created TestCaseResult OID: %s TestCase: %s Build: %s Date: %s Verdict: %s" % \ (tcr.oid, test_case.FormattedID, tcr.Build, tcr.Date, tcr.Verdict)
def test_basic_connection(): """ Using a known valid Rally server and access credentials, issue a simple query request against a known valid Rally entity. """ rally = Rally(server=TRIAL, user=TRIAL_USER, password=TRIAL_PSWD) response = rally.get('Project', fetch=False, limit=10) assert response != None assert response.status_code == 200 time.sleep(1)
def test_start_value_query(): """ Use a pagesize of 200 and a start index value of 300 in the params in the URL """ rally = Rally(server=TRIAL, user=TRIAL_USER, password=TRIAL_PSWD) qualifier = "State = Submitted" response = rally.get('Defect', fetch=True, query=qualifier, pagesize=200, start=300) items = [item for item in response] assert len(items) > 200 assert len(items) < 600
def test_rank_story_to_bottom(): rally = Rally(server=TRIAL, user=TRIAL_USER, password=TRIAL_PSWD, server_ping=False, isolated_workspace=True) response = rally.get('Story', fetch="FormattedID,Name,Description,State,DragAndDropRank", order="Rank ASC", limit=100) stories = [story for story in response] assert len(stories) > 6 first_story = stories[0] target_story = stories[1] assert target_story.DragAndDropRank > first_story.DragAndDropRank result = rally.rankToBottom(target_story) assert result.status_code == 200 response = rally.get('Story', fetch="FormattedID,Name,Description,State,DragAndDropRank", order="Rank ASC", limit=100) stories = [story for story in response] top_story = stories[0] bottom_story = stories[-1] assert bottom_story.FormattedID == target_story.FormattedID
def test_five_condition_query_in_list(): rally = Rally(server=TRIAL, user=TRIAL_USER, password=TRIAL_PSWD) qualifiers = ["State = Submitted", "FormattedID < DE6000", "FormattedID != DE5986", 'Priority = "High Attention"', "Severity != Cosmetic" ] response = rally.get('Defect', fetch=True, query=qualifiers, limit=10) assert response.resultCount > 0
def test_rank_story_below(): rally = Rally(server=TRIAL, user=TRIAL_USER, password=TRIAL_PSWD, server_ping=False, isolated_workspace=True) response = rally.get('Story', fetch="FormattedID,Name,Description,State,DragAndDropRank", order="Rank ASC", limit=100) stories = [story for story in response] assert len(stories) > 6 story1 = stories[2] story2 = stories[4] assert story1.DragAndDropRank < story2.DragAndDropRank result = rally.rankBelow(story2, story1) assert result.status_code == 200 response = rally.get('Story', fetch="FormattedID,Name,Description,State,DragAndDropRank", order="Rank ASC", limit=100) stories = [story for story in response] assert stories[3].FormattedID == story2.FormattedID assert stories[4].DragAndDropRank > story2.DragAndDropRank
def test_basic_connection_with_apikey(): """ Using a known valid Rally server and valid API Key value, issue a simple query request against a known valid Rally target. """ rally = Rally(server=PROD, apikey=API_KEY) response = rally.get('Project', fetch=False, limit=10) assert response != None assert response.status_code == 200 time.sleep(1)
class RallyClient: rally = None debug = False PrefixActionMap = {"US": "HierarchicalRequirement", "DE": "Defect" } def __init__(self, config): self.rally = Rally(config.rallyUrl, config.username, config.password, workspace="Betfair", project="Betfair") self.rally.enableLogging('rallycli.log') self.debug = config.debug def retrieveItems(self, itemIds): ''' Use pyral to retrieve items from Rally. ''' items = {} for itemId in itemIds: query_criteria = 'formattedID = "%s"' % itemId prefix = itemId[0:2] response = self.rally.get(self.PrefixActionMap[prefix], fetch=True, query=query_criteria) if self.debug: print response.content if response.errors: sys.stdout.write("\n".join(response.errors)) print "ERROR" sys.exit(1) for item in response: # there should only be one qualifying item # items[itemId] = item # print "%s: %s (%s)" % (item.FormattedID, item.Name, item.Project.Name) items[item.FormattedID] = item return items def info(self, args): ''' Return information for specified work items, in a variety of formats. ''' itemIds = args.workItems # print "Retrieving items %s..." % (itemIds) items = self.retrieveItems(itemIds) for itemId, item in items.iteritems(): if item == None: print "ERROR: Could not retrieve item %s from Rally" % itemId else: # print item.attributes() # print item.ObjectID # @TODO Refactor these into configurable/dynamic values baseUrl = "https://rally1.rallydev.com/#" workspaceId = "3254856811d" itemUrl = "%s/%s/detail/userstory/%s" % (baseUrl, workspaceId, item.ObjectID) if args.format == "confluence" : print "# [%s: %s|%s]" % (itemId, item.Name, itemUrl) elif args.format == "conftable" : print "| %s | %s | %s |" % (itemId, item.Name, itemUrl) elif args.format == "csv": print "%s,%s,%s" % (itemId, item.Name, itemUrl) elif args.format == "tsv": print "%s\t%s\t%s" % (itemId, item.Name, itemUrl) else: print "%s: %s (%s)" % (itemId, item.Name, itemUrl)
def test_query_with_special_chars_in_criteria(): """ DE3228 in DEFAULT_WORKSPACE / NON_DEFAULT_PROJECT has Name = Special chars:/!@#$%^&*()-=+[]{};:./<>?/ query for it by looking for it by the name value """ rally = Rally(server=TRIAL, user=TRIAL_USER, password=TRIAL_PSWD) rally.setWorkspace(DEFAULT_WORKSPACE) rally.setProject(NON_DEFAULT_PROJECT) rally.enableLogging('spec_char_query') criteria = 'Name = "distinctive criteria of -32% degradation in rust protection"' response = rally.get('Defect', fetch=True, query=criteria, limit=10) assert response.__class__.__name__ == 'RallyRESTResponse' assert response.status_code == 200 assert response.errors == [] assert response.warnings == [] assert response.resultCount == 1 criteria = 'Name = "Looking for the #blowback hashtag"' response = rally.get('Defect', fetch=True, query=criteria, limit=10) assert response.status_code == 200 assert response.errors == [] assert response.warnings == [] assert response.resultCount == 1 special_chars = "/!@#$%^*_-+=?{}[]:;,<>" # characters that break the RallyQueryFormatter and/or WSAPI: ( ) ~ & | backslash for character in special_chars: criteria = 'Name contains "%s"' % character response = rally.get('Defect', fetch=True, query=criteria, limit=10) assert response.__class__.__name__ == 'RallyRESTResponse' assert response.status_code == 200 assert response.errors == [] assert response.warnings == [] assert response.resultCount >= 1 criteria = 'Name = "Special chars:/!@#$%^*-=+[]{};:.<>? in the name field"' response = rally.get('Defect', fetch=True, query=criteria, limit=10) assert response.__class__.__name__ == 'RallyRESTResponse' assert response.status_code == 200 assert response.errors == [] assert response.warnings == [] assert response.resultCount >= 1
def test_bogus_query(): """ Using a known valid Rally server and known valid access credentials, issue a simple query specifying a entity for which there is no valid Rally entity. The status_code in the response must not indicate a valid request/response and the errors attribute must have some descriptive info about the error. """ rally = Rally(server=PREVIEW, user=PREVIEW_USER, password=PREVIEW_PSWD) response = rally.get('payjammas', fetch=False, limit=10) assert response.status_code != 200 assert len(response.errors) > 0
def test_test_folder_fields(): """ Using a known valid Rally server and known valid access credentials, issue a simple query (no qualifying criteria) for a known valid Rally entity, and observe that you can access both standard and custom fields by the field Display Name. """ rally = Rally(apikey=APIKEY, workspace=WORKSPACE, project=PROJECT, isolated_workspace=True) response = rally.get('TestFolder', fetch=True, projectScopeDown=True) assert response.status_code == 200 assert response.resultCount > 10 tf = response.next() assert tf.TestFolderStatus is not None assert tf.TestFolderStatus.Name == 'Unknown' response2 = rally.get('TestFolder', fetch="FormattedID,Name,Parent,Children", projectScopeDown=True) assert response2.status_code == 200 assert response2.resultCount > 10 tf = response2.next()
def test_add_attachment(): """ """ rally = Rally(server=TRIAL, user=TRIAL_USER, password=TRIAL_PSWD) # find a Project with some US artifacts # pick one with no attachments # create an attachment file (or choose a smallish file with a commonly used suffix) # create the attachment in Rally and link it to the US artifact wksp = rally.getWorkspace() assert wksp.Name == DEFAULT_WORKSPACE response = rally.get('Project', fetch=False, limit=10) assert response != None assert response.status_code == 200 proj = rally.getProject() # proj.Name == DEFAULT_PROJECT assert proj.Name == DEFAULT_PROJECT #response = rally.get("UserStory", fetch="FormattedID,Name,Attachments") #for story in response: # print "%s %-48.48s %d" % (story.FormattedID, story.Name, len(story.Attachments)) candidate_story = "US1" # was "US96" in trial response = rally.get("UserStory", fetch="FormattedID,Name,Attachments", query='FormattedID = "%s"' % candidate_story) ##print(response.resultCount) story = response.next() assert len(story.Attachments) == 0 attachment_name = "Addendum.txt" att_ok = conjureUpAttachmentFile(attachment_name) assert att_ok == True att = rally.addAttachment(story, attachment_name) assert att.Name == attachment_name response = rally.get("UserStory", fetch="FormattedID,Name,Attachments", query='FormattedID = "%s"' % candidate_story) story = response.next() assert len(story.Attachments) == 1
def main(args): options = [opt for opt in args if opt.startswith('--')] args = [arg for arg in args if arg not in options] entity = args.pop(0) attributes = args server, user, password, apikey, workspace, project = rallyWorkset(options) print(" ".join([ "|%s|" % item for item in [server, user, password, apikey, workspace, project] ])) #rally = Rally(server, user, password, apikey=apikey, workspace=workspace, project=project, server_ping=False) rally = Rally(server, user, password, apikey=apikey, server_ping=False) rally.enableLogging( 'rally.hist.avl') # name of file you want the logging to go to target = entity if entity in ['Story', 'User Story', 'UserStory']: entity = "HierarchicalRequirement" target = entity mo = CAMEL_CASED_NAME_PATT.search(entity) if mo: txfm = re.sub(CAMEL_CASED_NAME_PATT, r'\1 \2', entity) print('transforming query target "%s" to "%s"' % (entity, txfm)) entity = txfm print("%s" % entity) response = rally.get('TypeDefinition', fetch="Name,Attributes", query='Name = "%s"' % entity) # could check for response.errors here... if response.errors: print("Errors: %s" % response.errors) if response.warnings: print("Warnings: %s" % response.warnings) td = response.next() for attribute in td.Attributes: attr_name = attribute.Name.replace(' ', '') if attributes and attr_name not in attributes: continue if attribute.AttributeType not in ['STATE', 'RATING', 'STRING']: continue allowed_values = rally.getAllowedValues(target, attr_name) if not allowed_values: continue print(" %-28.28s (%s)" % (attr_name, attribute.AttributeType)) for av in allowed_values: print(" |%s|" % av)
def test_simple_named_fields_query(): """ Using a known valid Rally server and known valid access credentials, issue a simple query (no qualifying criteria) for a known valid Rally entity. The fetch specifies a small number of known valid attributes on the Rally entity. """ rally = Rally(server=TRIAL, user=TRIAL_USER, password=TRIAL_PSWD) response = rally.get('Project', fetch="Owner,State", limit=10) assert response.status_code == 200 assert len(response.errors) == 0 assert len(response._page) > 0
def test_basic_query(): """ Using a known valid Rally server and known valid access credentials, issue a simple query (no qualifying criteria) for a known valid Rally entity. """ rally = Rally(server=TRIAL, user=TRIAL_USER, password=TRIAL_PSWD) response = rally.get('Project', fetch=False, limit=10) assert response.status_code == 200 assert response.errors == [] assert response.warnings == [] assert response.resultCount > 0
def test_simple_named_fields_query(): """ Using a known valid Rally server and known valid access credentials, issue a simple query (no qualifying criteria) for a known valid Rally entity. The fetch specifies a small number of known valid attributes on the Rally entity. """ rally = Rally(server=PREVIEW, user=PREVIEW_USER, password=PREVIEW_PSWD) response = rally.get('Project', fetch="Owner,State", limit=10) assert response.status_code == 200 assert len(response.errors) == 0 assert len(response._page) > 0
def test_default_connection(): """ Using a known valid Rally server and access credentials, connect without specifying workspace or project. Return status should be OK, Rally._wpCacheStatus should be 'minimal' """ rally = Rally(server=AGICEN, user=AGICEN_USER, password=AGICEN_PSWD) response = rally.get('Project', fetch=False, limit=10) assert response != None assert response.status_code == 200 assert rally._wpCacheStatus() == 'minimal'
def main(args): options = [opt for opt in args if opt.startswith('--')] args = [arg for arg in args if arg not in options] server, user, password, workspace, project = rallySettings(options) print " ".join([ "|%s|" % item for item in [server, user, '********', workspace, project] ]) rally = Rally(server, user, password) # specify the Rally server and credentials rally.enableLogging( 'rally.hist.item') # name of file you want logging to go to if len(args) != 1: errout(USAGE) sys.exit(2) ident = args[0] mo = FORMATTED_ID_PATT.match(ident) if mo: ident_query = 'FormattedID = "%s"' % ident entity_name = ARTIFACT_TYPE[mo.group('prefix')] else: errout('ERROR: Unable to determine ident scheme for %s\n' % ident) sys.exit(3) response = rally.get(entity_name, fetch=True, query=ident_query) if response.errors: errout("Request could not be successfully serviced, error code: %d\n" % response.status_code) errout("\n".join(response.errors)) sys.exit(1) if response.resultCount == 0: errout('No item found for %s %s\n' % (entity_name, ident)) sys.exit(4) elif response.resultCount > 1: errout('WARNING: more than 1 item returned matching your criteria\n') for item in response: for attr in COMMON_ATTRIBUTES: print " %-16.16s : %s" % (attr, getattr(item, attr)) attrs = [ attr for attr in item.attributes() if attr not in COMMON_ATTRIBUTES ] for attr in sorted(attrs): attribute = getattr(item, attr) cn = attribute.__class__.__name__ if cn[0] in string.uppercase: attribute = attribute.Name if cn != 'NoneType' else None print " %-16.16s : %s" % (attr, attribute)
def main(args): options = [opt for opt in args if opt.startswith('-')] args = [arg for arg in args if arg not in options] #if len(args) != 1: # errout('ERROR: Wrong number of arguments\n') # sys.exit(3) #args = ["US504765"] # no TF #args = ["US487422"] #for Titans server = 'rally1.rallydev.com' apikey = '_LhzUHJ1GQJQWkEYepqIJV9NO96FkErDpQvmHG4WQ' workspace = 'Sabre Production Workspace' project = 'Sabre' project = 'LGS Titans (BLR)' print('Logging in...') rally = Rally(server, apikey=apikey, workspace=workspace, project=project) print('Query execution...') for arg in args: if arg[0] == "D": entityName = 'Defect' elif arg[0] == "U": entityName = 'HierarchicalRequirement' else: entityName = 'PortfolioItem' #queryString = 'FormattedID = "%s"' % arg queryString = '(Iteration.StartDate > "2017-12-31")' entityName = 'HierarchicalRequirement' print("Query = ", queryString) response = rally.get(entityName, fetch=True, projectScopeDown=True, query=queryString) if response.resultCount == 0: errout('No item found for %s %s\n' % (entityName, arg)) else: fileName = 'out.csv' with open(fileName, 'w', newline='') as csvfile: outfile = csv.writer(csvfile, delimiter=',', quotechar='"', quoting=csv.QUOTE_MINIMAL) outrow = [field for field in gAttribs] outfile.writerow(outrow) for item in response: outfile.writerow( [get_deep_attr(item, param) for param in gAttribs])
def main(): # Parse command line inParser = argparse.ArgumentParser() buildInputParser(inParser) args = inParser.parse_args() if args.infile: tokens = args.IDs + getTokens(args.infile) else: tokens = args.IDs # Rally setup server = 'rally1.rallydev.com' apikey = '_LhzUHJ1GQJQWkEYepqIJV9NO96FkErDpQvmHG4WQ' workspace = 'Sabre Production Workspace' project = 'Sabre' #print ('Logging in...') rally = Rally(server, apikey=apikey, workspace=workspace, project=project) #print ('Start queries...') for id in tokens: if id[0] == "U": entityName = 'HierarchicalRequirement' elif id[0] == "T": entityName = 'PortfolioItem' elif id[0] == "F": entityName = 'PortfolioItem' else: continue queryString = 'FormattedID = "%s"' % id response = rally.get(entityName, fetch=True, projectScopeDown=True, query=queryString) if response.resultCount > 0: for item in response: if id[0] == "U": if item.TeamFeature == None: outstring = '%s, %s, "%s"' % (item.FormattedID, 'None', 'None') else: outstring = '%s, %s, "%s"' % ( item.FormattedID, item.TeamFeature.FormattedID, item.TeamFeature.Name.encode( 'ascii', 'replace')) #good for US else: if item.Parent == None: outstring = '%s, %s, "%s"' % (item.FormattedID, 'None', 'None') else: outstring = '%s, %s, "%s"' % ( item.FormattedID, item.Parent.FormattedID, item.Parent.Name.encode( 'ascii', 'replace')) #good for TF and FEA print(outstring)
def test_single_condition_query_parenned(): """ Using a known valid Rally server and known valid access credentials, issue a query with a single qualifying criterion against a Rally entity (Defect) known to exist for which the qualifying criterion should return one or more Defects. The qualifying criterion is a string that _is_ surrounded with paren chars. """ rally = Rally(server=RALLY, user=RALLY_USER, password=RALLY_PSWD) qualifier = "(State = Submitted)" #qualifier = '(FormattedID = "US100")' response = rally.get('Defect', fetch=True, query=qualifier, limit=10) assert response.resultCount > 0
def test_rank_story_to_top(): """ """ rally = Rally(server=AGICEN, user=AGICEN_USER, password=AGICEN_PSWD, server_ping=False, isolated_workspace=True) response = rally.get('Story', fetch="FormattedID,Name,Description,State,DragAndDropRank", order="Rank ASC", limit=100) stories = [story for story in response] assert len(stories) > 6 first_story = stories[0] target_story = stories[4] assert first_story.DragAndDropRank < target_story.DragAndDropRank result = rally.rankToTop(target_story) assert result.status_code == 200 response = rally.get('Story', fetch="FormattedID,Name,Description,State,DragAndDropRank", order="Rank ASC", limit=100) stories = [story for story in response] top_story = stories[0] bottom_story = stories[-1] assert top_story.FormattedID == target_story.FormattedID assert top_story.DragAndDropRank < stories[1].DragAndDropRank
def test_rank_story_above(): """ Using a known valid Rally server and known valid access credentials, obtain a Rally instance and issue a get for Story items ordered by Rank ASC. """ rally = Rally(server=AGICEN, user=AGICEN_USER, password=AGICEN_PSWD, server_ping=False, isolated_workspace=True) response = rally.get('Story', fetch="FormattedID,Name,Description,State,DragAndDropRank", order="Rank ASC", limit=100) stories = [story for story in response] assert len(stories) > 6 story1 = stories[0] story2 = stories[4] assert story1.DragAndDropRank < story2.DragAndDropRank result = rally.rankAbove(story1, story2) assert result.status_code == 200 response = rally.get('Story', fetch="FormattedID,Name,Description,State,DragAndDropRank", order="Rank ASC", limit=100) stories = [story for story in response] assert stories[0].FormattedID == story2.FormattedID assert stories[0].DragAndDropRank < story2.DragAndDropRank
def test_two_condition_query_parenned(): """ Using a known valid Rally server and known valid access credentials, issue a query with two qualifying conditions against a Rally entity (Defect) known to exist for which the qualifying criterion should return one or more Defects. The qualifying criterion is a string that _is_ surrounded with paren chars and each condition itself is surrounded by parens.. """ rally = Rally(server=TRIAL, user=TRIAL_USER, password=TRIAL_PSWD) qualifiers = "(State = Submitted) AND (FormattedID != US100)" response = rally.get('Defect', fetch=True, query=qualifiers, limit=10) assert response.resultCount > 0
def test_two_condition_query_in_list(): """ Using a known valid Rally server and known valid access credentials, issue a query with two qualifying conditions against a Rally entity (Defect) known to exist for which the qualifying criterion should return one or more Defects. The qualifying criterion is a list that contains two condition strings, each condition string does _not_ have any surrounding paren chars. """ rally = Rally(server=TRIAL, user=TRIAL_USER, password=TRIAL_PSWD) qualifiers = ["State = Submitted", "FormattedID != US100"] response = rally.get('Defect', fetch=True, query=qualifiers, limit=10) assert response.resultCount > 0
def test_limit_query(): """ Use a pagesize of 200 and a limit of 80 in the params in the URL """ rally = Rally(server=TRIAL, user=TRIAL_USER, password=TRIAL_PSWD) qualifier = "State = Submitted" response = rally.get('Defect', fetch=True, query=qualifier, pagesize=100, limit=30) items = [item for item in response] assert len(items) == 30
def main(args): options = [opt for opt in args if opt.startswith('--')] args = [arg for arg in args if arg not in options] server, user, password, apikey, workspace, project = rallyWorkset(options) if apikey: rally = Rally(server, apikey=apikey, workspace=workspace, project=project) else: rally = Rally(server, user=username, password=password, workspace=workspace, project=project) rally.enableLogging('rally.hist.getattachs') # name of file you want logging to go to if len(args) != 2: errout(USAGE) sys.exit(2) entity_name, ident = args if entity_name in STORY_ALIASES: entity_name = 'HierarchicalRequirement' mo = OID_PATT.match(ident) if mo: ident_query = 'ObjectID = %s' % ident else: mo = FORMATTED_ID_PATT.match(ident) if mo: ident_query = 'FormattedID = "%s"' % ident else: errout('ERROR: Unable to determine ident scheme for %s\n' % ident) sys.exit(3) response = rally.get(entity_name, fetch=True, query=ident_query, workspace=workspace, project=project) if response.errors: errout("Request could not be successfully serviced, error code: %d\n" % response.status_code) errout("\n".join(response.errors)) sys.exit(1) if response.resultCount == 0: errout('No item found for %s %s\n' % (entity_name, ident)) sys.exit(4) elif response.resultCount > 1: errout('WARNING: more than 1 item returned matching your criteria\n') artifact = response.next() attachments = rally.getAttachments(artifact) for attachment in attachments: print "-" * 32 print attachment.Name print "~" * len(attachment.Name) print attachment.Content print "" print "=" * 64
def main(args): options = [opt for opt in args if opt.startswith('--')] args = [arg for arg in args if arg not in options] server, username, password, apikey, workspace, project = rallyWorkset(options) print(f'server: {server}') print(f'apikey: {apikey}') print(f'workspace: {workspace}') print(f'project : {project}') if apikey: #rally = Rally(server, apikey=apikey, workspace=workspace, project=project) rally = Rally(server, apikey=apikey, workspace=workspace) else: #rally = Rally(server, user=username, password=password, workspace=workspace, project=project) rally = Rally(server, user=username, password=password, workspace=workspace) rally.enableLogging('rally.hist.artifact') # name of file you want logging to go to if len(args) != 1: errout(USAGE) sys.exit(2) ident = args.pop(0) mo = FORMATTED_ID_PATT.match(ident) if mo: ident_query = 'FormattedID = "%s"' % ident else: errout('ERROR: Unable to detect a valid Rally FormattedID in your arg: %s\n' % ident) sys.exit(3) mo = re.match(r'^(?P<art_abbrev>DE|S|US|TA|TC|F|I|T)\d+$', ident) if not mo: errout('ERROR: Unable to extract a valid Rally artifact type abbrev in %s' % ident) sys.exit(4) art_abbrev = mo.group('art_abbrev') entity_name = ARTIFACT_TYPE[art_abbrev] response = rally.get(entity_name, fetch=True, query=ident_query, workspace=workspace) if response.errors: errout("Request could not be successfully serviced, error code: %d\n" % response.status_code) errout("\n".join(response.errors)) sys.exit(1) if response.resultCount == 0: errout('No item found for %s %s\n' % (entity_name, ident)) sys.exit(4) elif response.resultCount > 1: errout('WARNING: more than 1 item returned matching your criteria\n') sys.exit(5) for item in response: print(item.details())
def test_epic_query_by_formatted_id(): """ Using a known valid Rally server and known valid access credentials, exercise the Rally.get method to retrieve and Epic instance that has been created offline and be handed back a usable pyral.entity representing the PortfoloItem/Epic instance. """ rally = Rally(server=RALLY, apikey=APIKEY) rally.setWorkspace('NMTest') target_workspace = rally.getWorkspace() rally.setProject('*MFA Benefit Durt') target_project = rally.getProject() epic = rally.get('PortfolioItem/Epic', fetch=True, query='FormattedID = E876', workspace=target_workspace.Name, project=None, instance=True) assert epic.FormattedID == 'E876' print("{0} {1}".format(epic.FormattedID, epic.Name)) epic = rally.get('PortfolioItem/Epic', fetch=True, query='FormattedID = E876', instance=True) assert epic.FormattedID == 'E876' epic = rally.get('PortfolioItem/Epic', fetch=True, query="FormattedID = \"E876\"", instance=True) assert epic.FormattedID == 'E876' epic = rally.get('Epic', fetch=True, query='FormattedID = "E876"', instance=True) assert epic.FormattedID == 'E876'
def validRallyIdent(api_key, sub_id): try: rally = Rally("rally1.rallydev.com", apikey=api_key) fields = "SubscriptionID" user = rally.get('User', fetch=fields, instance=True) if not user: return False, "The Api Key provided is not valid" if user.SubscriptionID != int(sub_id): return False, "The Api Key provided does not match " except Exception as ex: #return False, "Unable to reach Rally to verify your Api Key and Subscription ID" return False, str(ex) return True, "Everything is copacetic!"
def test_start_value_query(): """ Use a pagesize of 200 and a start index value of 10 in the params in the URL """ rally = Rally(server=TRIAL, user=TRIAL_USER, password=TRIAL_PSWD) qualifier = "State = Submitted" response = rally.get('Defect', fetch=True, query=qualifier, pagesize=200, start=10) items = [item for item in response] assert len(items) > 20 assert len(items) < 1000
def test_get_project(): """ Using a known valid Rally server and known valid access credentials, issue a simple query (no qualifying criteria) for a known valid Rally entity. """ rally = Rally(server=TRIAL, user=TRIAL_USER, password=TRIAL_PSWD, workspace=DEFAULT_WORKSPACE, project='Sample Project') response = rally.get('Project', fetch=False, limit=10) assert response.status_code == 200 assert response.errors == [] #assert response.warnings == [] assert response.resultCount > 0 proj = rally.getProject() assert str(proj.Name) == 'Sample Project'
def test_get_named_project(): """ Using a known valid Rally server and known valid access credentials, call the Rally.getProject using a valid (but non-default and non-current) project name as a parameter to the call. """ rally = Rally(server=TRIAL, user=TRIAL_USER, password=TRIAL_PSWD, workspace=DEFAULT_WORKSPACE, project='Sample Project') response = rally.get('Project', fetch=False, limit=10) assert response.status_code == 200 assert response.errors == [] #assert response.warnings == [] assert response.resultCount > 0 proj = rally.getProject('My Project') assert str(proj.Name) == 'My Project'
def main(args): options = [opt for opt in args if opt.startswith('--')] args = [arg for arg in args if arg not in options] if len(args) != 1: errout(USAGE) sys.exit(1) storyID = args[0] server, user, password, workspace, project = rallySettings(options) rally = Rally(server, user, password, workspace=workspace, project=project) rally.enableLogging("rally.history.crtask") # For a task: Workspace, Project, WorkProduct, Name, State, TaskIndex are required; # Workspace cannot be specified in the JSON, it defaults to # the logged in account's Workspace setting # Project and WorkProduct must be object refs to relevant Rally Entity instances. # In this example the WorkProduct is a UserStory (HierarchicalRequirement). target_project = rally.getProject() target_story = rally.get('UserStory', query='FormattedID = %s' % storyID, instance=True) info = { "Project": target_project.ref, "WorkProduct": target_story.ref, "Name": "BigTaters", "State": "Defined", "TaskIndex": 1, "Description": "Fly to Chile next week to investigate the home of potatoes. Find the absolute gigantoidist spuds and bring home the eyes to Idaho. Plant, water, wonder, harvest, wash, slice, plunge in and out of hot oil, drain and enjoy! Repeat as needed.", "Estimate": 62.0, "Actuals": 1.0, "ToDo": 61.0, "Notes": "I have really only done some daydreaming wrt this task. Sorry Jane, I knew you had big plans for Frankie's blowout BBQ next month, but the honeycomb harvest project is taking all my time." } print "Creating Task ..." task = rally.put('Task', info) print "Created Task: %s OID: %s" % (task.FormattedID, task.oid)
def test_multiple_entities_query(): """ Using a known valid Rally server and known valid access credentials, issue a simple query (no qualifying criteria) for a comma separated list of known valid Rally entity names. As of the initial swag at the Python toolkit for Rally REST API, this is an invalid request; only a single Rally entity can be specified. """ rally = Rally(server=PREVIEW, user=PREVIEW_USER, password=PREVIEW_PSWD) response = rally.get('Project,Workspace', fetch=False, limit=10) assert len(response.errors) > 0 # note how 'Project,Workspace' has been lower-cased to 'project,workspace' expectedErrMsg = u"Not able to parse artifact type: project,workspace" actualErrMsg = response.errors[0] assert actualErrMsg == expectedErrMsg
def test_multiple_page_response_query(): """ Using a known valid Rally server and known valid access credentials, issue a simple query (no qualifying criteria) against a Rally entity (Defect) known to have more than 5 items. Set the pagesize to 5 to force pyral to retrieve multiple pages to satisfy the query. """ rally = Rally(server=PREVIEW, user=PREVIEW_USER, password=PREVIEW_PSWD) response = rally.get('Defect', fetch=False, pagesize=5, limit=15) count = 0 for ix, bugger in enumerate(response): count += 1 assert response.resultCount > 5 assert count <= response.resultCount assert count == 15
def test_single_condition_query_plain_expression(): """ Using a known valid Rally server and known valid access credentials, issue a query with a single qualifying criterion against a Rally entity (Defect) known to exist for which the qualifying criterion should return one or more Defects. The qualifying criterion is a string that is _not_ surrounded with paren chars. """ rally = Rally(server=TRIAL, user=TRIAL_USER, password=TRIAL_PSWD) workspace = rally.getWorkspace() project = rally.getProject() qualifier = 'State = "Submitted"' response = rally.get('Defect', fetch=True, query=qualifier, limit=10) assert response.resultCount > 0
def test_multiple_entities_query(): """ Using a known valid Rally server and known valid access credentials, issue a simple query (no qualifying criteria) for a comma separated list of known valid Rally entity names. As of Rally WSAPI 1.x, this is an invalid request; only a single Rally entity can be specified. """ rally = Rally(server=TRIAL, user=TRIAL_USER, password=TRIAL_PSWD) multiple_entities = "Project,Workspace" with py.test.raises(InvalidRallyTypeNameError) as excinfo: response = rally.get(multiple_entities, fetch=False, limit=10) actualErrVerbiage = excinfo.value.args[0] assert excinfo.value.__class__.__name__ == 'InvalidRallyTypeNameError' assert actualErrVerbiage == multiple_entities
def test_basic_query(): """ Using a known valid Rally server and known valid access credentials, issue a simple filtering query targeting RecycleBinEntry items whose Name value does not contain a specific value. """ rally = Rally(server=RALLY, user=RALLY_USER, password=RALLY_PSWD) response = rally.get('RecycleBinEntry', fetch="ObjectID,ID,Name", query='Name = "Gone but not forgotten with the wind"', limit=100) assert response.status_code == 200 assert response.errors == [] assert response.warnings == [] assert response.resultCount > 0
def test_query_pull_requests(): #rally = Rally(server=AGICEN, user=AGICEN_USER, password=AGICEN_PSWD) #rally = Rally(server=TESTN, user=TESTN_USER, password=TESTN_PSWD) rally = Rally(server=AGICEN, apikey=AGICEN_SUB_100_API_KEY) attrs = "ExternalId,ExternalFormattedId,Artifact,Name,Url,Description" response = rally.get('PullRequest', fetch=attrs, project=None) assert response.status_code == 200 assert len(response.errors) == 0 assert len(response.warnings) == 0 prs = [pr for pr in response] assert len(prs) > 0 assert prs[0].Artifact assert prs[0].Artifact.__class__.__name__ == 'HierarchicalRequirement' print (prs[0].Artifact.oid) print(prs[0].details())
def test_basic_connection_with_a_header(): """ Using a known valid Rally server and access credentials, issue a simple query request against a known valid Rally entity. """ headers = { 'name': 'Fungibles Goods Burn Up/Down', 'vendor': 'Archimedes', 'version': '1.2.3' } rally = Rally(RALLY, apikey=APIKEY, headers=headers) response = rally.get('Project', fetch=False, limit=10) assert response != None assert response.status_code == 200 time.sleep(1)
def test_start_and_limit_query(): """ Use a pagesize of 50 and a start index value of 10 and a limit of 40 in the params in the URL """ rally = Rally(server=RALLY, user=RALLY_USER, password=RALLY_PSWD) qualifier = "State = Submitted" response = rally.get('Defect', fetch=True, query=qualifier, pagesize=50, start=10, limit=40) items = [item for item in response] assert len(items) > 10 assert len(items) <= 40
def main(args): options = [opt for opt in args if opt.startswith('--')] args = [arg for arg in args if arg not in options] #server, user, password, apikey, workspace, project = rallyWorkset(options) #if apikey: rally = Rally(server, user, password, apikey=apikey, workspace=workspace, project=project) #else: # rally = Rally(server, user, password, workspace=workspace, project=project) rally.enableLogging("rally.history.showstories") Hierarchfields = "FormattedID,Name,Iteration,TaskRemainingTotal,TaskStatus" #,Feature" Artifactfields = "owner,tags" #criterion = '((Iteration.Name contains "Iteration 3")OR(Iteration.Name contains "Iteration 7")) AND (Feature != null)' #query = "%s " criterion = '(Iteration.Name contains "PI%s - Iteration %s")' % ( pivalue, iterationvalue) response = rally.get('HierarchicalRequirement', fetch=Hierarchfields, query=criterion, order="FormattedID", pagesize=200, limit=400) # artifactresponse = rally.get('Artifacts', fetch=True, query=criterion, order="owner", limit=400) print criterion postmessage = "*Current Stories Iteration Stories*" + "\n" + "```" for story in response: #print (story.FormattedID,story.Iteration) postmessage = postmessage + "%-8s %-70s %-4.1f %-25s" % ( story.FormattedID, story.Name, story.TaskRemainingTotal, story.TaskStatus) + "\n" postmessage = postmessage + "```" + "\n" print response.resultCount, "qualifying stories" slack.chat.post_message(channel=channel, text=postmessage, username="******", as_user=False)