Increase method visibility
Introduction
Increase method visibility refactoring
Increase the visibility of a method from private to package, package to protected or protected to public.
Pre and post-conditions
Pre-conditions:
User must enter the method's name, and the source class's name for the refactoring in order to increase the target method's visibility.
Post-conditions:
No specific post-condition
IncreaseMethodVisibilityListener (JavaParserLabeledListener)
To implement ِIncrease Method Visibility refactoring based on its actors.
Detects the required method and increases/changes its visibility status.
Source code in codart\refactorings\increase_method_visibility.py
class IncreaseMethodVisibilityListener(JavaParserLabeledListener):
"""
To implement ِIncrease Method Visibility refactoring based on its actors.
Detects the required method and increases/changes its visibility status.
"""
def __init__(self, source_class, source_method, rewriter: TokenStreamRewriter):
"""
Args:
source_class (str): Name of the class in which the refactoring has to be done
source_method (str): Name of the field whose visibility status has to be changed
rewriter (CommonTokenStream): An instance of TokenStreamRewriter
Returns:
object (IncreaseMethodVisibilityListener): An instance of IncreaseMethodVisibilityListener
"""
self.source_class = source_class
self.source_method = source_method
self.in_class = False
self.detected_method = False
self.rewriter = rewriter
def enterClassDeclaration(self, ctx: JavaParserLabeled.ClassDeclarationContext):
if ctx.IDENTIFIER().getText() == self.source_class:
self.in_class = True
def exitClassDeclaration(self, ctx: JavaParserLabeled.ClassDeclarationContext):
if ctx.IDENTIFIER().getText() == self.source_class:
self.in_class = False
def enterMethodDeclaration(self, ctx: JavaParserLabeled.MethodDeclarationContext):
if ctx.IDENTIFIER().getText() == self.source_method:
self.detected_method = True
def exitClassBodyDeclaration2(self, ctx: JavaParserLabeled.ClassBodyDeclaration2Context):
if self.detected_method:
if ctx.modifier(0) is not None:
if "@" in ctx.modifier(0).getText():
if ctx.modifier(1) is not None:
self.rewriter.replaceSingleToken(
token=ctx.modifier(1).start,
text="public "
)
else:
self.rewriter.replaceSingleToken(
ctx.memberDeclaration().getChild(0).getChild(0).start,
text="public " + ctx.memberDeclaration().getChild(0).getChild(0).getText()
)
else:
if ctx.modifier(0).getText() == 'private' or ctx.modifier(0).getText() == 'protected':
self.rewriter.replaceSingleToken(
token=ctx.modifier(0).start,
text="public "
)
else:
self.rewriter.insertBeforeToken(
token=ctx.modifier(0).start,
text="public "
)
else:
if ctx.memberDeclaration().getChild(0).getChild(0) is not None:
self.rewriter.insertBeforeToken(
ctx.memberDeclaration().getChild(0).getChild(0).start,
text="public "
)
self.detected_method = False
__init__(self, source_class, source_method, rewriter)
special
Parameters:
Name | Type | Description | Default |
---|---|---|---|
source_class |
str |
Name of the class in which the refactoring has to be done |
required |
source_method |
str |
Name of the field whose visibility status has to be changed |
required |
rewriter |
CommonTokenStream |
An instance of TokenStreamRewriter |
required |
Returns:
Type | Description |
---|---|
object (IncreaseMethodVisibilityListener) |
An instance of IncreaseMethodVisibilityListener |
Source code in codart\refactorings\increase_method_visibility.py
def __init__(self, source_class, source_method, rewriter: TokenStreamRewriter):
"""
Args:
source_class (str): Name of the class in which the refactoring has to be done
source_method (str): Name of the field whose visibility status has to be changed
rewriter (CommonTokenStream): An instance of TokenStreamRewriter
Returns:
object (IncreaseMethodVisibilityListener): An instance of IncreaseMethodVisibilityListener
"""
self.source_class = source_class
self.source_method = source_method
self.in_class = False
self.detected_method = False
self.rewriter = rewriter
main(udb_path, source_package, source_class, source_method, *args, **kwargs)
Source code in codart\refactorings\increase_method_visibility.py
def main(udb_path, source_package, source_class, source_method, *args, **kwargs):
"""
"""
db = und.open(udb_path)
methods = db.lookup(f"{source_package}.{source_class}.{source_method}", "Method")
if methods is None or len(methods) == 0:
logger.error("Invalid inputs.")
db.close()
return False
method_entity = methods[0]
if method_entity.simplename() != source_method:
logger.error("Invalid entity.")
db.close()
return False
# Strong overlay precondition
# if not method_entity.kind().check("Private"):
# logger.error("Method is not private.")
# db.close()
# return False
parent = method_entity.parent()
while parent.parent() is not None:
parent = parent.parent()
main_file = parent.longname() # The file that contain the method
db.close()
parse_and_walk(
file_path=main_file,
listener_class=IncreaseMethodVisibilityListener,
has_write=True,
source_class=source_class,
source_method=source_method
)
# db.close()
return True