1414from pprint import pprint
1515import array as arr
1616
17+ from urllib3 .exceptions import ReadTimeoutError
18+
1719http .client ._MAXHEADERS = 1000
1820
1921logging .basicConfig (
@@ -44,15 +46,18 @@ def RepWarning(msg):
4446parser .add_argument ("--project" , dest = 'project_name' , help = "Project name" )
4547parser .add_argument ("--version" , dest = 'version_name' , help = "Version name" )
4648
47- parser .add_argument ("--max-projects" , dest = 'max_projects' , type = int , help = "Maximum projects to inspect else all" )
49+ parser .add_argument ("--max-projects" , dest = 'max_projects' , type = int , help = "Maximum number of projects to inspect else all" )
4850parser .add_argument ("--max-versions-per-project" , dest = 'max_versions_per_project' , type = int , help = "Maximum versions per project to inspect else all" )
4951parser .add_argument ("--max-components" , dest = 'max_components' , type = int , help = "Maximum components to inspect in total else all" )
5052
51- parser .add_argument ("--debug" , dest = 'debug' , type = int , default = 0 , help = "Debug verbosity (0=none)" )
53+ parser .add_argument ("--skip-projects" , dest = 'skip_projects' , type = int , help = "Skip first 'n' projects to inspect" )
54+
55+ parser .add_argument ("--debug" , dest = 'debug' , type = int , default = 0 , help = "Debug verbosity (0=none 'n'=level)" )
56+ parser .add_argument ("--dryrun" , dest = 'dry_run' , type = int , default = 0 , help = "Dry run test (0=no 1=yes)" )
5257
5358parser .add_argument ("--no-verify" , dest = 'verify' , action = 'store_false' , help = "Disable TLS certificate verification" )
54- parser .add_argument ("-t" , "-- timeout" , default = 15 , type = int , help = "Adjust the (HTTP) session timeout value (default: 15s )" )
55- parser .add_argument ("-r" , "- -retries" , default = 3 , type = int , help = "Adjust the number of retries on failure (default: 3)" )
59+ parser .add_argument ("-- timeout" , default = 60 , type = int , help = "Adjust the (HTTP) session timeout value (default: 60s )" )
60+ parser .add_argument ("--retries" , default = 3 , type = int , help = "Adjust the number of retries on failure (default: 3)" )
5661
5762args = parser .parse_args ()
5863
@@ -63,8 +68,8 @@ def RepWarning(msg):
6368# access the Black Duck platform
6469bd = Client (
6570 base_url = args .base_url ,
66- token = access_token ,
6771 verify = args .verify ,
72+ token = access_token ,
6873 timeout = args .timeout ,
6974 retries = args .retries ,
7075)
@@ -73,6 +78,7 @@ def RepWarning(msg):
7378all_my_comp_data = []
7479my_statistics = {}
7580
81+ str_unknown = "n/a"
7682
7783# version of components API to call
7884comp_api_version = 6
@@ -118,7 +124,7 @@ def RepWarning(msg):
118124my_statistics ['_cntRefresh' ] = 0
119125my_statistics ['_cntNoOrigins' ] = 0
120126my_statistics ['_cntNoIDs' ] = 0
121-
127+ my_statistics [ '_cntSkippedProjects' ] = 0
122128
123129# record any control values
124130if args .project_name :
@@ -149,18 +155,32 @@ def RepWarning(msg):
149155 # all projects are in scope
150156 projects = bd .get_resource ('projects' )
151157
158+
159+ cnt_projects = 0
160+
152161# loop through projects list
153162for this_project in projects :
154163
164+ cnt_projects += 1
165+
166+ # check if we are skipping over this project
167+ if args .skip_projects and cnt_projects <= args .skip_projects :
168+ my_statistics ['_cntSkippedProjects' ] += 1
169+ RepDebug (1 , 'Skipping project [%d] [%s]' % (cnt_projects , this_project ['name' ]))
170+ continue
171+
155172 # check if we have hit any limit
156173 if args .max_components and my_statistics ['_cntComponents' ] >= args .max_components :
174+ RepDebug (1 , 'Reached component limit [%d]' % args .max_components )
157175 break
158176
159177 if args .max_projects and my_statistics ['_cntProjects' ] >= args .max_projects :
178+ RepDebug (1 , 'Reached project limit [%d]' % args .max_projects )
160179 break
161180
181+ # process this project
162182 my_statistics ['_cntProjects' ] += 1
163- RepDebug (1 , '## Project %d: %s ' % (my_statistics [ '_cntProjects' ] , this_project ['name' ]))
183+ RepDebug (1 , '## Project: [%d] [%s] ' % (cnt_projects , this_project ['name' ]))
164184
165185 if args .version_name :
166186 # note the specific project version of interest
@@ -181,78 +201,121 @@ def RepWarning(msg):
181201
182202 # check if we have hit any limit
183203 if args .max_components and my_statistics ['_cntComponents' ] >= args .max_components :
184- # exit component loop - at the limit
204+ RepDebug ( 1 , 'Reached component limit [%d]' % args . max_components )
185205 break
186206
187207 if args .max_versions_per_project and nVersionsPerProject >= args .max_versions_per_project :
188- # exit loop - at the version per project limit
208+ RepDebug ( 1 , 'Reached versions per project limit [%d]' % args . max_versions_per_project )
189209 break
190210
191211 nVersionsPerProject += 1
192212 my_statistics ['_cntVersions' ] += 1
193213
194214 # Announce
195215# logging.debug(f"Found {this_project['name']}:{this_version['versionName']}")
196- RepDebug (3 , ' Version: %s ' % this_version ['versionName' ])
216+ RepDebug (3 , ' Version: [%s] ' % this_version ['versionName' ])
197217
198218
199219 # iterate through all components for this project version
200220 for this_comp_data in bd .get_resource ('components' , this_version , ** comp_kwargs ):
201221
202222 if args .max_components and my_statistics ['_cntComponents' ] >= args .max_components :
203- # exit component loop - at the limit
223+ RepDebug ( 1 , 'Reached component limit [%d]' % args . max_components )
204224 break
205225
206226 my_statistics ['_cntComponents' ] += 1
207- RepDebug (4 , ' Component: %s (%s)' %
208- (this_comp_data ['componentName' ], this_comp_data ['componentVersionName' ]))
227+
228+ if this_comp_data .get ("componentName" ):
229+ comp_name = this_comp_data ['componentName' ]
230+ else :
231+ comp_name = str_unknown
232+
233+ if this_comp_data .get ("componentVersionName" ):
234+ comp_version_name = this_comp_data ['componentVersionName' ]
235+ else :
236+ comp_version_name = str_unknown
237+
238+ comp_label = "{} ({})" .format (comp_name , comp_version_name )
239+
240+ RepDebug (4 , ' Component: [%s]' % comp_label )
209241
210242 if this_comp_data ['inputExternalIds' ].__len__ () > 0 :
211243 inputExternalIds = this_comp_data ['inputExternalIds' ][0 ]
212244 else :
213245 my_statistics ['_cntNoIDs' ] += 1
214- inputExternalIds = "n/a"
215- RepDebug (2 , ' ID: %s ' % inputExternalIds )
246+ inputExternalIds = str_unknown
247+ RepDebug (2 , ' ID: [%s] ' % inputExternalIds )
216248
217249
218- # refresh the copyrights for this component
250+ # refresh the copyrights for this component-origin
219251 if this_comp_data ['origins' ].__len__ () > 0 :
220- url = this_comp_data ['origins' ][0 ]['origin' ]
221- else :
222- # no origins
223- RepWarning ('No origin defined for [%s]' % this_comp_data ['componentVersion' ])
224- # url = this_comp_data['componentVersion']
225- url = ''
226-
227- if len (url ) > 0 :
228- # refresh end point
229- url += "/copyrights-refresh"
230-
231- try :
232- response = bd .session .put (url , data = None , ** refresh_kwargs )
233- RepDebug (5 ,'Refresh response %s' % response )
234- except urllib3 .exceptions .ReadTimeoutError :
235- print ('Failed to confirm copyrights refresh' )
236-
237- my_statistics ['_cntRefresh' ] += 1
252+
253+ n_origin = 0
254+
255+ for this_origin in this_comp_data ['origins' ]:
256+
257+ n_origin += 1
258+ if this_origin .get ('externalId' ):
259+ origin_id = this_origin ['externalId' ]
260+ else :
261+ origin_id = str_unknown
262+
263+ url = this_origin ['origin' ]
264+
265+ # refresh with end point
266+ url += "/copyrights-refresh"
267+
268+ status = - 1
269+
270+ if args .dry_run != 0 :
271+ RepDebug (2 , "DryRun: origin - no [%d] id [%s] url [%s]" % (n_origin , origin_id , url ))
272+ else :
273+ try :
274+ response = bd .session .put (url , data = None , ** refresh_kwargs )
275+ RepDebug (5 ,'Refresh response: origin [%s] [%s]' % (this_origin , response ))
276+ my_statistics ['_cntRefresh' ] += 1
277+ status = 0
278+
279+ except Exception :
280+ print ('Failed to confirm copyrights refresh' )
281+ status = 1
282+
283+
284+ # if recording the data - perhaps outputting to a CSV file
285+ if args .dump_data :
286+ my_data = {}
287+ my_data ['componentName' ] = this_comp_data ['componentName' ]
288+ my_data ['componentVersion' ] = this_comp_data ['componentVersionName' ]
289+ my_data ['status' ] = status
290+ my_data ['url' ] = url
291+
292+ if hasattr (args , 'debug' ) and 5 <= args .debug :
293+ pprint (my_data )
294+
295+ # add to our list
296+ all_my_comp_data .append (my_data )
297+
238298 else :
299+ # no origins defined
300+ RepWarning ('No origin(s) defined for [%s]' % comp_label )
239301 my_statistics ['_cntNoOrigins' ] += 1
302+ origin_id = ''
303+ status = 3
240304 url = 'n/a'
241305
306+ # if recording the data
307+ if args .dump_data :
308+ my_data = {}
309+ my_data ['componentName' ] = comp_name
310+ my_data ['componentVersion' ] = comp_version_name
311+ my_data ['status' ] = status
312+ my_data ['url' ] = url
242313
243- # if recording the data - perhaps outputting to a CSV file
244- if args .dump_data :
245- my_data = {}
246- my_data ['componentName' ] = this_comp_data ['componentName' ]
247- my_data ['componentVersion' ] = this_comp_data ['componentVersionName' ]
248- my_data ['url' ] = url
249-
250- if hasattr (args , 'debug' ) and 5 <= args .debug :
251- pprint (my_data )
252-
253- # add to our list
254- all_my_comp_data .append (my_data )
314+ if hasattr (args , 'debug' ) and 5 <= args .debug :
315+ pprint (my_data )
255316
317+ # add to our list
318+ all_my_comp_data .append (my_data )
256319
257320# end of processing loop
258321
@@ -275,6 +338,7 @@ def RepWarning(msg):
275338 field_names = [
276339 'Component' ,
277340 'Component Version' ,
341+ 'Status' ,
278342 'Url'
279343 ]
280344
@@ -285,6 +349,7 @@ def RepWarning(msg):
285349 row_data = {
286350 'Component' : my_comp_data ['componentName' ],
287351 'Component Version' : my_comp_data ['componentVersion' ],
352+ 'Status' : my_comp_data ['status' ],
288353 'Url' : my_comp_data ['url' ]
289354 }
290355 writer .writerow (row_data )
0 commit comments