recording finer-grained software evolution with ide: an annotation-based approach

35
Shinpei Hayashi and Motoshi Saeki Dept. of Computer Science, Tokyo Institute of Technology Japan Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach IWPSE-EVOL 2010

Upload: shinpei-hayashi

Post on 15-Jan-2015

2.054 views

Category:

Documents


0 download

DESCRIPTION

Presented at IWPSE-EVOL 2010 http://dx.doi.org/10.1145/1862372.1862378

TRANSCRIPT

Page 1: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

Shinpei Hayashi andMotoshi SaekiDept. of Computer Science,Tokyo Institute of TechnologyJapan

Recording Finer-GrainedSoftware Evolutionwith IDE:An Annotation-Based Approach

IWPSE-EVOL 2010

Page 2: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

Recording Finer-Grained SE− Avoiding to commit mixed changesets

Annotation-Based Approach− Developers perform edit operations of source

code together with classifying them− Restructuring source code delta

Results: It works well!− Defined algorithms for automation− Implemented a prototyping tool

Abstract

2

Page 3: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

3

Task Level Commit [SCM Patterns]

− We should avoid to commit mixed changesets

Background

Revision: 1Log: fixed bug #5,

refactored, andcorrected a typo

Revision: 1Log: fixed bug #5

Revision: 2Log: refactored

Revision: 3Log: corrected a typo

diff

diff

diff

diff+-+-

++

--++

--+++-+-++

Mixedchangeset

Page 4: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

4

Task Level Commit [SCM Patterns]

− We should avoid to commit mixed changesets

Why?− Reuse (e.g. backport): separation required if we

apply a part of a changeset to another branch− Reverting: extraction needed if we revert a part

of a changeset− Understanding: the relations are unclear if the

commit log of a changeset describes multiple changes

Background

Page 5: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

5

Mixed changesets occur in practice− Bug-fix + logging− Large refactorings (via transitional state)

Problems

Page 6: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

6

Example: bug-fix + loggingint foo() {

int state = ……;

……state = bar(state, false);

…… }

Page 7: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

7

1. Insertion of logging function calls (LFCs) +finding the bug by executing the program and confirming outputs of LFCs

Example: bug-fix + loggingint foo() {

int state = ……;log.trace(”state = ” + state);……state = bar(state, false);log.trace(”state = ” + state);……

}

Page 8: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

8

1. Insertion of LFCs + finding the bug2. Fixing the bug

Example: bug-fix + loggingint foo() {

int state = ……;log.trace(”state = ” + state);……state = bar(state, true);log.trace(”state = ” + state); ……

}

false

true

Page 9: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

9

1. Insertion of LFCs + finding the bug2. Fixing the bug3. Execution again for confirming correct output4. Commit

Example: bug-fix + loggingint foo() {

int state = ……;log.trace(”state = ” + state);……state = bar(state, true);log.trace(”state = ” + state); ……

}

Page 10: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

10

1. Insertion of LFCs + finding the bug2. Fixing the bug3. Execution again for confirming correct output4. Commit

Example: bug-fix + loggingint foo() {

int state = ……;log.trace(”state = ” + state);……state = bar(state, true);log.trace(”state = ” + state); ……

}

Difficult to commit each of them independently in advance

Dependseach other

Page 11: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

11

Involved with basic refactorings Reverting needed if we commit each of

basic refactorings

Example: large refactoring

Refactoring 1 Refactoring 2 Refactoring 3

Large refactoring

commit commit commitrevert

commit

Page 12: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

12

Mixed changesets exist in practice− Bug-fix + logging− Large refactorings (via transitional state)

Changes should be managed on IDE− Hypothesis: developers can identify the

timing of switching their editing intentions

Our Solution

Page 13: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

13

Edit + mode changes Structuring edits

according to modes

Proposed Approach

Developer

IDE

time

r3:“typo ..."

r2:"refactored ..."

r1:"fixed bug #5 ..." Version

Archive

<<edit>>

1: fixing bug #5Modes

: mode changes

<<annotate>>

Structuring

2: correcting a typo3: Move Method refactoring

Page 14: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

14

Example: bug-fix + loggingint foo() {

int state = ……;

……state = bar(state, false);

…… }

Page 15: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

15

1. Insertion of logging function calls (LFCs) +finding the bug by executing the program and confirming outputs of LFCs

Example: bug-fix + loggingint foo() {

int state = ……;log.trace(”state = ” + state);……state = bar(state, false);log.trace(”state = ” + state);……

}

Editingby mode 1

Page 16: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

16

1. Insertion of LFCs + finding the bug2. Fixing the bug

Example: bug-fix + loggingint foo() {

int state = ……;log.trace(”state = ” + state);……state = bar(state, true);log.trace(”state = ” + state); ……

}

Editingby mode 2

Page 17: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

17

1. Insertion of LFCs + finding the bug2. Fixing the bug3. Execution again for confirming correct output4. Commit

Example: bug-fix + loggingint foo() {

int state = ……;log.trace(”state = ” + state);……state = bar(state, true);log.trace(”state = ” + state); ……

}

Committingas revisions

1 and 2

Page 18: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

18

Use individual mode for each refactoring

Example: large refactoring

Refactoring 1 Refactoring 2 Refactoring 3

Large refactoring

commit commit commit

Mode 1By mode 2 By mode 3

Page 19: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

19

Ordering edit operations Deciding the group order

Automation

Developer

IDE

time

r3:“typo ..."

r2:"refactored ..."

r1:"fixed bug #5 ..." Version

Archive

<<edit>>

1: fixing bug #5Modes

: mode changes

<<annotate>>

Structuring

2: correcting a typo3: Move Method refactoring

Page 20: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

20

Ordering edit operations Deciding the patch order

Automation

Developer

IDE

time

r3:“typo ..."

r2:"refactored ..."

r1:"fixed bug #5 ..." Version

Archive

<<edit>>

1: fixing bug #5Modes

: mode changes

<<annotate>>

Structuring

2: correcting a typo3: Move Method refactoring

Which ordersare feasible?

< << << << << << <

Page 21: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

21

Proposed SystemInputs Outputs

Source code deltas for eachintentional changesMode switching

information• when• which mode

Edit history(Seq. of

edit operations)

Page 22: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

22

Edit Operations (EOs)int foo() {int state = 1; return state;

}

int foo() {int state = 1;log.trace(state);return state;

}

int foo() {int state = 1;log.trace(state);return state+1;

}

pi = (add, f, 29, 20)

pj = (add, f, 63, 2)

A code fragment is added• to file f• begins with 29th character• Its length is 20

Page 23: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

23

Modifying the offsetsof EOs

Commutations of EOsint foo() {int state = 1; return state;

}

int foo() {int state = 1;log.trace(state);return state;

}

int foo() {int state = 1;log.trace(state);return state+1;

}

pi = (add, f, 29, 20)

pj = (add, f, 63, 2)

int foo() {int state = 1; return state+1;

}

int foo() {int state = 1;log.trace(state);return state+1;

}

pi' = (add, f, 29, 20)

pj' = (add, f, 43, 2)

Page 24: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

24

Bubble sort basedon group orders− E.g. < <

EOs are commutated when they are swapped

sorting criteria neededfor achieving thatall commutationssucceed

Ordering EOstime

Page 25: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

25

3 cases

When Commutations Fail

(a) add; remove

pi pj

(b) add; add

pi pj pi pj

(c) remove; remove

Page 26: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

26

Possible group order: |G|! cases< << << << << << <

Deciding candidates basedon commutability of EOs

Deciding Group Order

time

Impossible

Impossible

Impossible

Impossible

Page 27: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

Edit history(XML)

27

ModeManager: As an Eclipse plug-in Automating the reordering mechanism

Tann: Prototype Implementation

Eclipse

OperationRecorder[Omori 08]

• Collecting EOs

ModeManager• UI of mode switching• Collecting switch info.

commute.rb• Reordering EOs

based on modes

SwitchingInformation

Outputs:Deltas for each mode

Page 28: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

28

Page 29: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

29

The currentmode

The number ofavailable modes

The title ofthe current mode

Page 30: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

30

Application Exampleimport node.Directory;import node.Entry;import node.File;import node.FileTreatmentException;import node.Link;import observer.SizeObserver;import visitor.ListVisitor;

public class Main {public static void main(String[] args) {

try {Directory rootDir = new Directory("rootDir");Directory dir1 = new Directory("dir1");File file1 = new File("file1", 100);file1.addObserver(new SizeObserver());rootDir.add(file1);rootDir.add(dir1);dir1.add(new File("file2", 200));dir1.add(new File("file3", 300));Link link1 = new Link(file1);dir1.add(link1);

Link link2 = new Link(file1);dir1.add(link2);

// for debuggingSystem.out.println("total size : " + rootDir.getSize());rootDir.accept(new ListVisitor());

// executing Observerfile1.setSize(50);

((Entry)file1).setContent("this is file1");System.out.println(file1.getContent());((Entry)link1).setContent("this is link1");System.out.println(link1.getContent());((Entry)link2).setContent("this is link2");System.out.println(link2.getContent());

} catch (FileTreatmentException e) {// FIXMEe.printStackTrace();

}}

}

1

2

Adding method invocations

Adding comments

Page 31: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

31

Raw delta

Application Example@@ -21,4 +21,8 @@

dir1.add(link1);

+ Link link2 = new Link(file1);+ dir1.add(link2);+ + // for debugging

System.out.println("total size : " + rootDir.getSize());rootDir.accept(new ListVisitor());

@@ -31,5 +35,8 @@((Entry)link1).setContent("this is link1");System.out.println(file1.getContent());

+ ((Entry)link2).setContent("this is link2");+ System.out.println(file1.getContent());

} catch (FileTreatmentException e) {+ // FIXME

e.printStackTrace();}

@@ -21,4 +21,7 @@dir1.add(link1);

+ Link link2 = new Link(file1);+ dir1.add(link2);+

System.out.println("total size : " + rootDir.getSize());rootDir.accept(new ListVisitor());

@@ -31,4 +34,6 @@((Entry)link1).setContent("this is link1");System.out.println(file1.getContent());

+ ((Entry)link2).setContent("this is link2");+ System.out.println(file1.getContent());

} catch (FileTreatmentException e) {e.printStackTrace();

@@ -24,4 +24,5 @@dir1.add(link2);

+ // for debuggingSystem.out.println("total size : " + rootDir.getSize());rootDir.accept(new ListVisitor());

@@ -37,4 +38,5 @@System.out.println(file1.getContent());

} catch (FileTreatmentException e) {+ // FIXME

e.printStackTrace();}

Delta by Tann

Page 32: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

32

Positive points− Not depend on programming languages− Fully-automated (except for classification)− High affinity to traditional SCMs

(current) Negative points− Not considering syntaxes/semantics of

programming languages− Classifications have to be done correctly

Pros and Cons

Page 33: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

33

Improving maturity of implementation− Collaborating with UI of underlying SCM− Warning when the structuring fails

New UI for reclassifying EOs− Changing the group of past EOs

Other applications− Large (group-level) undo on IDE

Future Work

Page 34: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

3

Task Level Commit [SCM Patterns]

− We should avoid to commit mixed changesets

Background

Revision: 1Log: fixed bug #5,

refactored, andcorrected a typo

Revision: 1Log: fixed bug #5

Revision: 2Log: refactored

Revision: 3Log: corrected a typo

diff

diff

diff

diff+-+-

++

--++

--+++-+-++

Mixedchangeset

13

Edit + mode changes Structuring edits

according to modes

Proposed Approach

Developer

IDE

time

r3:“typo ..."

r2:"refactored ..."

r1:"fixed bug #5 ..." Version

Archive

<<edit>>

1: fixing bug #5Modes

: mode changes

<<annotate>>

Structuring

2: correcting a typo3: Move Method refactoring

Edit history(XML)

27

ModeManager: As an Eclipse plug-in Automating the reordering mechanism

Tann: Prototype Implementation

EclipseEclipse

OperationRecorder[Omori 08]

•Collecting EOs

OperationRecorder[Omori 08]

•Collecting EOs

ModeManager•UI of mode switching•Collecting switch info.

ModeManager•UI of mode switching•Collecting switch info.

commute.rb•Reordering EOsbased on modes

commute.rb•Reordering EOsbased on modes

SwitchingInformation

Outputs:Deltas for each mode26

Possible group order: |G|! cases< << << << << << <

Deciding candidates basedon commutability of EOs

Deciding Group Order

time

failedfailed

Impossible

Impossible

Impossible

Impossible

Page 35: Recording Finer-Grained Software Evolution with IDE: An Annotation-Based Approach

35

Photo by tokyofoodcasthttp://www.flickr.com/photos/tokyofoodcast/92537891/

Credits