Skip to content

Commit b52ccaa

Browse files
committed
option --percontribution now avoids contributions not in the specified project
1 parent 18ef8aa commit b52ccaa

30 files changed

+1872
-1760
lines changed

.bumpversion.cfg

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
[bumpversion]
2-
current_version = 0.10.0
2+
current_version = 0.11.1
33
commit = True
44
tag = True
55

README.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88

99
SPDX-License-Identifier: MIT
1010

11-
version="0.10.0"
11+
version="0.11.1"
1212

1313

1414
Introduction

elmclient/__meta__.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@
99

1010
app = 'elmoslcquery'
1111
description = 'Commandline OSLC query for ELM'
12-
version = '0.10.0'
12+
version = '0.11.1'
1313
license = 'MIT'
1414
author_name = 'Ian Barnard'
1515
author_mail = '[email protected]'

elmclient/_project.py

Lines changed: 16 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -200,6 +200,20 @@ def get_gc_contributions(self,gcuri):
200200
result = self.execute_get_json(self.reluri("gcsdk-api/flatListOfContributionsForGcHierarchy"), params={'configurationUri':gcuri,'include':'*'} )
201201
# print( f"{result=}" )
202202
return result
203+
204+
# get contributions and component details for just this app
205+
def get_our_contributions(self, gcuri):
206+
gc_contribs = self.get_gc_contributions(gcuri)
207+
results = []
208+
for contrib in gc_contribs['configurations']:
209+
if contrib['configurationUri'].startswith(self.reluri()):
210+
results.append( [contrib['configurationUri'],contrib['componentUri'] ] )
211+
# print( f"Included {contrib['configurationUri']}" )
212+
else:
213+
# print( f"Skipped {contrib['configurationUri']}" )
214+
pass
215+
# print( f"{results=}" )
216+
return results
203217

204218
def set_local_config(self, name_or_uri, global_config_uri=None):
205219
if name_or_uri:
@@ -211,13 +225,11 @@ def set_local_config(self, name_or_uri, global_config_uri=None):
211225
# find the contribution for this component
212226
config_uri = None
213227
for config in gc_contribs['configurations']:
214-
print( f"Checking {config=} for {self.project_uri=}" )
228+
# print( f"Checking {config=} for {self.project_uri=}" )
215229
if config['componentUri'] == self.project_uri:
216230
config_uri = config['configurationUri']
217-
if config_uri is None:
218-
burp
219231
if not config_uri:
220-
raise Exception('Cannot find configuration [%s] in project [%s]' % (name_or_uri, self.uri))
232+
raise Exception( 'Cannot find configuration [%s] in project [%s]' % (name_or_uri, self.uri))
221233
else:
222234
config_uri = None
223235

elmclient/_qm.py

Lines changed: 20 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -153,11 +153,26 @@ def load_components_and_configurations(self,force=False):
153153
self._components[cu]['component'] = c
154154
return (ncomps, nconfs)
155155

156-
def get_local_config(self, name_or_uri):
157-
for cu, cd in self._configurations.items():
158-
logger.debug( f"{cu=} {cd=} {name_or_uri=}" )
159-
if cu == name_or_uri or cd['name'] == name_or_uri:
160-
return cu
156+
def get_local_config(self, name_or_uri, global_config_uri=None):
157+
if global_config_uri:
158+
if not name_or_uri:
159+
raise Exception( "can't find a local config in a GC if config name not provided" )
160+
# gc and local config both specified - try to avoid loading all the local configs by using the gc tree to locate the local config
161+
gc_contribs = self.get_gc_contributions(global_config_uri)
162+
# find the contribution for this component
163+
config_uri = None
164+
for config in gc_contribs['configurations']:
165+
# print( f"Checking {config=} for {self.project_uri=}" )
166+
if config['componentUri'] == self.project_uri:
167+
config_uri = config['configurationUri']
168+
if not config_uri:
169+
raise Exception( 'Cannot find configuration [%s] in project [%s]' % (name_or_uri, self.uri))
170+
return config_uri
171+
else:
172+
for cu, cd in self._configurations.items():
173+
logger.debug( f"{cu=} {cd=} {name_or_uri=}" )
174+
if cu == name_or_uri or cd['name'] == name_or_uri:
175+
return cu
161176
return None
162177

163178
# load the typesystem using the OSLC shape resources

elmclient/_rm.py

Lines changed: 35 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -188,7 +188,7 @@ def load_folders(self,name_or_uri=None,force=False):
188188
return None
189189

190190
def load_components_and_configurations(self,force=False):
191-
if self._components and self._configurations and not force:
191+
if self._components and not force:
192192
return
193193
logger.info( f"load_components_and_configurations {self=} {self.is_optin=}" )
194194
self._components = {}
@@ -307,7 +307,6 @@ def load_components_and_configurations(self,force=False):
307307
compu = component_el.get("{%s}resource" % rdfxml.RDF_DEFAULT_PREFIX["rdf"])
308308
compx = self.execute_get_rdf_xml(compu, intent="Retrieve component definition to find all configurations", action="Retrieve each configuration")
309309
comptitle = rdfxml.xmlrdf_get_resource_text(compx, './/dcterms:title')
310-
311310
confu = rdfxml.xmlrdf_get_resource_uri(compx, './/oslc_config:configurations')
312311
self._components[compu] = {'name': comptitle, 'configurations': {}, 'confs_to_load': [confu]}
313312
ncomps += 1
@@ -383,6 +382,7 @@ def load_components_and_configurations(self,force=False):
383382
return (ncomps, nconfs)
384383

385384
def load_configs(self):
385+
# load configurations
386386
while self._confs_to_load:
387387
confu = self._confs_to_load.pop()
388388
if not confu:
@@ -435,27 +435,40 @@ def load_configs(self):
435435
self._confs_to_load.append( rdfxml.xmlrdf_get_resource_uri(confmember, './oslc_config:baselines') )
436436
self._confs_to_load.append( rdfxml.xmlrdf_get_resource_uri(confmember, './rm_config:changesets') )
437437

438-
def get_local_config(self, name_or_uri):
438+
def get_local_config(self, name_or_uri, global_config_uri=None):
439439
logger.info( f"GLC {self=} {name_or_uri=}" )
440-
self.load_configs()
441-
result = None
442-
filter = None
443-
if name_or_uri.startswith("S:"):
444-
filter="Stream"
445-
name_or_uri = name_or_uri[2:]
446-
elif name_or_uri.startswith("B:"):
447-
filter="Baseline"
448-
name_or_uri = name_or_uri[2:]
449-
elif name_or_uri.startswith("C:"):
450-
filter="ChangeSet"
451-
name_or_uri = name_or_uri[2:]
452-
for cu, cd in self._configurations.items():
453-
if filter and cd['conftype'] != filter:
454-
continue
455-
if cu == name_or_uri or cd['name'] == name_or_uri:
456-
if result:
457-
raise Exception( f"Config {name_or_uri} isn't unique - you could try prefixing it with S: for stream, B: for baseline, or C: for changeset")
458-
result = cu
440+
if global_config_uri:
441+
# gc and local config both specified - try to avoid loading all the local configs by using the gc tree to locate the local config
442+
gc_contribs = self.get_gc_contributions(global_config_uri)
443+
# find the contribution for this component
444+
config_uri = None
445+
for config in gc_contribs['configurations']:
446+
# print( f"Checking {config=} for {self.project_uri=}" )
447+
if config['componentUri'] == self.project_uri:
448+
config_uri = config['configurationUri']
449+
if not config_uri:
450+
raise Exception( 'Cannot find configuration [%s] in project [%s]' % (name_or_uri, self.uri))
451+
result = config_uri
452+
else:
453+
self.load_configs()
454+
result = None
455+
filter = None
456+
if name_or_uri.startswith("S:"):
457+
filter="Stream"
458+
name_or_uri = name_or_uri[2:]
459+
elif name_or_uri.startswith("B:"):
460+
filter="Baseline"
461+
name_or_uri = name_or_uri[2:]
462+
elif name_or_uri.startswith("C:"):
463+
filter="ChangeSet"
464+
name_or_uri = name_or_uri[2:]
465+
for cu, cd in self._configurations.items():
466+
if filter and cd['conftype'] != filter:
467+
continue
468+
if cu == name_or_uri or cd['name'] == name_or_uri:
469+
if result:
470+
raise Exception( f"Config {name_or_uri} isn't unique - you could try prefixing it with S: for stream, B: for baseline, or C: for changeset")
471+
result = cu
459472
return result
460473

461474
# for RM, load the typesystem using the OSLC shape resources listed for the Requirements and Requirements Collection creation factories

elmclient/examples/OSLCQUERY.md

Lines changed: 17 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -75,7 +75,8 @@ usage: oslcquery [-h] [-f SEARCHTERMS] [-n NULL] [-o ORDERBY] [-p PROJECTNAME] [
7575
[-F CONFIGURATION] [-G GLOBALCONFIGURATION] [-H SAVECONFIGS] [-I] [-J JAZZURL] [-L LOGLEVEL]
7676
[-M MAXRESULTS] [-N] [-O OUTPUTFILE] [-P PASSWORD] [-Q] [-R] [-S] [-T] [-U USERNAME] [-V] [-W]
7777
[-X XMLOUTPUTFILE] [-Y] [-Z PROXYPORT] [--nresults NRESULTS] [--compareresults COMPARERESULTS]
78-
[--pagesize PAGESIZE] [--typesystemreport TYPESYSTEMREPORT] [--cachedays CACHEDAYS] [-0 SAVECREDS]
78+
[--pagesize PAGESIZE] [--typesystemreport TYPESYSTEMREPORT] [--cachedays CACHEDAYS]
79+
[--saverawresults SAVERAWRESULTS] [--saveprocessedresults SAVEPROCESSEDRESULTS] [-0 SAVECREDS]
7980
[-1 READCREDS] [-2 ERASECREDS] [-3 SECRET] [-4]
8081
8182
Perform OSLC query on a Jazz application, with results output to CSV (and other) formats - use -h to get some basic
@@ -109,8 +110,8 @@ options:
109110
Post-filter: A property name that must have a value for the resource to be included in the
110111
results - you can specify this option more than once
111112
-A APPSTRINGS, --appstrings APPSTRINGS
112-
A comma-seperated list of apps, the query goes to the first entry, default "rm,gc,ccm". Each
113-
entry must be a domain or domain:contextroot e.g. rm or rm:rm1 - Default can be set using
113+
A comma-seperated list of apps, the query goes to the first entry, default "rm". Each entry
114+
must be a domain or domain:contextroot e.g. rm or rm:rm1 - Default can be set using
114115
environemnt variable QUERY_APPSTRINGS
115116
-C COMPONENT, --component COMPONENT
116117
The local component (optional, you *have* to specify the local configuration using -F)
@@ -126,7 +127,7 @@ options:
126127
id, the full URI, or the config name (not implemented yet)
127128
-H SAVECONFIGS, --saveconfigs SAVECONFIGS
128129
Name of CSV file to save details of the local project components and configurations
129-
-I, --totalize For all columns with multiple results, put in the total instead of the results
130+
-I, --totalize For any column with multiple results, put in the total instead of the results
130131
-J JAZZURL, --jazzurl JAZZURL
131132
jazz server url (without the /jts!) default https://jazz.ibm.com:9443 - Default can be set
132133
using environemnt variable QUERY_JAZZURL - defaults to https://jazz.ibm.com:9443 which DOESN'T
@@ -172,8 +173,12 @@ options:
172173
Load the specified project/configuration and then produce a simple HTML type system report of
173174
resource shapes/properties/enumerations to this file
174175
--cachedays CACHEDAYS
175-
The number of days for caching received data, default 1. To disable caching use -WW. To keep
176+
The number of days for caching received data, default 7. To disable caching use -WW. To keep
176177
using a non-default cache period you must specify this value every time
178+
--saverawresults SAVERAWRESULTS
179+
Save the raw results as XML to this path/file prefix - pages are numbered starting from 0000
180+
--saveprocessedresults SAVEPROCESSEDRESULTS
181+
Save the processed results as JSON to this path/file
177182
-0 SAVECREDS, --savecreds SAVECREDS
178183
Save obfuscated credentials file for use with readcreds, then exit - this stores jazzurl, jts,
179184
appstring, username and password
@@ -184,10 +189,9 @@ options:
184189
Wipe and delete obfuscated credentials file
185190
-3 SECRET, --secret SECRET
186191
SECRET used to encrypt and decrypt the obfuscated credentials (make this longer for greater
187-
security) - required if using -0 or -1
192+
security) - only affects if using -0 or -1
188193
-4, --credspassword Prompt user for a password to save/read obfuscated credentials (make this longer for greater
189-
security)
190-
```
194+
security)```
191195
192196
193197
BEFORE you start:
@@ -455,7 +459,11 @@ To find all artifacts in project/component in a specific module id 3892 modified
455459
456460
To find all artifacts in project/component in a specific module id 3892 modified before a specific date `-q rm:module=~3892 and dcterms:modified<"2020-08-01T21:51:40.979Z"^^xsd:dateTime` - NOTE this is using the enhanced OSLC Query sytnax for finding an artifact by id using ~
457461
458-
To totalize a column which has multiple results replacing them with a count of the number of results, which might be useful for example to get a count of artifacts in each module, use a query for modules `rdm_types:ArtifactFormat=jazz_rm:Module` and select `oslc_rm:uses` then use the -I option. Because this doesn't need name resolution which can slow the query and post-processing down when processing many modules, also use -R and -Q - for results from components across a GC `/gc/configuration/26` in GCM project `gcproj` the query looks like: `-s oslc_rm:uses,dcterms:title -q rdm_types:ArtifactFormat=jazz_rm:Module -G 26 -E gcproj` - the result is a spreadsheet containing the module URI, the module name and identifier and a column with the count of artifacts in the module.
462+
To totalize a column which has multiple results replacing them with a count of the number of results, which might be useful for example to get a count of artifacts in each module, use a query for modules `rdm_types:ArtifactFormat=jazz_rm:Module` and select `oslc_rm:uses` then use the -I option. Because this doesn't need name resolution which can slow the query and post-processing down when processing many modules, also use -R and -Q - for results from components across a GC `/gc/configuration/26` in GCM project `gcproj` the query looks like: `-s oslc_rm:uses,dcterms:title -q rdm_types:ArtifactFormat=jazz_rm:Module -G 26 -E gcproj` - the result is a spreadsheet containing the module URI, the module name and identifier and a column with the count of artifacts in the module. You can improve performance (assuming you don't need friendly names, and counting artifacts/module doesn't really need friendly names) by suppressing the reading of the type system using `-Q` and `-R`, and because the results will be large you may consider carefully whether to suppress paging by using `--pagesize 0`.
463+
464+
If you have a project with many components and/or configurations, you may observe that startup is slow - this is because by default if you don't specify a component then oslcquery reads all the components in the project and all the configurations in each component so that it can find the configuration which might be in any component. As of version 0.10.0 you can reduce this cost in a few ways: - most basic is to specify a component using -C, when you do this oslcquery only reads the configurations for that component. The next is to specify a component using `-C` and GC as well - using `-E` and `-G` -and also as a local configuration using `-F` - `oslcquery` will find the contribution to the GC for that component. If you only specify a GC configuration (usinging `-E` and `-G`) then oslcquery won't read RM components or configurations and the query will work on the project returning results from all contributing componenets in the project.
465+
466+
If there are very many results then paging can add significant cost - you may want to suppress paging using `--pagesize 0` but BE CAREFUL not to impact on other users!
459467
460468
GCM basic usage
461469
===============

0 commit comments

Comments
 (0)