This article discusses patching in Eclipse, including a feature introduced in Eclipse Galileo. To take advantage of the examples in this article, you need to have Eclipse installed and a source-code repository, such as Subversion (SVN) or Concurrent Versions System (CVS), available.
The Eclipse integrated development environment (IDE) facilitates work in a team environment by providing features that allow you to integrate with a source-control management system directly from the IDE. These features not only enable you to get source, view changes, and commit them but also provide the ability to work with changes by applying patches to code.
Patches can be exchanges in the form of files that contain the changes among versions of your
code in a standard diff format. When created correctly, the patch files contain only
the differences between the modified files and the files in your workspace. Not only does
this make the patches smaller but it also makes it
easier to apply the patches more selectively.
Sometimes in team development environments, it's necessary to share changes to the code base directly from developer to developer. Different scenarios for using patch files include:
- The change comes from outside the team — for example, in open source code when the change could come from someone in the community.
- The change cannot be committed into the current source tree for some reason, such as a breaking change, that would affect the build.
- The change is complex and needs to be integrated with another change before being committed into the source-code management system.
An advantage of a patch file is that it can be submitted as an attachment to an e-mail message or bug report. The patch file can then be applied to the source to integrate the modified code.
When you create patches in Eclipse, the patch is written in unified diff format. This means that you can create diffs from CVS or SVN and apply them to your Eclipse project.
It also means that you can rely on a standard format for the patch files so they're easily shared.
diff files come in several formats (see Resources to learn more about them).
Understanding the patch file format is not critical to understanding how to apply them in
Eclipse, but having a basic understanding of the diff file format used by Eclipse can help you
troubleshoot problems and understand what to expect when applying a patch.
For example, see the simple Motorcycle class in Listing 1. In this article, it serves as
a baseline example from which you'll make changes and see how the patch file appears in later examples.
Listing 1. The example
Motorcycle class
package com.nathangood.examples;
public class Motorcycle {
private int cc;
private String model;
private String make;
private String year;
public String getModel() {
return model;
}
public int getCc() {
return cc;
}
public void setCc(int cc) {
this.cc = cc;
}
public void setModel(String model) {
this.model = model;
}
public String getMake() {
return make;
}
public void setMake(String make) {
this.make = make;
}
public String getYear() {
return year;
}
public void setYear(String year) {
this.year = year;
}
}
|
Add a simple constructor to the class, such as the constructor in Listing 2.
Listing 2. A simple constructor using
make
public Motorcycle(String make) {
super();
this.make = make;
}
|
Now when you generate a unified diff between the modified class and the original version of the class,
your diff will look like the one in Listing 3.
Listing 3. The patch for adding the constructor
Index: src/com/nathangood/examples/Motorcycle.java
===================================================================
--- src/com/nathangood/examples/Motorcycle.java (revision 3)
+++ src/com/nathangood/examples/Motorcycle.java (working copy)
@@ -7,6 +7,11 @@
private String make;
private String year;
+ public Motorcycle(String make) {
+ super();
+ this.make = make;
+ }
+
public String getModel() {
return model;
}
|
The patch file contains only the new lines that have been added, plus a few lines before and after that provide some context for the change.
Note the following line in the patch file: @@ -7,6 +7,11 @@.
This line provides the line numbers and ranges of the changes immediately following
it. The minus sign (-) or plus sign (+) before each change corresponds with the
file names directly above the line. In this example, - refers
to revision 3, and + refers to the
working copy.
The changes in the working copy, which is the new version of the file, start at line 7 and go for 11 lines, including
the lines shown for context. The original version of the file, called revision 3 in this
example, included only six lines. The difference between the two are the five new lines
with a + in front of them.
Consider another example by removing the accessors for the
make variable, getMake()
and setMake() — discarding the changes to the constructor for the moment. The patch showing
the differences would look like Listing 4.
Listing 4. An example of removing elements with a patch
Index: src/com/nathangood/examples/Motorcycle.java
===================================================================
--- src/com/nathangood/examples/Motorcycle.java (revision 3)
+++ src/com/nathangood/examples/Motorcycle.java (working copy)
@@ -23,14 +23,6 @@
this.model = model;
}
- public String getMake() {
- return make;
- }
-
- public void setMake(String make) {
- this.make = make;
- }
-
public String getYear() {
return year;
}
|
The patch shows that the context of the changes started on line 23 of the version of the file
in the repository (revision 3) and went for 14 lines. Because lines from the file have
been deleted, the context of the new change also starts on line 23 and spans only six lines.
The lines to be deleted start with a -.
Finally, consider a modification to the original file (again discarding the last changes).
The changes are shown in bold in Listing 5, demonstrating a renaming of cc to cubicCentimeters.
Listing 5. An example of modifying elements with a patch
Index: src/com/nathangood/examples/Motorcycle.java
===================================================================
--- src/com/nathangood/examples/Motorcycle.java (revision 3)
+++ src/com/nathangood/examples/Motorcycle.java (working copy)
@@ -2,7 +2,7 @@
public class Motorcycle {
- private int cc;
+ private int cubicCentimeters;
private String model;
private String make;
private String year;
@@ -11,12 +11,12 @@
return model;
}
- public int getCc() {
- return cc;
+ public int getCubicCentimeters() {
+ return cubicCentimeters;
}
- public void setCc(int cc) {
- this.cc = cc;
+ public void setCubicCentimeters(int cubicCentimeters) {
+ this.cubicCentimeters = cubicCentimeters;
}
public void setModel(String model) {
|
The patch showing the changes is a little more sophisticated than simple additions or deletions because it shows the change by combining the two.
The context of the first change starts at line 2 and goes for seven lines. The context of the
changed file contains the same range because one line has been removed and one line has been
added to make the change. The original line containing cc was replaced with
the new line containing cubicCentimeters. The second modification in the file is done in
the context that starts on line 11 and goes for 12 lines in the same manner.
Now that you understand the basic structure of the patch file, you can create one in Eclipse to apply it to the same project in another workspace. If you'd rather run through these examples in the same workspace, simply make changes to a file in source control in Eclipse. Create the patch and revert to the original version of the file. You can then reapply the patch to see the changes you made come back again.
With the original version of the Motorcycle class, use the Source menu to generate a few
constructors, like those shown in Listing 6.
Listing 6. Example new constructors
public Motorcycle() {
super();
}
public Motorcycle(int cc, String model, String make, String year) {
super();
this.cc = cc;
this.model = model;
this.make = make;
this.year = year;
}
|
In Eclipse, open the context menu (usually the right mouse button) on the project and choose Team > Create Patch.
In the Create Patch window, select Save in File System (see Figure 1) and click Browse to find a suitable location for your new patch file. Click Next when finished.
Figure 1. Create Patch
On the next step, choose Project (see Figure 2) and click Finish. You can create a patch for more than one project in your workspace at the same time. When you choose Project, Eclipse builds the patch using the current project as the root directory for the patch and ignores the changes in the other projects. Limiting the patch scope to your project can be simpler because it reduces the number of changes you need to review later.
Figure 2. Selecting the patch root
After Eclipse creates the patch file, you can view it in Eclipse by clicking File > Open File to open the file. The patch will look similar to the one in Listing 7.
Listing 7. The patch that adds the new constructors
Index: src/com/nathangood/examples/Motorcycle.java
===================================================================
--- src/com/nathangood/examples/Motorcycle.java (revision 3)
+++ src/com/nathangood/examples/Motorcycle.java (working copy)
@@ -6,7 +6,19 @@
private String model;
private String make;
private String year;
-
+
+ public Motorcycle() {
+ super();
+ }
+
+ public Motorcycle(int cc, String model, String make, String year) {
+ super();
+ this.cc = cc;
+ this.model = model;
+ this.make = make;
+ this.year = year;
+ }
+
public String getModel() {
return model;
}
|
Applying a patch in Package Explorer
If you only have a single workspace available, revert the changes that you made to Motorcycle.java. Alternatively, you can switch to a workspace with original versions of the project files in it.
On an original version of the project, use the Team > Apply Patch context menu item to open the Apply Patch wizard shown in Figure 3. Select File, then click Browse to find the location of the patch file you created in "Creating a simple patch."
Figure 3. Choosing the input for the patch
Because you created the patch based on a project and not a workspace root, select Apply the patch to the selected file and select the project folder from the list (see Figure 4). Click Next.
Figure 4. Choosing the target for the patch
The next screen, shown in Figure 5, shows a comparison between the original version (Local Copy) and the version including the modifications (After Patch). Because this is a Java™ file, the Java Structure Compare section shows the differences in the file in an outline form, which makes it somewhat easier to understand.
Figure 5. Reviewing the changes before applying them
If you are confident of the changes shown, click Finish.
Now when you open the file, it includes the changes you made before.
An alternative method of applying patches with Eclipse Galileo is to simply paste the contents into the Package Explorer view. If you have Eclipse Galileo installed, you can apply the patch that you created by:
- Opening the patch file you created in a text editor.
- Copying the contents of the file to your clipboard.
- In the Package Explorer, right-clicking on the project and selecting Paste from the context menu.
- Following the wizard as shown when applying the patch from a file.
In the Review Patch step shown in Figure 5, there are several options for applying a patch. The simple patch in the previous example did not require any changes to the default options on the Review Patch step. However, there are some cases when you might need to modify the settings while you are reviewing the patch to get the results you want.
When applying a patch, sometimes you get errors in the Patch Contents list during the Review Patch step (see Figure 6). This is a good indication that you need to modify some of the patch options.
Figure 6. Dealing with errors while applying a patch
The Ignore leading path name segments option is useful if your original directory structure in the patch is different from the version to which you're applying the patch. You can simulate this behavior by creating the patch for the project and selecting the src folder in the Target Resource step (Figure 4) of the Apply Patch wizard. You will get errors (as in Figure 6), but if you change the Ignore leading path name segments value to 1 Eclipse can apply the patch correctly.
The Show matched hunks option displays the line numbers and context in the Patch Contents list.
The Fuzz factor option allows you to tell Eclipse to ignore some of the context lines when applying the patch. In the example in this article, the need for a Fuzz factor can be simulated by using the Source > Sort Members menu option to sort the original file before attempting to apply that patch. Because some of the context lines will now be out of order, you need the Fuzz factor to correctly apply the patch. You can click Guess to have Eclipse to make its best attempt at finding the Fuzz factor for you, or you can modify the setting until you're confident of the changes.
The Show Excluded option shows excluded patch operations, if any.
The Generate a .rej file for unmerged hunks stores the entries from the patch file that were not applied during the operation. To see this behavior in action, use the patch containing the new constructor, but before applying it, type your own, slightly different, constructor — like the one in Listing 8.
Listing 8. Adding a local constructor to create a conflict
public Motorcycle() {
// TODO: Create some conflict with this constructor
}
|
When you attempt to apply the patch, there will now be a conflict between the code in the
patch file and the code in the Motorcycle class. The conflict will not be applied to the modified
file. Instead, it will be written to a file called Motorcycle.java.rej, as shown in Listing 9.
Listing 9. The rejected patch code
@@ -5,6 +5,10 @@
private String model;
private String make;
private String year;
+
+ public Motorcycle() {
+ super();
+ }
public String getModel() {
return model;
|
The file shown in Listing 9 is not a complete, valid patch file. But you could use it to create a patch for the class if the conflicts were resolved first.
Creating a patch in the Synchronize View
Another method of creating a patch is in the Synchronize View, after synchronizing your changes with your code repository. To create a patch in the Synchronize View, open the Team Synchronizing perspective and click the synchronize button shown in Figure 7.
Figure 7. The synchronize button
Open the context menu for the project in the Synchronize View and click Create Patch. From there, follow the patch creation process described in "Creating a Simple Patch."
A reverse patch does just that: It reverses the action of the patch being applied. Instead of lines being added, they are removed. Lines that would be removed in the patch are instead added. You can use a reverse patch to revert certain changes from a previous version of a file or to back out changes from a patch that caused problems.
Eclipse's team tools allow you to easily share changes to code using patches in standard
unified diff format. Team members can now apply patches submitted as attachments in files
using the new method of pasting the patch contents in the Package Explorer in Eclipse Galileo.
Learn
-
See
diffat Wikipedia to learn more about the variousdiffformats used for patching. -
Check out the "Recommended Eclipse reading list."
-
Browse all the Eclipse content on developerWorks.
-
Follow developerWorks on Twitter.
-
New to Eclipse? Read the developerWorks article "Get started with the Eclipse Platform" to learn its origin and architecture, and how to extend Eclipse with plug-ins.
-
Expand your Eclipse skills by checking out IBM developerWorks' Eclipse project resources.
-
To listen to interesting interviews and discussions for software developers, check out check out developerWorks podcasts.
-
Stay current with developerWorks' Technical events and webcasts.
-
Watch and learn about IBM and open source technologies and product functions with the no-cost developerWorks On demand demos.
-
Check out upcoming conferences, trade shows, webcasts, and other Events around the world that are of interest to IBM open source developers.
-
Visit the developerWorks Open source zone for extensive how-to information, tools, and project updates to help you develop with open source technologies and use them with IBM's products, as well as our most popular articles and tutorials.
Get products and technologies
-
Download and learn more about SVN.
-
Dig in to CVS.
-
Check out the latest Eclipse technology downloads at IBM alphaWorks.
-
Download Eclipse Platform and other projects from the Eclipse Foundation.
- Download
IBM product evaluation versions
or explore
the online trials in the IBM SOA Sandbox and get your hands on application development tools and middleware products from
DB2®, Lotus®, Rational®, Tivoli®, and WebSphere®.
-
Innovate your next open source development project with IBM trial software, available for download or on DVD.
Discuss
-
The Eclipse Platform newsgroups should be your first stop to discuss questions regarding Eclipse. (Selecting this will launch your default Usenet news reader application and open eclipse.platform.)
-
The Eclipse newsgroups has many resources for people interested in using and extending Eclipse.
-
Participate in developerWorks blogs and get involved in the developerWorks community.

Nathan A. Good lives in the Twin Cities area of Minnesota. Professionally, he does software development, software architecture, and systems administration. When he's not writing software, he enjoys building PCs and servers, reading about and working with new technologies, and trying to get his friends to make the move to open source software. He's written and co-written many books and articles, including Professional Red Hat Enterprise Linux 3, Regular Expression Recipes: A Problem-Solution Approach and Foundations of PEAR: Rapid PHP Development.
Comments (Undergoing maintenance)





