Forschungsberichte der Fakultät IV – Elektrotechnik und Informatik
1st Workshop on
Refactoring Tools (WRT'07)
Proceedings
July 31, 2007, TU Berlin, Germany
Danny Dig, Michael Cebulla (Eds.)
Bericht-Nr. 2007 – 8
ISSN 1436-9915
Table of Contents
WRT’07 Organization …………………………………………………….v
Proceedings ………………………………………………………………….
• KABA: Automated Refactoring for Improved Cohesion ……………………..1 G. Snelting, M. Streckenbach (Universitat Passau)
• Automation of Refactoring and Refactoring Suggestions for TTCN-3 Test Suites. The TRex TTCN-3 Refactoring and Metrics Tool ……………..…………3 H. Neukirchen, B. Zeiss (University of Gottingen)
• A visual interface for type-related refactorings ……………………………….5 P. Mayer (Ludwig-Maximilians-Universität), A. Meißner (Fernuniversität in Hagen), F. Steimann (Fernuniversität in Hagen)
• ITCORE: A Type Inference Package for Refactoring Tools …………………7 H. Kegel (ej-technologies GmbH), F. Steimann (Fernuniversität in Hagen)
• Flexible Transformation Language …………………………………………….9 A. A. Santos, L. Menezes, and M. Cornélio (UPE)
• A Refactoring Discovering Tool based on Graph Transformation …………11 J. Perez, Y. Crespo (Universidad de Valladolid)
• Refactoring with Contracts ……………………………………………………13 Y. A. Feldman, M. Goldstein (IBM Haifa Research Lab), S. Tyszberowicz (The Academic College of Tel-Aviv Yaffo)
• Synchronizing Refactored UML Class Diagrams and OCL Constraints ……………………………………………………………...15 S. Markovic, T. Baar (Ecole Polytechnique Federale de Lausanne)
• Code Analyses for Refactoring by Source Code Patterns and Logical Queries ……………………………………………………...17 D. Speicher, M. Appeltauer, G. Kniesel (University of Bonn)
• Reuse Based Refactoring Tools ………………………………………………..21 R. Marticorena, C. Lopez (University of Burgos), Y. Crespo, J. Perez (University of Valladolid)
i • SORMASA: A tool for Suggesting Model Refactoring Actions by Metrics-led Genetic Algorithm ………………………………………….……..23 T. Bodhuin, G. Canfora, L. Troiano (University of Sannio)
• Model-driven Software Refactoring …………………………………………..25 T. Mens (Université de Mons-Hainaut),G. Taentzer (Philipps-Universität Marburg)
• The “Extract Refactoring” Refactoring ………………………………………29 R. Robbes, M. Lanza (University of Lugano)
• Advanced Refactoring in the Eclipse JDT: Past, Present, and Future ………………………………………………………….31 R. M. Fuhrer (IBM Research), M. Keller (IBM Zurich), A. Kieżun (MIT)
• Product Line Variability Refactoring Tool ………………………………..…33 F. Calheiros, V. Nepomuceno (Meantime Mobile Creations), P. Borba , S. Soares (UPFE), V. Alves (Lancaster University)
• AJaTS: AspectJ Transformation System …………………………………….35 R. Arcoverde, S. Soares, P. Lustosa, P. Borba (UFPE)
• Towards a Change Specification Language for API Evolution ……………..37 J. Reuter, F. Padberg (Universitat Karlsruhe)
• Holistic Semi-Automated Software Refactoring ……………………………..39 E. Mealy (University of Queensland)
• Engineering Usability for Software Refactoring Tools ……………………...41 E. Mealy (University of Queensland)
• Automated Testing of Eclipse and NetBeans Refactoring Tools ……………43 B. Daniel, D. Dig, K. Garcia, D. Marinov (University of Illinois at Urbana-Champaign)
• Refactoring in Erlang, a Dynamic Functional Language ……………...……45 L. Lovei, Z. Horvath, T. Kozsik, R. Kiraly, A. Vıg, T. Nagy (Eotvos Lorand University)
• Operation-based Merging of Development Histories ………………………..47 T. Freese (University of Oldenburg)
• Improving Method Extraction: A Novel Approach to Data Flow Analysis Using Boolean Flags and Expressions ………………………………….49 N. Juillerat, B. Hirsbrunner (University of Fribourg)
ii • Refactoring-Based Support for Binary Compatibility in Evolving Frameworks ……………………………………………………………...51 I. Savga, M. Rudolf (Technische Universitat Dresden)
• The LAN-simulation: A Refactoring Lab Session ………………………....5…3 S. Demeyer, B. Du Bois, M. Rieger, B. Van Rompaey (University Of Antwerp)
• A Heuristic-Based Approach to Code-Smell Detection ……………………...55 D. Kirk, M. Roper, M. Wood (University of Strathclyde)
• Using Java 6 Compiler as a Refactoring and an Analysis Engine …………..57 J. Bečička, P. Zajac, P. Hřebejk (Sun Microsystems, Inc.)
• Making Programmers Aware Of Refactorings ………………………………59 P. Weißgerber, B. Biegel, S. Diehl (University of Trier)
• Why Don’t People Use Refactoring Tools? ………………………………. …..61 E. Murphy-Hill, A. P. Black (Portland State University)
• Automating Feature-Oriented Refactoring of Legacy Applications ……..…63 C. Kastner, M. Kuhlemann (University of Magdeburg), D. Batory (University of Texas at Austin)
• An Adaptation Browser for MOF ………………………………………… .….65 G. Wachsmuth (Universitat zu Berlin)
• Refactoring Functional Programs at the University of Kent ……………..…67 S. Thompson, C. Brown, H. Li, C. Reinke, N. Sultana (University of Kent)
iii
1st Workshop on Refactoring Tools (WRT’07) Organization
Chair and Organizer: Danny Dig (University of Illinois at Urbana-Champaign)
Program Committee: Jan Becicka (NetBeans Refactoring Engine, Sun Microsystems) Danny Dig (University of Illinois at Urbana-Champaign) William G. Griswold (University of California, San Diego) Ralph Johnson (University of Illinois at Urbana-Champaign) Markus Keller (Eclipse Refactoring Engine, IBM) Oege de Moor (Oxford University Computing Laboratory) Frank Tip (IBM T.J. Watson Research Center)
v
1st Workshop on Refactoring Tools (WRT'07)
KABA: Automated Refactoring for Improved Cohesion
G. Snelting, M. Streckenbach Universitat¨ Passau
class A { 1Overview int x, y, z; void f() { class Client { Cohesion is one of the most important software en- y=x; public static void } gineering principles. Cohesion demands in partic- main(String[] args) { } ular that data and function operating on these data A a1 = new A(); // A1 A a2 = new A(); // A2 are defined together in one class definition. But not class B extends A { B b1 = new B(); // B1 void f() { all existing Java class hierarchies define a cohesive B b2 = new B(); // B2 software architecture. y++; } a1.x = 17; KABA analyses a class hierarchy together with void g() { a2.x = 42; a set of client programs. It refactors the hierarchy x++; if (...) { a2 = b2; } f(); such that data members (fields) and methods oper- a2.f(); } ating on the data are always grouped together, and b1.g(); void h() { b2.h(); that any class in the refactored hierarchy contains f(); } only fields and methods which are indeed needed by x--; } some client code using the class. Every class-typed } variable is given a new type (namely a class from } the refactored hierarchy), while the program state- ments remain essentially unchanged. In contrast to some other refactoring tools, KABA guarantees that program behaviour is unchanged after refactoring. KABA is based on fine-grained (static or dy- namic) program analysis, namely points-to analysis, type constraints, and mathematical concept lattices. Typically, an original class is split if different clients use different subsets of a class’s functionality. In order to avoid too fine-grained refactorings, the ini- Figure 1: A small program and its KABA refactor- tial refactoring is usually simplified by automatic or ing manual semantics-preserving transformations. Thus KABA provides fine-grained insight into the true usage patterns of classes in a program, can serve B1 calls g() while B2 calls h(), hence two to evaluate cohesion of existing systems, and will new subclasses for B are introduced. automatically generate semantics-preserving refac- The new subclasses give fine-grained insight into torings which improve cohesion. KABA is imple- what objects really do, and maximise cohesion as mented in form of a refactoring browser. in the new hierarchy members are grouped together iff they are used together. A nice by-product is that 2 Examples and Experiences objects are minimized and dead members are elim- inated. But since the refactored hierarchy may be KABA reacts to usage patterns of a class by client quite fine-grained, the engineer may remerge classes code. In figure 1, client objects A1, A2, B1, B2 (eg the two top classes in figure 1). In any case, access different subsets of class A and B: KABA guarantees preservation of semantics. For the complex technical details, see [1]. object A1 accesses only x from class A, while The resulting refactored hierarchy, as well as A2 also accesses f() and thus y; therefore cross references between new and old classes, as class A is split into two subclasses displayed by the KABA refactoring browser, are
1 1st Workshop on Refactoring Tools (WRT'07)
...RuleBlock
...TreeElement ...OneOrMoreBlock ...AlternativeBlock ...BlockWithImpliedExitPath ...ZeroOrMoreBlock ...RuleRefElement ...SynPredBlock
...BlockEndElement ...RuleEndElement
Object ...GrammarElement ...AlternativeElement ...ActionElement ...TokenRefElement
...GrammarAtom ...CharLiteralElement
...CharRangeElement ...StringLiteralElement
...TokenRangeElement ...WildcardElement
5 ...GrammarElement 1
4 ...BlockEndElement 14 ...RuleEndElement 2 2 13 ...ZeroOrMoreBlock Figure 2: KABA screenshot for figure 1 1 12 ...BlockWithImpliedExitPath
11 ...AlternativeBlock 17 ...OneOrMoreBlock 1 ...AlternativeBlock 2 ...RuleRefElement 19 3 ...SynPredBlock 1 16 ...ActionElement 1 1 10 ...AlternativeBlock ...AlternativeBlock ...AlternativeBlock 3 ...AlternativeElement 20 21 ...RuleBlock 1 ...RuleBlock 1 ...GrammarElement 22 ...CharRangeElement Object 1 ...AlternativeElement 1 ...AlternativeBlock ...AlternativeElement 6 7 ...AlternativeBlock ...AlternativeBlock 2
24 ...TreeElement 1
...GrammarAtom 9 ...TokenRefElement 1
8 ...GrammarAtom 15 ...WildcardElement 1
18 ...StringLiteralElement 1
23 ...CharLiteralElement 1
Figure 4: KABA refactoring (lower) for a part of antlr (upper)
Figure 3: Browser for original types (top); Browser KABA is a research prototype. It can handle full for class content (bottom). Java (without reflection). KABA has been applied to several small and medium-scale example systems, and generated useful refactorings. For large sys- shown in figures 2 and 3. The user may remerge tems, the refactorings may be quite fine-grained, splitted classes, which can reduce cohesion again thus we are exploring even more agressive simpli- but may improve other software quality factors. fications of the original refactoring which still im- More details about the KABA refactoring browser prove cohesion and guarantee behaviour preserva- and semantics-preserving class merging and elimi- tion. nation of multiple inheritance can be found in [3]. A more realistic case study was the antlr parser References. Technical details and more experi- generator. KABA discovered problems with cohe- ence with KABA can be found in sion in the original design and generated an im- proved class hierarchy (figure 4). For example, 1. G. Snelting, F. Tip: Reengineering Class Hier- KABA discovered that the original classes Gram- archies Using Concept Analysis. ACM Trans- marElement and AlternativeElement can actions on Programming Languages and Sys- be merged, while preserving semantics and improv- tems (TOPLAS), May 2000, pp. 540-582. ing cohesion. On the other hand, some original 2. M. Streckenbach, G. Snelting: Refactoring classes were split to 5, 6 or 9 new classes. Thus Class Hierarchies with KABA. Proc. OOPSLA the hierarchy structure was changed quite a bit. But 2004, Vancouver, British Columbia, Canada, note that the number of classes remained about the October 2004, pp. 315-330. same. As a third example, we mention javac,where 3. Mirko Streckenbach: KABA - A System for KABA reproduced the original class hierarchy al- Refactoring Java Programs. PhD thesis, Uni- most exactly. This proved that the original javac versitat¨ Passau, April 2005. design was good. More details about refactoring antlr and javac can be found in [2].
2 1st Workshop on Refactoring Tools (WRT'07)
Automation of Refactoring and Refactoring Suggestions for TTCN-3 Test Suites The TRex TTCN-3 Refactoring and Metrics Tool
Helmut Neukirchen and Benjamin Zeiss Software Engineering for Distributed Systems Group, Institute for Informatics, University of G¨ottingen, Lotzestr. 16–18, 37083 G¨ottingen, Germany {neukirchen|zeiss}@cs.uni-goettingen.de
Abstract Refactoring is not only useful for For being able to automatically identify loca- source code of implementations, but as well for tions in source code where a refactoring is worth- test specifications. The open source TRex tool while, we investigated corresponding TTCN-3 automates the application of refactorings and metrics and TTCN-3 code smells. For example, the detection of refactoring opportunities for test a Number of References metric is used to iden- suites that are specified using the standardised tify definitions that are never referenced and can Testing and Test Control Notation (TTCN-3). thus be removed or that are referenced only once Depending on the refactoring, the behaviour pre- and can thus be inlined using a corresponding serving transformations may include syntax tree refactoring. Even though we experienced that transformations and direct modification of the metrics are able to detect various issues, they source code; for suggesting refactorings, metrics are not sophisticated enough to detect more ad- are calculated and code smell patterns are de- vanced problems. Therefore, we investigated tected. pattern-analysis of source code and as a result, we have developed a catalogue of TTCN-3 code smells [6]. So far 38 TTCN-3 code smells have Introduction. The Testing and Test Control been identified. Notation (TTCN-3) [1] is a mature standard from the telecommunication and data commu- TRex Implementation. To automate refac- nication domain that is widely used in indus- toring for TTCN-3 test specifications, we have try and standardisation to specify and execute implemented the open source TTCN-3 Refac- test suites. Just like any other software artifact, toring and Metrics tool TRex [4]. The ini- tests suffer from quality problems [2]. To remove tial version has been developed in collaboration such quality problems from TTCN-3 test suites, with Motorola Labs, UK [7]. TRex implements we use refactoring [3]. For suggesting refactor- state-of-the-art editing capabilities, assessment ings, we use a combination of metrics and code and improvement techniques for TTCN-3 test smell detection. suites based on the calculation of metrics, au- In the following, we first present our approach tomated smell detection, and refactoring. TRex for the quality assessment and improvement of is based on the Eclipse Platform [8] and thus TTCN-3 test suites. Subsequently, the TTCN-3 makes use of the infrastructure offered, e.g. the Refactoring and Metrics Tool TRex and its Language Toolkit (LTK) or the Eclipse Test implementation are described. Finally, future & Performance Tools Platform (TPTP) static work is discussed in the outlook. analysis framework. The analysis infrastruc- ture including lexer, parser, symbol table, pretty Refactoring, Metrics, and Code Smell De- printer, etc. for TTCN-3 have been implemented tection for TTCN-3 Test Suites. Refactor- using ANother Tool for Language Recognition ing of test suites has so far only been studied (ANTLR) [9]. in the context of JUnit [2]. Thus, we have de- The automated refactorings we currently pro- veloped a refactoring catalogue for TTCN-3 [4, vide concentrate mostly on the improvement 5] which includes 23 refactorings using language of test data descriptions (TTCN-3 templates). specific concepts of TTCN-3. Furthermore, we The refactoring implementations can be applied found 28 refactorings from Fowler’s Java refac- in two different ways: either the test developer toring catalogue [3] to be applicable to TTCN-3. invokes the refactoring from the code location
3 1st Workshop on Refactoring Tools (WRT'07)
(2) Quality Assessment (3) Automated Refactorings Rule-Based Refactoring Suggestions Transformed Subtree of the Pretty Printer Metrics / Code Smell Detection Syntax Tree
(1) Static Analysis
ANTLR Refactored TTCN-3 Syntax Tree / Refactoring Change Lexing, TTCN-3 Source Code Symbol Table Processor Weaver Parsing Source Code
User Language Eclipse Platform Text Editor TPTP ... Interface Toolkit
Figure 1: The TRex Toolchain which should be subject to the refactoring or further TTCN-3 refactorings and more sophis- the refactoring is invoked directly by a quick-fix ticated code smell detection techniques. which is provided by the analysis results of the automated quality assessment. References For the assessment, a considerable number of size metrics (such as counting the number of [1] ETSI: ETSI Standard (ES) 201 873 V3.2.1: references to a definition) and structural met- The Testing and Test Control Notation ver- rics (using control-flow graphs and call graphs) sion 3; Parts 1-8. European Telecommuni- are calculated. Furthermore, a total number cations Standards Institute (ETSI), Sophia- of 11 TTCN-3 code smell detection rules have Antipolis, France (2007) been implemented that partially allow the use [2] van Deursen, A., Moonen, L., van den of quick-fixes to invoke automated refactorings. Bergh, A., Kok, G.: Refactoring Test Code. The overall toolchain of TRex is depicted in In: XP2001. (2001) Fig. 1. Based on the syntax tree and symbol table, the automated refactorings can either be [3] Fowler, M.: Refactoring – Improving the applied directly or invoked through the refac- Design of Existing Code. Addison-Wesley, toring suggestions obtained by means of met- Boston (1999) rics and code smell detection. The refactorings [4] TRex Team: TRex Website. http://www. are applied directly to the source code using a trex.informatik.uni-goettingen.de programmatic text editor and may as well in- (2007) volve syntax tree transformations. The corre- sponding text representation from transformed [5] Zeiss, B.: A Refactoring Tool for TTCN- subtrees is reobtained by a pretty printer com- 3. Master’s thesis, Institute for Informatics, ponent and weaved back into the surrounding University of G¨ottingen, Germany, ZFI-BM- TTCN-3 source code. 2006-05 (2006) The implementations of metric calculation, [6] Bisanz, M.: Pattern-based Smell Detec- code smell detection, and refactoring are tested tion in TTCN-3 Test Suites. Master’s using Plug-in Development Environment (PDE) thesis, Institute for Informatics, University JUnit tests, e.g. by comparing source code snip- of G¨ottingen, Germany, ZFI-BM-2006-44 pets before and after the refactoring. (2006) [7] Baker, P., Evans, D., Grabowski, J., Outlook. A remaining issue open for research Neukirchen, H., Zeiss, B.: TRex – The is the validation of test refactorings: Unlike Java Refactoring and Metrics Tool for TTCN-3 refactorings, for example, there are no unit tests Test Specifications. In: TAIC PART 2006, available for tests and simply running a test IEEE Computer Society (2006) 90–94 suite against an implementation is not enough if the test behaviour consists of more than one [8] Eclipse Foundation: Eclipse. http://www. path. We are thus investigating bisimulation eclipse.org (2007) to validate that the observable behaviour of a [9] Parr, T.: ANTLR parser generator v2. refactored test suite has not changed. In addi- http://www.antlr2.org (2007) tion, we are extending TRex by implementing
4 1st Workshop on Refactoring Tools (WRT'07)
A visual interface for type-related refactorings
Philip Mayer Andreas Meißner Friedrich Steimann Institut für Informatik Lehrgebiet Programmiersysteme Lehrgebiet Programmiersysteme Ludwig-Maximilians-Universität Fernuniversität in Hagen Fernuniversität in Hagen D-80538 München D-58084 Hagen D-58084 Hagen
[email protected] [email protected] [email protected]
ABSTRACT Refactoring to the use of such interfaces requires an analysis of In this paper, we present our approach to a visual refactoring what is really needed in contexts by analyzing the code to find tool, the Type Access Analyzer (TAA), which uses program used or unused members. With this information, the code can analysis to detect code smells and for suggesting and be refactored in an informed way by: performing refactorings related to typing. In particular, the • creating, adapting, or removing interfaces, and TAA is intended to help the developers with consistently • retrofitting existing variable types to the newly introduced, programming to interfaces. or adapted, interfaces. The TAA follows the approach discussed in the introduction by 1. INTRODUCTION analyzing the code using the type inference algorithm we have When looking at currently available type-related refactoring introduced in [2], presenting the results in a visual form, and tools, a noticeable gap shows between simple refactorings like providing access to and feedback from simplified versions of Extract Interface and more complex, “heavyweight” ones like refactorings such as Extract Interface or Infer Type. Use Supertype Where Possible and Infer Type [2]: While the former do not provide any analysis-based help to the user, the To give the programmer a comprehensive and concise view of latter perform complex program analyses, but due to their the program that is tailored to the specific problems of autonomous workings – without interacting further with the interface-based programming, we have developed the supertype user except for preview functionality – it is not always clear lattice view described in [4]. In this view, the supertype when to apply them, what result to expect, and just how far the hierarchy of the type under consideration is enhanced by changes of the refactorings will reach. For example, displaying a bounded lattice of the set of members of the type, each node being enriched with various kinds of information. • Extract Interface keeps programmers in the dark about Figure 1 shows a screenshot of the TAA in action on a four- which methods to choose, method class (due to space limitations, only a part is shown). • Use Supertype Where Possible replaces all declaration
elements found without a proper way of restricting it, • Infer Type creates new types guaranteeing a type-correct program, but often lacking a conceptual justification. As a remedy, we propose a new approach to refactoring. The contributions of this approach consist of: • moving precondition checking and parameterization from refactorings to a dedicated program analysis component, • presenting the analysis results visually in such a way that they suggest refactorings, and • breaking down existing refactorings into simpler tools which perform predictable changes immediately visible and controllable by the visual refactoring view. This approach is prototypically realized in our Type Access Analyser (TAA) tool for type-related refactorings. Figure 1: TAA Visual View 2. THE TYPE ACCESS ANALYZER Four types of information are immediately visible from the A loosely coupled and extensible software design can be graph: reached by consistently programming to interfaces [1], • Possible types – each node is a possible supertype of the specifically to what we have called context-specific interfaces class (which is situated at the bottom; not shown). [3]. An interface is considered to be context-specific if it contains exactly – or, in a more relaxed interpretation, not • Available types are shown in the types section on a node. much more than – the set of members of a type required in a Subtyping relations between types are indicated by UML- certain area of code (which is comprised of variables and style subtyping arrows. methods declared with the interface as their types and their transitive assignment closure).
5 1st Workshop on Refactoring Tools (WRT'07)
• Variables and methods. Each variable or method typed Interface is Interface is present in a Redeclare with one of the type(s) under consideration is included in not (yet) used node with ideally but no variables / the graph. Assignments between these elements are shown declared placements methods with with red arrows. existing interface • Declared placement. A variable or method is shown in the declared placement section of the node containing Table 1: Code Smells the declared type of the variable or method. As can be seen from the table above, the TAA suggests a • Ideal placement. If different from the declared number of actions to be taken as a result of identified smells. placement, a variable or method is shown in the ideal These actions are implemented as refactorings. In line with our placement section of the node which corresponds to the approach of putting the developer in charge, these refactorings set of members (transitively) invoked on this variable or may be selected as (semantically) appropriate by the user. method. Contrary to existing refactorings, the ones invoked from the The quality of the variable and method declarations (i.e. the TAA in general do not require further dialog-based matching between types and their usage contexts) is shown by parameterization – all information required for a refactoring is the colours of the background of the node. A green colour already available in the graph and the way the user invokes the represents the use of context specific types, while a red colour refactoring in a visual way. These visual start procedures are signals a mismatch between types and usage contexts. shown in Table 2: Selecting variables or methods in the graph further enriches the display: Refactoring Visual start procedure Extract interface Alt + Drag an interface to • A line is drawn connecting the ideal and declared another, higher node in the graph placements of an element (if different). Move interface in Drag an interface to another node • Additional lines are drawn connecting all elements which hierarchy in the graph (up or down) the current element is being assigned to (transitively). Remove interface from Select an interface, select delete This data may be used to detect smells in the code and take hierarchy appropriate action. The following section will detail this. Merge interfaces Select two interfaces, select merge 3. VISUAL REFACTORINGS Redeclare declaration Select a variable or method, elements (transitively, select redeclare By analyzing a type in the TAA view, the developer has i.e. following complete overview of the usages of this type. The annotations assignments) on the supertype lattice suggest a number of ways of improving the typing situation; specifically, the arrangements of types and Table 2: Refactorings variables/methods visualize code smells which can be removed While the Extract Interface refactoring is already available as- by applying refactorings. is in many tools, the others have been either adapted or The following table associates design problems in the code, the specifically written for the TAA. way these problems show up in the visual view (as smells), and the actions to be taken by the developer to deal with those 4. SUMMARY problems. Later on, we will present refactorings for executing In this paper, we have described our approach to visual these actions. refactoring. The TAA tool aids the developer by providing valuable information about the typing situation in the code – in Problem Smell Action itself suitable for program understanding – and thereby suggests No interfaces Nodes in the graph with Extract interface refactorings whose effect is more predictable and which can be available for a ideal placement of and redeclare executed directly from the visual view. The results of the context variables/methods, but variables/ refactorings are likewise directly shown in the graph. methods with without interfaces In the future, we will investigate ways of further improving the new interface user interface and add more refactorings to the TAA. Poorly Ideal placement of Move existing designed variables/methods interface up or 5. REFERENCES interface swarming around down in [1] E Gamma, R Helm, R Johnson, J Vlissides Design existing interfaces hierarchy Patterns - Elements of Reusable Software (Addison- Two Two interfaces share Merge Wesley, 1995). interfaces for the same/ neighbouring interfaces [2] F Steimann “The Infer Type refactoring and its use for the same nodes, each with ideally interface-based programming” JOT 6:2 (2007) 67–89. purpose placed variables/ methods [3] F Steimann, P Mayer “Patterns of interface-based programming” JOT 4:5 (2005) 75–94. Superfluous Interface present in a Remove interface node without declared interface from [4] F Steimann, P Mayer “Type Access Analysis: Towards placements; no ideal hierarchy informed interface design” in: TOOLS (2007) to appear placements in vicinity
This work has been partially sponsored by the project SENSORIA, IST-2005-016004.
6 1st Workshop on Refactoring Tools (WRT'07)
ITCORE: A Type Inference Package for Refactoring Tools
Hannes Kegel Friedrich Steimann ej-technologies GmbH Lehrgebiet Programmiersysteme Claude-Lorrain-Straße 7 Fernuniversität in Hagen D-81543 München D-58084 Hagen [email protected] [email protected]
1. Introduction ment is typed with its inferred type, no member can be removed from the type without introducing a typing error. ECLIPSE’s current distribution comes with various type-related The constraints generated by ITCORE are similar to that of IN- refactoring tools, some of which rely on a built-in framework for FER GENERIC TYPE ARGUMENTS in that parameterized types are solving a set of type constraints derived from the declarations and decomposed and separate constraint variables for all type argu- expressions of a type-correct program. We have adapted this ments are created. For assignments, individual constraints are framework to embody the type inference underlying our INFER generated for the main types and all type arguments. If the re- TYPE refactoring tool for JAVA [6], which extracts the maximally ceiver of a method invocation is a parameterized type, method general type for a declaration element (variable or method) based and type arguments are also connected through constraints. on the use of that element in a program. The new implementation ITCORE differs from the engines of its predecessors in various surpasses the original one by greater memory efficiency; it also respects: fully embodies the language extensions of JAVA 5, most notably 1. The constraints generated by ITCORE cover the complete type generics. It has been extensively tested by automatically applying system of JAVA 5. This lets ITCORE change type arguments in- it to all declaration elements of several large code bases. cluding those of nested parametric types, as e.g. Test in Experimenting with INFER TYPE, it soon became clear that its class MyComparator implements Comparator
7 1st Workshop on Refactoring Tools (WRT'07)
USE SUPERTYPE WHERE POSSIBLE In a similar vein, ITCORE can applications remain independent of each other [1]. Components serve as the basis for USE SUPERTYPE WHERE POSSIBLE: by com- are independent (decoupled) only if they do not reference each puting the inferred types for all declaration elements of a certain other directly, neither through declarations nor through instance type, it can be checked for a selected supertype where this super- creation (constructor calls). One prerequisite to successful de- type could be used instead. Again, using ITCORE would make full pendency injection is therefore that all such references are re- coverage of generics available to this refactoring. moved. As has been outlined above, this can easily be done by ITCORE, namely by inferring the common type of all references to EXTRACT INTERFACE Current implementations of EXTRACT IN- the class depended upon. The rest, removing constructor calls (as TERFACE let the developer choose the members of the interface. for instance described in [8]) and instrumenting the assembly of By naming the declaration elements for which this interface is to components, is independent of ITCORE; it can be done with the be used, ITCORE can be used to preselect the members that are standard means of AST manipulation. We are currently working needed, allowing the developer to add (but not delete!) members on an implementation for SPRING and EJB3. if deemed appropriate. It is then guaranteed that the new interface can be used where it is intended to be. CREATE MOCK OBJECT Unit testing requires that each unit is tested independently of others. In practice, however, units depend INFER TYPE INFER TYPE is a relatively new refactoring de- on others that have not been sufficiently tested to be assumed cor- scribed in some detail elsewhere [6]. It is currently the only one rect, or whose behaviour cannot be controlled by a test case. In that has already been migrated to ITCORE; see these cases, units depended upon are replaced by mock objects http://www.fernuni-hagen.de/ps/prjs/InferType3/. (really: mock classes). These objects exhibit the same provided interface as those they replace; their implementation, though, is 3.2 Refactorings awaiting tool support different (“mocked”). Many useful refactorings still lack automation. Some of them can Mocking complete classes with many methods may be more be implemented using ITCORE, as the following list suggests. than is actually needed. To avoid this, ITCORE can compute from a test case (or test suite) the interface actually required from a REPLACE INHERITANCE WITH FORWARDING Suppose a class in- mock class, which may be less than what is offered by the class it herits many members but needs only few of them, so that its inter- mocks. This computed interface can drive the creation of the face is needlessly bloated; in this case, it may be better to define a mock class, or the necessary overriding of methods if the mock is new class with just the required interface, and have it hold an in- derived from the original class. Also, it can serve as a common stance of its former superclass to which it forwards all service re- abstraction of the original and the mock class in the context of the quests. The protocol of the new class can be computed using IT- test (suite). Cf. also [2]. CORE, simply by inferring the types of all declaration elements typed with the class. 4. Conclusion In case instances of the new class need to substitute for in- stances of its former superclass (which is often the case in frame- There seems to be a whole class of refactorings that rely on the works), subtyping cannot be avoided. However, in these cases ei- determination of the minimal protocol, or the maximally general ther an existing or an inferred interface of the new class and its type, of a program element. The reasons for this may vary: de- former superclass can be used in the places where the substitution creasing coupling and increasing variability as for GENERALIZE occurs (the plug points of the framework). Both can be derived DECLARED TYPE, USE SUPERTYPE WHERE POSSIBLE, INJECT DE- PENDENCY, or INFER TYPE; cleaning up the interface as for RE- using ITCORE. In fact, as has been pointed out in [7], even the question of whether such a substitution is possible (and corre- PLACE INHERITANCE WITH FORWARDING/DELEGATION; or simply sponding subtyping, i.e., interface implementation, is therefore reducing the amount of necessary work, as in CREATE MOCK OB- JECT. All have in common that they can be built on the type infer- necessary) can be computed by means of ITCORE; all that needs to be done is search for assignment chains from (declaration ele- ence procedure offered by ITCORE. ments of) the new class to (declaration elements of) its former su- References perclass [7]. [1] http://www.martinfowler.com/articles/injection.html REPLACE INHERITANCE WITH DELEGATION A simple, but easily [2] S Freeman, T Mackinnon, N Pryce, J Walnes “Mock roles, not ob- overlooked, twist to the previous refactoring is that a superclass jects” in: OOPSLA Companion (2004) 236–246. may contain calls to its own, non-final methods. In this case, and if any of the called methods are overridden in the subclass to be [3] RM Fuhrer, F Tip, A Kiezun, J Dolby, M Keller “Efficiently refac- refactored, replacing inheritance with forwarding changes pro- toring Java applications to use generic libraries” in: ECOOP (2005) 71–96. gram semantics, because the formerly overriding methods in the subclass no longer override (the extends is removed; the new [4] http://www.jetbrains.com/idea/docs/help/refactoring/ class is no longer a subclass of its former superclass) so that dy- replaceinheritwithdelegat.html namic binding of these methods does not apply. In these cases, [5] P Mayer, A Meißner, F Steimann “A visual interface for type-related forwarding must be replaced by delegation [9]. refactorings” submitted to: 1st Workshop on Refactoring Tools. In class-based languages such as JAVA, delegation must be [6] F Steimann “The Infer Type refactoring and its use for interface- mimicked by subclassing. IDEA’s REPLACE INHERITANCE WITH based programming” JOT 6:2 (2007) 67–89. DELEGATION refactoring tool does exactly this [4]; combining it [7] F Steimann, P Mayer “Type Access Analysis: Towards informed in- with REPLACE INHERITANCE WITH FORWARDING as described terface design” in: TOOLS (2007) to appear. above would further automate this refactoring. [8] http://www.fernuni-hagen.de/ps/prjs/InferType/ INJECT DEPENDENCY DEPENDENCY INJECTION is an increasingly ReducingDependencyWithInferType.html popular design pattern that lets components to be assembled into [9] LA Stein “Delegation is inheritance” in: OOPSLA (1987) 138–146.
8 1st Workshop on Refactoring Tools (WRT'07)
Flexible Transformation Language
Alexandre A. Santos1, Luis Menezes1, and Márcio Cornélio1
1 Departamento de Sistemas Computacionais Rua Benfica, 455, 50720-001, Brazil. {aasj, lcsm, mlc}@dsc.upe.br
1. Introduction to be affected by the transformations; afterwards the transformation code is explained in detail. The use of automatic refactoring [1] in large scale projects has increased in the last few years. 3.1. The Sample Program Unfortunately the available tools provide a fixed set of program transformations. Thus, if a user needs a Our sample program, written in a pseudo-language, refactoring that is not supplied by a development has an attribute x and a get method to return it, called environment, it is necessary to know deeply the getName. After the transformation, it is going to have environment architecture in order to implement it, the attribute name and all its usage renamed from x to which takes a lot of time and usually is not in name for a better legibility. This transformation is accordance with project constraints. shown in Figure 1. This paper presents the Flexible Transformation System, which can be easily extended with language and 1 Program temp; 1 Program temp; refactoring descriptions. 2 string x; 2 string name; 3 string getName() 3 string getName() 4 { 4 { 2. The Flexible Transformation System 5 Return x; 5 Return name; 6 } 6 } The transformation system is composed by a set of 7 End temp; 7 End temp; tools that process a refactoring description and produces Figure 1 – A Sample Program Transformation. a refactoring environment according to the description. The refactoring description makes use of the abstract 3.2. The Transformation Code and concrete syntax of the target language, and its static semantics description, which are written using In this Section, a transformation code written using traditional notations such as BNF and attribute the Flexible Transformation Language is described to grammars. demonstrate how easy are the usage of the operators of During the transformation execution, a validation is this language along with their purposes. Figure 2 performed in order to capture errors like ill-term usage, presents the code that will be detailed later during this invalid semantic production, etc. Any error found makes Section. the system abort and return to the initial state with the Basically, it looks for an identifier declaration node purpose of avoiding inconsistencies. which has x as name and string as type. If found, it The Flexible Transformation System is being verifies if does not exist an identifier declaration node developed using Java [2] as programming language and with any type called name. If not, it replaces each usage JavaCC [3] as the parser generator. However, the most of x with name and also renames the node declaration relevant contribution of our system is a language for from x to name. describing refactorings.
01 start { 3. Transformation Language Operators 02 foreach(W in IdDecl("string", "x")) { 03 if (not exist(IdDecl(A, “name”))) { The transformation language contains operators 04 foreach(R in IdUsage("x")) { designed to ease operations against the decorated 05 R=>IdUsage("name"); abstract syntax tree such as tree searching, pattern 06 }; matching and term rewriting that are useful in 07 W=>IdDecl("string", "name"); 09 }; refactorings. 10 }; In order to demonstrate the applicability of those 11 } operators, a sample program wrote in a pseudo- language is used and analyzed focusing on what is going Figure 2 – The Transformation Code.
9 1st Workshop on Refactoring Tools (WRT'07)
The lines 01 and 11 delimit the program scope called 5. References the program start point. Each line inside this block will be executed. However, the start point is not mandatory 1. W. Opdyke: Refactoring Object-Oriented and someone might implement just procedures to be Frameworks. PhD thesis, University of Illinois at imported and used by others program transformations. Urbana-Champaign, 1992. In this case, the program start point will not exist. 2. Sun Microsystems. Retrieved 07-2007, from Java Before explaining the foreach statement, it is SE: http://java.sun.com/javase/. necessary to elucidate the node function as the 3. CollabNet. Retrieved 07-2007, from JavaCC foreach uses it. Node function is an expression in the Home: https://javacc.dev.java.net/. language, responsible for looking in the AST to find a specific node or a set of nodes based on the arguments passed which are filter criteria. Besides searching, the node function could also be used in pattern matching expressions to verify if some variable matches the specified format. In the above example, IdDecl and IdUsage are node functions defined in the abstract syntax of the pseudo-language. The lines 02,10 and 04,06 delimit the scope of the first and second foreach statement, respectively shown in Figure 2. The command foreach is iterative and uses the node function structure to bring back all tree nodes that matches a format defined. This command iterate over the result list making possible the execution of operations over each node. The node function used in the example was the IdDecl and IdUsage as said before. The first one returns all identifier declarations that have x as name and string as type and the second one returns all identifier usages that have x as name. The If-Else command could be used to verify the existence of a specific node using the exist clause, or to verify if the current node matches a specific format using the is clause. Both are flexible validations available on the language. The lines 03 and 09 delimit its scope. In this case, it checks if it does not exist an identifier declaration with any type called “name”. Finally, the term rewriting operation, described by the symbol “=>”, which is used in the lines 05 and 07, responsible for transforming a node in a new one. In the first case, it renames the identifier usage from x to name; in the other case, it renames the identifier declaration from x to name, preserving the same type. It is important to mention that the language has other features that were not shown here, such as procedures definitions and string operations since they are standard for the existent languages.
4. Future Plans
In the short term, we are going to have a flexible transformation system based on a generic transformation language, tested against different programming languages. This system will help both refactoring community and developers, in which anyone will be able to define his own transformations and automate the application of complex refactoring as the transformation language defined is easy to understand and to use.
10 1st Workshop on Refactoring Tools (WRT'07)
A Refactoring Discovering Tool based on Graph Transformation
Javier P´erez,Yania Crespo Departamento de Inform´atica Universidad de Valladolid {jperez,yania}@infor.uva.es
Abstract so we believe that graph transformation, which focuses on description and manipulation of structural informa- One of the problems of documenting software evo- tion, is a quite appropriate formalism. lution arises with the extensive use of refactorings. In [4, 7] the graph transformation approach is shown Finding and documenting refactorings is usually harder to be valid for refactoring formalisation. In these than other changes performed to an evolving system. works, programs and refactorings are represented with We introduce a tool prototype, based on graph trans- graphs, in a language independent way, using a kind formation, to discover refactoring sequences between of abstract syntax trees with an adequate expressive- two versions of a software system. When a refactor- ness level for the problem. This representation format ing sequence exists, our tool can also help reveal the is claimed to be language independent and very sim- functional equivalence between the two versions of the ple, with the purpose of making it easy to use and as system, at least, as far as refactorings can assure be- flexible as possible. Therefore, as suggested in [7], it haviour preservation. was necessary to extend the graph format to represent ‘real’ programs containing specific elements and con- structions of a particular language. We have developed 1 Introduction an extension to represent Java programs which we have named ‘Java program graphs’. Efforts to include refactorings as a regular tech- Once programs have been represented with graphs, nique in software development have led refactoring and refactoring operations have been described as support to be commonly integrated into development graph transformation rules, we apply graph parsing al- environments (i.e. Eclipse Development Platform, gorithms to find the refactoring sequence between two IntelliJ R Idea, NetBeans, etc.). Finding refactorings, different versions of a software system. We address now they are extensively used, is one of the problems the problem of finding a transformation sequence from of software evolution [2, 3]. For version management one version of the system to another as a state space tools, for example, refactorings are modifications more search problem. With this approach we identify: the difficult to deal with than any other kind of changes. original/old system as a start state, refactoring Our tool prototype implements a method, based on operations as state changing operations (edges), the graph transformation [5, 8], to discover refactoring se- refactored/new system as the goal state, the prob- quences between two versions of a software system. In lem of whether a refactoring sequence exists as case a refactoring sequence exists, our tool can also a reachability problem, and a refactoring sequence help reveal the functional equivalence between the two as the path from the start state to the goal state. versions of the system, at least, as far as refactorings We propose a basic search algorithm to look for can assure behaviour preservation. refactoring sequences. In order to allow some kind of guided search, we base our solution in the use of 2 Graph parsing approach refactoring preconditions and postconditions. So our approach needs refactoring definitions which include To search refactorings we use graph transforma- preconditions and postconditions. tion as an underlying formalism to represent Object- The main idea of our algorithm is to iteratively mod- Oriented software and refactorings themselves. Refac- ify the start state applying refactoring graph transfor- torings involve modification of the system structure, mation rules. The set of selectable refactorings at each
11 1st Workshop on Refactoring Tools (WRT'07)
iteration is composed just of refactorings whose precon- ditions are held in the current state and whose post- conditions are held in the goal state. When no more refactorings are selectable, the algorithm backtracks to the last transformation applied. The algorithm ends up in success when the current state graph is isomor- phic to the goal state graph. The refactoring sequence is the path found to the goal state. The algorithm ends up in fail when no more refactorings can be executed, and the current and goal states are not isomorphic. Figure 1. Outline of our tool
3 Our tool so far not. Our implementation is a proof of concept that offers very promising results. Our refactoring discovering tool consists mainly of a Our innmediate objectives are to improve the vi- refactoring searching graph grammar and a plu- sualisation of results, to implement refactoring search- gin for the Eclipse Development Platform (see ing rules to support more refactoring operations and to Fig. 1), which has a strong refactoring support. measure the scalability of our technique over industrial- We have developed a sample implementation of some size systems. This will include improving rule descrip- searching rules to test the validity of our approach. tions to take benefit of new features being added in the Up to date, the refactoring searching graph grammar newest versions of the AGG tool or even testing other searchs for pullUpMethod, renameMethod and useSu- graph transformation tools for the back-end. perType, supported by the Eclipse refactoring engine, removeMethod and removeClass. Using graph repre- References sentation for source code enables to adjust the detail level by adding or removing elements from the graph [1] Agg home page, graph grammar group, Technische Uni- model. The set of searchable refactorings can be easily versit¨atBerlin. http://tfs.cs.tu-berlin.de/agg. extended by adding more searching rules to the gram- [2] S. Demeyer, S. Ducasse, and O. Nierstrasz. Finding mar. refactorings via change metrics. In OOPSLA, pages We use the AGG graph transformation tool [1] as 166–177, 2000. the back-end of our prototype implementation. AGG [3] D. Dig, C. Comertoglu, D. Marinov, and R. Johnson. is a rule-based tool that supports an algebraic approach Automatic detection of refactorings in evolving com- to graph transformation, and allows rapid prototyping ponents. In ECOOP 2006 - Object-Oriented Program- for developing graph transformation systems. We have ming; 20th European Conference, Nantes, France, July 2006, Proceedings, pages 404–428, 2006. chosen AGG mainly because it supports graph parsing. [4] N. V. Eetvelde and D. Janssens. Refactorings as graph Graph parsing can be used to perform depth first search transformations. Technical report, Universiteit Antwer- with backtracking, and our algorithm can be partially pen, 2005. implemented that way. [5] H. Ehrig, G. Engels, H.-J. Kreowski, and G. Rozen- Our initial Eclipse plugin [6] obtains the Java pro- berg, editors. Handbook of Graph Grammars and Com- gram graph representation from the source code of the puting by Graph Transformations, Volume II: Applica- two versions of a system, launches the graph transfor- tions, Languages and Tools, volume 2. World Scientific, mation parser and shows a part of the output dumped 1999. by the parser. From this raw information, we are able [6] B. Mart´ınArranz. Conversor de Java a grafos AGG para Eclipse. Master’s thesis, Escuela T´enica Superior to identify the refactoring sequence found, but this de Ingenier´ıa Inform´atica, Universidad de Valladolid, is only valid for the purpose of testing our approach. September 2006. There is a clear need to improve the front-end to show [7] T. Mens, N. Van Eetvelde, S. Demeyer, and up the search results in a more convenient way. D. Janssens. Formalizing refactorings with graph trans- formations. Journal on Software Maintenance and Evo- 4 Results and future work lution: Research and Practice, 17(4):247–276, July/Au- gust 2005. [8] G. Rozenberg, editor. Handbook of Graph Grammars We have developed a tool prototype based on graph and Computing by Graph Transformations, Volume I: transformation to find whether a refactoring sequence Foundations, volume 1. World Scientific, 1997. exists between two versions of a software system or
12 1st Workshop on Refactoring Tools (WRT'07)
Refactoring with Contracts
Yishai A. Feldman Maayan Goldstein Shmuel Tyszberowicz IBM Haifa Research Lab IBM Haifa Research Lab The Academic College [email protected] [email protected] of Tel-Aviv Yaffo [email protected]
1 Introduction the assertions in the unit tests are replaced by contract checks, tests need only exercise the code, and can there- Design by contract [9] is a practical methodology for fore be written at a higher level than a single method or developing object-oriented programs together with their even class. However, the contracts still need to be refac- specifications. It offers immediate benefits in terms of tored with the code. This is easier than refactoring unit early error detection as well as long-term process im- tests, since what programmers have in mind when refac- provement. The contract consists of class invariants and toring code is the intended functionality of the modified method pre- and postconditions. Method preconditions code, which is directly expressed by the relevant con- must hold on entry to the method; it is the responsi- tracts. Furthermore, it is possible to automate contract bility of the caller to make sure they hold when the refactoring to a large extent [3, 7]. call is made. Method postconditions must hold on exit Automating contract refactoring, in conjunction with from the method, provided that the preconditions held other tools (such as code instrumentation, verification, on entry. Class invariants must hold for every object and contract discovery), also has the potential to in- of the class on entry to and exit from every non-private crease acceptance and widespread use of the design-by- method. The contract is part of the public information contract methodology. of the class, for use by clients. The contract has several methodological implications [9]: 2 Refactoring Contracts