def DefaultDebuggee(self): """Find the default debuggee. Returns: The Debuggee for the default module and version, if there is exactly one such. Raises: errors.NoDebuggeeError if the default can't be determined. """ debuggees = self.ListDebuggees() if len(debuggees) == 1: # Just one possible target return debuggees[0] if not debuggees: raise errors.NoDebuggeeError() # If they're multiple minor versions of a single version (which we # assume to be the default), return the highest-numbered version. latest = _FindLatestMinorVersion(debuggees) if latest: return latest # Find all versions of the default module by_module = [d for d in debuggees if not d.module] if not by_module: # No default module. Can't determine the default target. raise errors.MultipleDebuggeesError(None, debuggees) if len(by_module) == 1: return by_module[0] # If there are multiple minor versions of a single version of the # default module, return the highest-numbered version. latest = _FindLatestMinorVersion(by_module) if latest: return latest # The default module may have multiple versions. Choose the default, if it # can be determined. by_version = [d for d in by_module if not d.version] if len(by_version) == 1: return by_version[0] if not by_version: # No default version. Can't determine the default target. raise errors.MultipleDebuggeesError(None, debuggees) # If there are multiple minor versions of the default version of the # default module, return the highest-numbered version. latest = _FindLatestMinorVersion(by_version) if latest: return latest # Could not find default version. Note that in the case where the debuggee # is an App Engine module version, it is possible to query the module and # find the name of the default version. That information is not visible in # the corresponding Debuggee object, unfortunately. raise errors.NoDebuggeeError()
def FindDebuggee(self, pattern=None): """Find the unique debuggee matching the given pattern. Args: pattern: A string containing a debuggee ID or a regular expression that matches a single debuggee's name or description. If it matches any debuggee name, the description will not be inspected. Returns: The matching Debuggee. Raises: errors.MultipleDebuggeesError if the pattern matches multiple debuggees. errors.NoDebuggeeError if the pattern matches no debuggees. """ if not pattern: return self.DefaultDebuggee() all_debuggees = self.ListDebuggees() match_re = re.compile(pattern) debuggees = [d for d in all_debuggees if d.target_id == pattern or match_re.search(d.name)] if not debuggees: # Try matching on description. debuggees = [d for d in all_debuggees if match_re.search(d.description)] if len(debuggees) == 1: # Just one possible target return debuggees[0] if not debuggees: raise errors.NoDebuggeeError(pattern) # Multiple possibilities. Find the latest minor version, if they all # point to the same module and version. best = _FindLatestMinorVersion(debuggees) if not best: raise errors.MultipleDebuggeesError(pattern, debuggees) return best
def FindDebuggee(self, pattern=None): """Find the unique debuggee matching the given pattern. Args: pattern: A string containing a debuggee ID or a regular expression that matches a single debuggee's name or description. If it matches any debuggee name, the description will not be inspected. Returns: The matching Debuggee. Raises: errors.MultipleDebuggeesError if the pattern matches multiple debuggees. errors.NoDebuggeeError if the pattern matches no debuggees. """ if not pattern: debuggee = self.DefaultDebuggee() log.status.write( 'Debug target not specified. Using default target: {0}\n'. format(debuggee.name)) return debuggee all_debuggees = self.ListDebuggees(include_inactive=True, include_stale=True) if not all_debuggees: raise errors.NoDebuggeeError() latest_debuggees = _FilterStaleMinorVersions(all_debuggees) # Find all debuggees specified by ID, plus all debuggees which are the # latest minor version when specified by name. The sets should be # disjoint, but ensure that there are no duplicates, since the list will # tend to be very small and it is cheap to handle that case. debuggees = set([d for d in all_debuggees if d.target_id == pattern] + [d for d in latest_debuggees if pattern == d.name]) if not debuggees: # Try matching as an RE on name or description. Name and description # share common substrings, so filter out duplicates. match_re = re.compile(pattern) debuggees = set( [d for d in latest_debuggees if match_re.search(d.name)] + [ d for d in latest_debuggees if d.description and match_re.search(d.description) ]) if not debuggees: raise errors.NoDebuggeeError(pattern, debuggees=all_debuggees) if len(debuggees) > 1: raise errors.MultipleDebuggeesError(pattern, debuggees) # Just one possible target return list(debuggees)[0]
def _FilterDebuggeeList(self, all_debuggees, pattern): """Finds the debuggee which matches the given pattern. Args: all_debuggees: A list of debuggees to search. pattern: A string containing a debuggee ID or a regular expression that matches a single debuggee's name or description. If it matches any debuggee name, the description will not be inspected. Returns: The matching Debuggee. Raises: errors.MultipleDebuggeesError if the pattern matches multiple debuggees. errors.NoDebuggeeError if the pattern matches no debuggees. """ if not all_debuggees: raise errors.NoDebuggeeError() latest_debuggees = _FilterStaleMinorVersions(all_debuggees) # Find all debuggees specified by ID, plus all debuggees which are the # latest minor version when specified by name. The sets should be # disjoint, but ensure that there are no duplicates, since the list will # tend to be very small and it is cheap to handle that case. debuggees = set([d for d in all_debuggees if d.target_id == pattern] + [d for d in latest_debuggees if pattern == d.name]) if not debuggees: # Try matching as an RE on name or description. Name and description # share common substrings, so filter out duplicates. match_re = re.compile(pattern) debuggees = set( [d for d in latest_debuggees if match_re.search(d.name)] + [ d for d in latest_debuggees if d.description and match_re.search(d.description) ]) if not debuggees: raise errors.NoDebuggeeError(pattern, debuggees=all_debuggees) if len(debuggees) > 1: raise errors.MultipleDebuggeesError(pattern, debuggees) # Just one possible target return list(debuggees)[0]
def DefaultDebuggee(self): """Find the default debuggee. Returns: The default debug target, which is either the only target available or the latest minor version of the application, if all targets have the same module and version. Raises: errors.NoDebuggeeError if no debuggee was found. errors.MultipleDebuggeesError if there is not a unique default. """ debuggees = self.ListDebuggees() if len(debuggees) == 1: # Just one possible target return debuggees[0] if not debuggees: raise errors.NoDebuggeeError() # More than one module or version. Can't determine the default target. raise errors.MultipleDebuggeesError(None, debuggees)